【问题标题】:Delphi TFontDialog - How to scale for High Dpi?Delphi TFontDialog - 如何针对高 Dpi 进行缩放?
【发布时间】:2020-04-27 23:54:54
【问题描述】:

我想在高 dpi 显示器上使用带有 Delphi 10.3.3 的 TFontDialog

但不幸的是,Delphi 并没有真正扩展内容。 (检查示例 (Beispiel) 的位置!)

我有 2 台显示器。主要有 96ppi,另一个 144ppi。 我的应用程序正在第二个上运行。

您是如何在您的应用程序中解决此类问题的? 有没有办法解决这个问题,还是我必须希望 Delphi 10.4 能解决这个问题?

使用 200% 或更高时,您将无法再阅读字体大小。

编辑(2020-01-13):

一切都取决于 Delphi 的 DPI 感知集:

无、无意识和系统意识:

FontDialog 的大小为 648x518 像素,一切都很好,但是很模糊

每台显示器:

FontDialog 的大小为 433x346 像素,并且太小 (100%)

每个监视器 V2:

FontDialog 的大小为 648x528 像素,一切都很清晰但不正确(见图)

【问题讨论】:

  • 您应该启用应用的 DPI 感知。如果您需要具有不同 DPI 值的多显示器 UI,请使用“每显示器”意识。这是在 Windows 平台上获取有关此信息的链接:docs.microsoft.com/en-us/windows/win32/hidpi/…
  • DPI-Awareness 通过 Delphi manifest 设置为“per Monitor V2”。
  • TFontDialog 只是 Win32 ChooseFont() API 的包装器,因此对话框中的任何 DPI 问题都是操作系统本身的问题,而不是 VCL 的问题。
  • @Jens 当使用FontDialog.Execute 打开对话框时,您是否将表单窗口句柄作为参数传递给执行调用,例如FontDialog1.Execute(Form1.Handle)?不确定,但我猜这将是必需的,以便 Dialog 可以检索打开它的显示器的正确 DPI 分辨率。
  • @SilverWarior 如果 HWND 没有传递给 Execute(),它使用当前活动表单的 HWND。

标签: delphi dialog highdpi


【解决方案1】:

不幸的是,TFontDialog,或者确切地说是来自 Windows 的底层 ChooseFont,不(尚)支持 per Monitor V2 DPI 感知。作为一种解决方法,您可以在显示对话框时暂时切换到系统感知,然后再切换回来。

为了实现这一点,我建议使用一个覆盖 TFontDialog 的插入器类:

type
  TFontDialog = class(Vcl.Dialogs.TFontDialog)
  protected
    function TaskModalDialog(DialogFunc: Pointer; var DialogData): Bool; override;
  end;

function TFontDialog.TaskModalDialog(DialogFunc: Pointer; var DialogData): Bool;
var
  previousDpiContext: DPI_AWARENESS_CONTEXT;
begin
  previousDpiContext := SetThreadDpiAwarenessContext(DPI_AWARENESS_CONTEXT_SYSTEM_AWARE);
  try
    Result := inherited TaskModalDialog(DialogFunc, DialogData);
  finally
    SetThreadDpiAwarenessContext(previousDpiContext);
  end;
end;

请注意,给定和从对话框中检索的字体大小基于系统 DPI,并且必须根据所使用的显示器 DPI 进行缩放。

【讨论】:

    猜你喜欢
    • 2021-12-15
    • 1970-01-01
    • 2015-04-23
    • 2020-05-18
    • 1970-01-01
    • 1970-01-01
    • 2018-08-07
    • 2010-09-26
    • 1970-01-01
    相关资源
    最近更新 更多