随着高分辨率屏幕越来越多,以前完全没有注意到的高分屏问题提上日程。
由于印刷和显示技术的历史限制,每英寸96个点长期被当成唯一标准,操作系统、软件开发都把96DPI当成理所当然的。前些年更高分辨率的显示器才普及开来,同尺寸屏幕,分辨率越高像素越小,按像素显示看不清。操作系统为了支持这些显示器,增加了缩放功能,操作系统会自动设置一个合适的缩放率,比如125%,这个基本属于入门显示器,好一些的150%,mac基本都是200%。
大部分程序默认支持系统的缩放,无需改动即可在高分屏上正常显示,但是有些程序是不支持系统缩放的,显示出来就会很小,没法看。对于专业像素处理程序,这是他们自己的事情,而对于使用了不支持高分屏的界面库的程序,就有些抓狂,不过会者不难,解决方法很简单。
下面分别讲MFC程序如何设置高分屏支持以及如何解决不支持高分屏的界面库的缩放问题。
MFC程序如何设置高分屏:
项目-设置-清单工具-输入和输出,“DPI识别功能”,默认“高DPI识别”,比较一下“无”和“高DPI识别”的区别:
这是一个对话框程序,无标题栏、无边框,设置了圆角(本来是为了验证圆角对话框,却有了重大发现),无高DPI识别的效果:
再看有高DPI识别的效果:
窗口长宽差不多,形状却完全不同了(还应该注意到文字和弧线边缘的锯齿的区别)。
想亲自验证可以用如下代码实现圆角:
// CMFCApplication1Dlg 消息处理程序
CRgn m_rgn;
BOOL CMFCApplication1Dlg::OnInitDialog()
{
。。。。。。
// TODO: 在此添加额外的初始化代码
// 创建圆角矩形区域
//this->MoveWindow(0, 0, 500, 500);
CRect rc; // rounded rectangle
GetWindowRect(&rc); // window rect in screen coords
m_rgn.CreateRoundRectRgn(rc.left, rc.top, rc.right + 1, rc.bottom + 1,
250, 250); // rounded rect w/50 pixel corners
//设置这个区域
SetWindowRgn(m_rgn, TRUE); // set window region to make rounded window
return TRUE; // 除非将焦点设置到控件,否则返回 TRUE
}
很显然的,我们能猜到是不同界面元素对不同DPI的处理方式是不同的导致了这种差异。所以呢,不要随便改这个属性,改了就要重新测一遍,看看界面有没有乱套,而且最好在高质量的屏幕上测试,125%的效果不明显。
顺便说一句,Qt实现高分屏支持是加一句代码,就一句。
程序不支持高DPI识别的如何解决?
某些界面库不支持高DPI识别,这就比较麻烦,但是也有不理想的解决方案。操作系统知道有些程序写得不好,但是还得帮他们,操作系统允许指定一个程序强制放大显示,可以手动在文件属性里设置,也可以用程序写入注册表解决。
手动设置:
文件上点右键-属性-兼容性-更改高DPI设置:
选中最下面的“替代高DPI缩放行为”,下拉列表选择“系统”或者“系统(增强)”,整个程序会被放大,但是由于这是按像素放大,模糊和锯齿是不可避免的。“系统”和“系统(增强)”是有区别的,其中一种不会对视频播放窗口放大(具体是哪一种,试试就知道了……嗯,没错,我忘了)。
设置完之后注册表里会增加一些信息,程序可以直接模仿,实现程序自动识别高分屏(代码我以后弄出来给大家看),注册表信息是这样的:
[HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers]
"C:\\Program Files\\VideoLAN\\VLC\\vlc.exe"="~ GDIDPISCALING DPIUNAWARE"
代码在这里:C++代码检测高分屏和设置高DPI支持(完整源码)-CSDN博客
(这里是文档结束)