20

我正在编写一个需要在高 dpi Windows(192dpi 而不是 96dpi)上运行的 Qt 应用程序。

不幸的是,Qt 框架还不支持高 dpi(至少在 Windows 上),所以我的应用程序及其所有元素看起来只有它应有的一半大小。

有什么方法可以强制/模拟 Windows 自动升级此类应用程序?

4

5 回答 5

10

使用固定坐标和大小的应用程序在高 DPI 分辨率下看起来很小。尽管即使使用布局,也存在一些关于元素和字体大小和边距的问题。幸运的是,自 Qt 5.4 起就支持高 DPI 显示器,因为已经修复了许多高 DPI 问题

Windows 上的应用程序可以采用以下“DPI Awareness”级别之一(来自 Qt 文档):

  • DPI Unaware:此级别已在 Windows-Vista 中引入。Windows 将假装应用程序在 1920x1080 的 96 DPI 标准显示器上运行,并相应地缩放应用程序。它旨在适应为低 DPI 显示器设计的旧应用程序。这种类型的缩放可能会导致一些伪影。
  • System-DPI Aware:此级别已在 Windows-Vista 中引入。仅当连接了多个监视器时,它才与 Per-Monitor DPI Aware 不同。Windows 将计算适用于所有连接的监视器的缩放比例。
  • Per-Monitor DPI Aware:此级别已在 Windows 8.1 中引入。Windows 根本不执行任何缩放。

它还指出:

默认情况下,Qt 应用程序是 Windows 8.1 上的 Per-Monitor DPI Aware 或旧版本 Windows 上的 System-DPI Aware。从 Qt 5.4 开始,可以通过将参数传递给平台插件来指定级别(请参阅使用 qt.conf):

<application> -platform windows:dpiawareness=0,1,2

您可以在此处阅读更多信息。

一般来说,要在高 DPI 显示器上拥有良好的 UI,请考虑以下几点:

  • 使用最新版本的 Qt
  • 使用布局并避免固定大小(除非您自己计算缩放比例)
  • 根据您的应用程序需要进行适当的与 DPI 相关的设置,例如,Qt::AA_UseHighDpiPixmaps如果您使用像素图,请设置属性QPainter,或者在特殊情况下计算缩放比例以调整某些元素大小。
于 2015-02-19T04:47:05.467 回答
9

从 Qt 5.6 开始,Qt 通过属性或环境变量完全支持高 DPI 监视器(在 OS X 上除外,其中支持是本机的)。对于属性方法,使用:

#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication::setAttribute(Qt::AA_EnableHighDpiScaling); // DPI support

    QApplication app(argc, argv);   
    return app.exec();
}

或者设置系统环境变量:

QT_AUTO_SCREEN_SCALE_FACTOR=1

我已经在 Windows 10 上使用高 DPI Surfacebook 监视器测试了这两种方法,结果按预期正确缩放。

于 2016-03-17T11:09:12.377 回答
7

这是在 Windows 上解决问题的最快方法。

在可执行文件旁边,创建一个 qt.conf 文件(如果还没有)并添加以下内容:

[Platforms]
WindowsArguments = dpiawareness=0

放大时窗口会显得模糊。此解决方案的最大优势在于 Windows 进行缩放,而不是 Qt。因此,伪影的出现被最小化。此外,这可以应用于已经分发的应用程序,因为它不需要重建。

当然,这不是最令人愉快的结果,而是让您在短期内摆脱困境的最快结果,让您毫无压力地开发“真正的”DPI-aware 版本。

于 2018-05-16T10:02:46.040 回答
1

我正在使用 Qt 4.8。首先,您应该使用布局。我的目标是防止用户也调整对话框、表单等的大小。

通过将此代码放入对话框构造函数中,我在不同的 DPI 上实现了正确的显示结果:

adjustSize();
setFixedSize(size());

第一行adjustSize()调整对话框的大小以适应其内容。第二行在setFixedSize(size())将对话框的大小调整为内容后修复了对话框的大小,并防止用户调整它的大小。您无需设置尺寸政策。

于 2017-04-15T19:25:05.487 回答
0

我正在使用 Qt 4.8.7。这是我的代码。

static float dpiX = (float)0;
inline int autoDpiSize(int inSize)
{
    if (dpiX == (float)0)
    {
        HDC screen = GetDC(0);
        dpiX = static_cast<float >(GetDeviceCaps(screen, LOGPIXELSX)) / 96.0;
        ReleaseDC(0, screen);
    }
    return dpiX * inSize;
}
someWidget->setFixedHeight(autoDpiSize(30));
于 2020-06-05T02:19:39.843 回答