• 从WM_DISPLAYCHANGE消息的角度谈谈分辨率


      众所周知,WM_DISPLAYCHANGE是当Windows显示器分辨率改变之后发送给所有的窗口的消息。但是不知道你有没有想过,显示器的分辨率不是固定的吗?为什么会有这条消息呢?

      这里就要说一下逻辑分辨率和物理(设备)分辨率了:

      我们说某个品牌的显示器的分辨率为80DPI(Dots Per Inch),是指在显示器的有效显示范围内,显示器的的显像设备可以在每英寸荧光屏上产生80个光点。举个例子来说,一台14英寸的显示器(荧光屏对角线长度为14英寸),其点距为0.28mm,那么:显示器分辨率=25.3995mm/inch÷0.28mm/Dot≈90DPI(1 inch=25.3995mm)。   显示器出厂时一般并不标出表征显示器分辨率的DPI值,只给出点距,我们根据上述公式即可算出显示器的分辨率。根据我们算出的DPI值,我们进而可以推算出显示器可支持的最高显示模式。假设该14英寸显示器荧光屏有效显示范围的对角线长度为11.5英寸,因显示器的水平方向和垂直方向的显示比例为4:3,故可设有效显示范围水平宽度为4X英寸,垂直高度为3X英寸,根据数学上的勾股定理,可得X=11.5÷5=2.3英寸。所以有效显示范围宽度为2.3×4=9.2英寸,垂直高度为2.3×3=6.8英寸。最高显示模式约为:800(9.2×90)×600(6.8×90),这时是用一个点(Dot)表示一个像素(pixel)。

      这里点的概念并非是书中所说的字体点的概念,而是指:

      DPI中的点(Dot)与图像分辨率中的像素(Pixel)是容易混淆的两个概念,DPI中的点可以说是硬件设备最小的显示单元,而像素则既可是一个点,又可是多个点的集合。

      而书中所指的字体点的概念则是指:

      在传统的排版中,字体字符的大小是由“点值”(point size 亦称磅值)来表示的。一点大约是1/72英寸(inch)。在计算机排版中,1点通常假定正好是1/72英寸。

      从这里我们可以很清楚的知道,设备分辨率,或者说这里的显示器的物理分辨率,就是指每英寸的物理硬件可显示的点数。而像素则是一个一个或多个点形成的一个集合单位,但从编程的角度讲,编程人员所能操纵的最小的单位就是像素。所以其实在我看来,像素其实是可以理解为一个逻辑分辨率所拥有的概念。由以上设备分辨率的概念对比《Windows程序设计》中分辨率的概念:

      在本书中,“分辨率”被阉割定义为每度量单位(通常是英寸)中含有的像素数。

      不难理解,这里的分辨率其实指的是逻辑分辨率,其中像素正是程序所能操纵的最小逻辑单位。由此也可以引出这个问题的答案了:系统软件控制了逻辑分辨率的大小,定义为每英寸的像素数。但显然这个逻辑分辨率是受到物理分辨率(即每英寸的点数)的限制的,最大的情况即为一个点代表一个像素,此时逻辑分辨率和物理分辨率是相同的,而当一个像素包含多个点时(由软件算法控制调整),逻辑分辨率就会变得不同。这也正是Windows中分辨率可以调整的原因。

      然后说一下有关GetDeviceCaps函数中获取的分辨率和尺寸的关系。

      首先,当我们以HORZRES或VERTRES为参数调用GetDeviceCaps()函数时,你所得到的是显示器的(逻辑)水平分辨率或(逻辑)物理分辨率。这没有问题。而我们又知道,当以LOGPIXELSX和LOGPIXELSY为参数调用GetDeviceCaps()函数时候,所得到的则是“每英寸的像素数”(当然,如果不具有正方形像素,所得到的两个值可能会不同。),而这两个值则是由用户在【控制面板】的【显示】中选择的以每英寸的像素点数为单位的假定的分辨率。这也没有问题,而在WindowsNT 中,以VERTSIZE或HORZSIZE为参数调用GetDeviceCaps()函数所得到值则是由以上两者计算出来的,我们知道,这两个值所表示的是指的“以毫米为单位的物理屏幕宽度(高度)”。这也正是《Windows程序设计》中所解释的东西。因为它并不是真正的物理尺寸,而是指对于用户来说(因为LOGPIXELSX和LOGPIXELSY为参数调用GetDeviceCaps()函数所得的值是用户所选择的(很大程度上是用户认为最舒适的分辨率)值)最合适的“物理尺寸”,所以对于程序而言,这正是它所需要的。在这种情况下,无论是连接多个显示设备还是连接投影仪,都会显示出来对用户非常合适的分辨率大小(其实就是如果不合适就可以直接通过上述的【显示】中更换值)。

      这正是《Windows程序设计》中所说的“并不是真正的物理尺寸”,和“如果程序需要视频显示器的实际物理尺寸怎么办?,最好的解决办法可能是使用一个对话框来实际要求用户输入他们”的原因。

  • 相关阅读:
    最小生成树(Prime算法)
    Spiral Matrix
    大于非负整数N的第一个回文数 Symmetric Number
    毁灭者问题
    查看Centos7虚拟机的IP
    创建Redis集群时遇到问题(二)
    EditPlus通过FTP远程连接Linux
    Redis集群搭建
    创建Redis集群时遇到问题(一)
    安装redis报错“系统 Ruby 版本过低”的解决办法
  • 原文地址:https://www.cnblogs.com/FWFC/p/8185655.html
Copyright © 2020-2023  润新知