You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Delphi Tokyo启用高DPI后TImage运行时比设计时缩小的问题

问题原因

Delphi Tokyo的VCL框架在高DPI模式下,会自动对窗体和控件按系统DPI比例进行缩放,但TImage的静态图像资源默认基于96DPI(标准DPI)设计,未适配高DPI环境:

  • 当Stretch=True时,图像被强制拉伸到缩放后的控件尺寸,因原始分辨率不足导致像素模糊。
  • 当Stretch=False时,图像仅按原始像素尺寸显示,而控件实际显示区域因高DPI缩放相对设计比例“缩小”,所以图像看起来只有窗体一半大小。
    禁用高DPI后,系统停止缩放逻辑,窗体和图像都按原始96DPI渲染,因此显示正常。
解决方法

1. 确保项目启用正确的高DPI支持

  • 打开项目选项,进入Application → Manifest:
    • 勾选Enable runtime themes,保证主题渲染正常。
    • 在High DPI设置中,优先选择Per Monitor V2(支持动态DPI变化),或至少勾选High DPI aware。
  • 确认窗体的Scaled属性设为True(默认值,确保窗体跟随DPI缩放)。

2. 使用多分辨率图像适配不同DPI

为常用DPI比例(100%/96DPI、125%/120DPI、150%/144DPI、200%/192DPI)准备对应分辨率的图像文件,比如命名为image_96.png、image_120.png等。在代码中根据当前屏幕DPI加载对应图像:

procedure TForm1.LoadImageByDPI;
var
  Dpi: Integer;
  ImagePath: string;
begin
  Dpi := Screen.PixelsPerInch;
  case Dpi of
    96: ImagePath := 'image_96.png';
    120: ImagePath := 'image_120.png';
    144: ImagePath := 'image_144.png';
    192: ImagePath := 'image_192.png';
  else
    ImagePath := 'image_96.png'; //  fallback到标准DPI图像
  end;
  Image1.Picture.LoadFromFile(ImagePath);
  Image1.Stretch := True; // 保持图像适配控件尺寸
end;

在窗体OnCreate和OnDpiChanged事件中调用该方法,确保DPI变化时自动切换图像。

3. 动态缩放单张图像(无多分辨率资源时)

如果只有单张原始图像,可通过代码按DPI比例缩放,同时用高质量渲染避免模糊:

procedure TForm1.ScaleImageToDPI;
var
  DpiScale: Double;
  OriginalBmp: TBitmap;
  ScaledBmp: TBitmap;
begin
  DpiScale := Screen.PixelsPerInch / 96; // 计算DPI缩放比例
  OriginalBmp := TBitmap.Create;
  ScaledBmp := TBitmap.Create;
  try
    OriginalBmp.LoadFromFile('original_image.png');
    // 创建缩放后的Bitmap
    ScaledBmp.SetSize(Round(OriginalBmp.Width * DpiScale), Round(OriginalBmp.Height * DpiScale));
    // 使用高质量拉伸
    ScaledBmp.Canvas.Brush.Color := clWhite;
    ScaledBmp.Canvas.FillRect(Rect(0, 0, ScaledBmp.Width, ScaledBmp.Height));
    ScaledBmp.Canvas.StretchDraw(Rect(0, 0, ScaledBmp.Width, ScaledBmp.Height), OriginalBmp);
    // 赋值给TImage
    Image1.Picture.Assign(ScaledBmp);
    Image1.Stretch := False; // 此时无需再拉伸,图像已适配尺寸
  finally
    OriginalBmp.Free;
    ScaledBmp.Free;
  end;
end;

同样在OnCreate和OnDpiChanged事件中调用该方法,处理初始加载和DPI变化场景。


内容的提问来源于stack exchange,提问作者robertjains

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 15:52:38