Delphi 开发者,显示图片请忘掉VCL中的 TImage 吧

news2024/11/26 12:30:51

 

目录

序言

 使用TImageCollection和TVirtualImageList组件支持高分辨率图像

一、总览

二、使用图像收集组件TImageCollection

2.1 图像收集组件编辑器

2.2 将现有 TImageList 载入 TImageCollection

三、使用Virtual ImageList 组件

3.1 Virtual ImageList Component 编辑器

四、多分辨率下使用图像组件 TVirtualImage

五、最佳实践

5.1 多种尺寸(Multiple sizes)

5.2 在应用程序中支持高 DPI 并转换旧版 TImageLists

5.3 在 TCanvas 上绘图时平滑缩放


序言

        delphi开发者都知道,显示图片都会使用TImage,非常方便,支持很多种图片格式,但是技术发展到今天,高分辨率显示器(4K 3840x2160)已经逐步在普及,那么TImage就显得力不从心了,所谓力不从心并不是说不能显示,TImage无论是在2K分辨率还是4K分辨率显示器上,都能正常的按照实际大小显示图像,但是,如果我们在4K分辨率上显示的图像,感觉比例调整的可以,但是到了2K(1920x1080)上图像就感觉放大了一倍。如下图:

  

         注意看,在4K分辨率下开发的程序(左图)到了2K分辨率下运行,TImage显示的图片明显变大2倍。这就是说TImage并不支持多分辨率下自动缩放并显示一致的功能。那么哪个控件可以实现呢,就是上图种的TVirtualImage控件,这个控件可以完全实现在不同分辨率下自动缩放,从而实现一致的的UI效果。

大多数delphi开发者可能还没有使用TVirtualImage控件,本片详细介绍高清分辨率下Delphi图片显示相关控件。Delphi 11开始支持高分辨率显示器,包括开发环境IDE

 使用TImageCollection和TVirtualImageList组件支持高分辨率图像

一、总览

        通过结合使用 TImageCollection 组件和 TVirtualImageList 组件,RAD Studio 可以在 Windows VCL 应用程序中包含缩放、高 DPI 和多分辨率图像。

请注意

        如果您在跨平台应用程序中使用 FireMonkey,请参阅 TImageList 组件和将 TImageLists 用作中央图像存储库的 FireMonkey 指南。

这些配对组件将图像集合(每个逻辑图像可以有多种分辨率)的概念与用于控件的单一特定尺寸的图像列表区分开来。简而言之,将多个分辨率的图像加载到一个图像集合中。图像列表包含一组来自图像集的图像,并以特定尺寸(如 16x16)显示。图像可平滑调整大小和缩放比例,图像列表的实际显示分辨率可根据 DPI 变化。它与传统的图像列表完全兼容,可以直接替代传统的图像列表,包括提供 HIMAGELIST 句柄,VCL 控件和任何使用 Windows API 图像列表调用的代码都可以使用它。

图像支持 alpha 通道,并可将 PNG 载入图像集。您还可以加载旧式的彩色抠像透明位图。

二、使用图像收集组件TImageCollection

通过 TImageCollection,可以使用原生 TWICImage 类存储、缩放和绘制本地格式的图像。

集合中的每张图片都可以有多个不同尺寸的版本。该组件会选择最佳尺寸进行缩放,或者在可用尺寸等于所需尺寸时使用图像。它还可以创建带 alpha 通道的 32 位 TBitmap 缩放版本,该版本可直接添加到 TCustomImageList 中。

TImageCollection 继承自 TCustomImageCollection 类(Vcl.BaseImageCollection 单元),该类定义了集合的基本方法。

2.1 图像收集组件编辑器

要打开图像集合编辑器,请将 TImageCollection 放置在表单或数据模块上,然后双击表单中的组件或右键单击该组件并从上下文菜单中选择 "Show collection editor… "选项。也可以双击对象检查器中的 TImageCollection.Images 属性。当然也可以通过右键菜单"Load from existing TIamgeLists"从TImageList控件中导入。

在 "图像集合编辑器 "窗口中,您可以将图像添加到组件中,并将它们分门别类。

单击 "添加 "显示 "打开 "对话框,并浏览到存储图片的文件夹。您可以一次添加一张图片,也可以从文件夹中选择多张图片同时添加。图像收藏编辑器按字母顺序显示图像。

添加图像时,您可能需要添加同一图像的多种尺寸。例如,你可能会有一个像素调整后的 16x16 版本的图片,然后还有一个更大的图片,需要根据其他尺寸进行绘制和缩放。要做到这一点,可以给单个图像的多个版本设置相同的文件名,加上一个分隔符(如连字符),然后再加上一个表示像素大小的数字:例如,foo-16.png 和 foo-64.png。然后选中 "检查文件名中的大小 "复选框,并从下拉选项中将图像大小分隔符更改为图像用于分隔通用名称和图像大小的字符(在上一示例中为连字符"-")。这样就能自动识别出文件名相似但像素大小不同的同一图像的多个分辨率,并将它们作为单一图像的多个分辨率添加到收藏中。

图像尺寸分隔符(Image size separator)设置可控制如何解析以分隔常用名称和图像尺寸,并包含常用图标和图像尺寸文件名约定的选项。

注意:

        "图像收集编辑器 "要求在文件名的编号中使用分隔符,以便识别同一图像的不同尺寸。

分类目前仅用于组织。(在 VCL 控件中,图像仍然只能通过索引来引用)。

要按类别组织图像,请选择图像并单击 "Set Category"。

使用顶部的 "Delete"按钮从集合中删除特定图像,使用 "Clear"按钮删除集合中的所有图像。

请注意: 从集合中删除图像时,VirtualImageList 会按索引查找图像。

将图片添加到图片集中后,您可以选择任何可用的图片并执行以下操作: 

  • 修改图像Name
  • 为图片指定自定义Description
  • 指定索引值,以修改图片集中的图片顺序。
  • 为同一图像Add其他来源。
  • Delete图像的来源。
  • Replace替换图像的现有来源。

请注意

        重命名和替换图像时,请按照以下步骤操作: 

  • 更改index[name]并应用更改(VirtualImageList 使用集合中的名称[索引]按索引[名称]更新图像)。
  • 更改name[index]并应用更改(VirtualImageList 使用集合中的索引[名称]按名称[索引]更新图像)。
  • 用不同的名称保存图像(save as...)。

提示:您还可以单击并拖动图像到不同的位置来修改其索引值

2.2 将现有 TImageList 载入 TImageCollection

为了帮助将旧式图像列表转换到新系统,您可以将旧 TImageList 中的图像加载到 TImageCollection 中。当您在不同的 TImageList 中拥有同一图像的多个尺寸时,您可以同时加载这两种图像;图像会被合并,从而使图像集合包含同一图像的多个分辨率。

要将 TImageList 中的图片加载到 TImageCollection 中,需要将这两个组件置于同一窗体中。

请按照以下步骤将表单中现有 TImageList 中的图像加载到 TImageCollection 中: 

  • 右键单击表单中的 TImageCollection 组件,然后从上下文菜单中选择从现有 TImageList... 选项。
  • 选择要加载的 TImageList,并为图片指定一个类别。您可以选择多个 TImageList。这对于加载以前存储在多个图像列表中的同一图像的多个分辨率特别有用。

  • 单击 "Load in order "以按照图像列表的相同顺序加载图像。
  • 单击Load with merging合并加载可合并不同图像列表中的不同图像源。合并加载时,图像列表必须具有相同的图像文件数量和不同的图像大小。

  • 单击 View Collection...(查看收藏...)验证图像在 TImageCollection 中的导入情况,而无需关闭对话框。
  • 单击 OK 应用设置并关闭对话框。
  • 单击 "Apply"应用一组特定的更改并继续配置设置。
  • 单击"Cancel"关闭对话框,放弃对图像集的所有更改。

请注意

        从传统 TImageList 导入 TImageCollection 或 TVirtualImageList 后,如果发现图像无法正确呈现,例如出现白边或其他伪影,请检查 TImageList 的 ColorDepth 属性。有时,FMX TImageList 的 ColorDepth 属性会设置为 cd32Bit,而它所保存的图像实际上是 24 位或 16 位的。请确保 ImageList 的颜色深度设置为 cd32Bit,如果它保存的位图是真正的 32 位,包括 Alpha 通道。

三、使用Virtual ImageList 组件

TVirtualImageList 允许您生成一个图像列表,并同时对所有图像应用更改。

TVirtualImageList 使用 TCustomImageCollection (TImageCollection) 来生成内部图像的动态列表。

通过 TVirtualImageList,您可以设置自定义的宽度和高度属性,而且该组件会自动缩放所有图片。当 DPI 发生变化时,它会对图像进行缩放,以便在高 DPI 显示器上正常显示。

注意:

        TVirtualImageList 在缩放时会自动继承其所有者(TCustomForm 或 TCustomFrame)的 DPI。
由于 TVirtualImageList 继承自 TCustomImageList,因此 VCL 控件无需修改即可使用 TVirtualImageList。

注意:

        要在 TVirtualImageList 中添加、插入和/或替换位图,必须使用从 ImageCollection 中添加、插入和/或替换项的方法。

3.1 Virtual ImageList Component 编辑器

要使用Virtual ImageList 组件和组件编辑器,首先需要在对象属性中设置 ImageCollection 属性。

 

要打开VirtualImageList虚拟图像列表编辑器,可双击表单中的组件,或右击该组件并从上下文菜单中选择 "Show image list editor… "选项。

如果将AutoFill(自动填充)属性设置为 True,虚拟图像列表将自动填充集合中的所有图像。否则,您可以使用图像列表编辑器将图像从集合中手动添加到列表中。

 VirtualImageList虚拟图像列表编辑器窗口允许您将图像添加到组件中,包括图像的禁用版本,并将它们分门别类。

单击Add打开相关的图像集,并选择要包含在虚拟图像列表中的图像。您可以从图像集中选择特定图像,也可以从图像集中或现有类别中选择所有图像。

此外,虚拟图像列表编辑器窗口还有以下选项: 

  • Add Disabled: 允许您创建并添加所选图像的低不透明度或灰度版本。禁用图像的外观由图像列表的 DisabledGrayscale 和 DisabledOpacity 属性控制。
  • Add with Disabled Copy: 允许您从相关图像集中添加图像,并同时创建和添加所选图像的禁用版本。
  • Replace: 允许您替换选定的图像。

注意

        只能用图像收藏组件中的图像替换虚拟图像列表组件中的图像,且该图像不在之前添加的图像列表中。

  • Set Category: 允许您将图像分门别类。要创建一个类别,请选择要包含在类别中的图像并单击 "设置类别...",输入类别名称,然后单击 "确定 "将其显示在类别列表中。组件编辑器会将类别名称添加到图像名称中。
  • Make All Disabled: 将之前添加的图像转换为禁用图像。

 

将图像添加到虚拟图像列表组件后,可以执行以下操作: 

  • Reload: 从 ImageCollection 重新载入图像名称和描述。
  • Delete: 从虚拟图像列表组件中删除所选图像。
  • Clear:  删除集合中的所有图像。
  • Name:  修改图像名称。
  • Description:  为图像指定自定义描述。

四、多分辨率下使用图像组件 TVirtualImage

TVirtualImage 组件支持类似 TImage 组件的多种分辨率。图像源来自图像集合(ImageCollection),根据屏幕 DPI 的不同,可以有多种分辨率。该组件会根据显示的显示器使用适当的版本。

VirtualImage 组件的一些配置设置和关键属性如下: ImageCollection、ImageHeight、ImageIndex、ImageName 和 ImageWidth。

 当您使用位图缩放逻辑来平滑绘制任何 VCL TGraphic 时(例如 StretchDraw),有一个 TScaledGraphicDrawer 类可以为不同的 TGraphic 类启用 HQ 缩放绘图,调用方式如下: 

MyBitmap.EnableScaler(TD2DGraphicScaler);
Image1.Picture.Graphic.EnableScaler(TWICGraphicScaler);

不同的解决方案可提供更好或更差的渲染效果以及更慢或更快的性能组合。您可以编写自定义的 TScaledGraphicDrawer 派生类,定义额外的缩放算法。

五、最佳实践

TVirtualImageList 组件会根据其所在表单的 DPI 缩放。这样,该窗体上与图像列表一起绘制的控件就能始终以正确的缩放分辨率绘制。不过,这意味着两件事: 

  • 控件应始终引用同一表单上的图像列表。如果控件引用了不同窗体上的图像列表,那么当两个窗体的 DPI 不同(如在不同的屏幕上)时,图像可能会绘制错误。
  • TVirtualImageList 应始终放在表单上,而不是数据模块上。表单有相关的显示器和 DPI,而数据模块没有。TImageCollection 可以放在任何地方,因为它们只是源,不受 DPI 变化的影响:它们是源,而TVirtualImageList 虚拟图像列表是呈现。

因此,如果窗体上的控件使用图像列表,则应始终在该窗体上放置一个或多个TVirtualImageLists,并让控件仅引用这些本地的同一窗体图像列表。这些 TVirtualImageLists 可以全部引用同一个 TImageCollection。

虚拟图像集合是一个非常有用的控件,它将图像集合(TImageCollection)的概念与特定尺寸(尽管可随 DPI 缩放)的图像集(TVirtualImageList)区分开来。图像集合不受 DPI 变化的影响,因为它只是一个容器。TVirtualImageList 虚拟图像列表可以引用另一个表单或数据模块上TImageCollection图像集合中的图像。好的设计是在应用程序的主表单或共享数据模块上为相关图像(如所有工具栏和菜单图像)建立一个图像集合。其他表单将拥有各自的虚拟图像列表,这些图像列表使用中央图像集。

5.1 多种尺寸(Multiple sizes)

        如果您需要同一图像的多种尺寸,例如具有 SmallImages 和 LargeImages 属性的 TListView,请使用两个 TVirtualImageLists,就像使用传统的 TImageLists 一样。两个虚拟图像列表都会引用同一个图像集合。

5.2 在应用程序中支持高 DPI 并转换旧版 TImageLists

将 VCL 应用程序从使用 TImageLists 转换为 TVirtualImageLists 是很常见的,这样可以提升视觉质量,并有助于支持高 DPI。

TVirtualImageList 是 TCustomImageList 的后代,因此在代码级别上可以直接替换,还提供了一个 HIMAGELIST Handle 属性,用于直接调用 Windows API 方法。

建议采用两种方法将应用程序转换为使用新的高 DPI 图像列表。

  1. 首先,您可能会同时升级图标,从旧式图标升级为更现代的图标,或从彩色透明图标升级为带有 alpha 通道的 32 位图像。如果这样做,您可能会发现最简单的方法就是将这些图标添加到新的图像集合中,创建新的图像列表,然后更改组件以指向新的图像列表。
  2. 其次,您可能希望逐步升级,逐步替换旧图像,甚至完全不替换(不过我们建议您利用新系统中的 32bpp alpha 通道支持)。为此,请放置一个 TImageCollection,然后右键单击并选择从现有 TImageList(s)加载。选择图像列表,然后选择添加图像或合并图像(如果它们包含多个分辨率的相同图像)。请参阅 TImageList 到 TImageCollection,将现有 TImageList 加载到 TImageCollection 以了解完整信息。

这将使您的图像集包含旧图像。虽然使用旧图片不会像使用新设计的图片那样提高图片质量或透明度,但这确实可以让图片根据每个表单的 DPI 进行缩放。在每个表单上创建新的 TVirtualImageList 组件,并从集合中添加图片:它们将保持相同的相对顺序,因此,除非集合中已有图片,否则索引也是相同的。然后,更改组件以使用新的 TVirtualImageLists。

5.3 在 TCanvas 上绘图时平滑缩放

TCanvas.StretchDraw 允许将 TGraphic 绘制到任意矩形上。虽然 TGraphic 子类的实现决定了如何做到这一点,但在实践中,VCL 绘图(如 TBitmap)通常通过 GDI 使用近邻重采样,通常无法获得理想的缩放或拉伸图像质量。

您可以使用 TImageCollection 来保存图像(内部存储为 WIC 并使用 WIC 绘制),并将其绘制为任意矩形。这样做将使用高质量的重采样。

显示图片请放弃TImage,请使用TImageCollection、TVirtualImageList、TVirtualImage

你将跟上4K的步骤!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/784854.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【数据结构】| 王道考研——树的前世今生

目录 一. 🦁 前言二. 🦁 各种树的知识点1. 树1.1 概念1.2 属性1.3 常考性质1.4 树转换成二叉树1.5 森林转换为二叉树1.6 二叉树转换为森林1.7 树的遍历1.8 森林的遍历 2. 二叉树2.1满二叉树2.2 完全二叉树2.3二叉排序树2.4 平衡二叉树2.5 二叉树常考性质…

IDEA使用lombok实体类加上@Data注解后无法找到get和set方法

文章目录 一、问题原因二、解决方法1.File→Settings2.Plugins→搜索"lombok"→Install3.Restart IDE(重启IDEA) 一、问题原因 IDEA没有安装lombok插件 二、解决方法 1.File→Settings 2.Plugins→搜索"lombok"→Install 3.Restart…

北斗定位导航系统,北斗模块应用领域发展概况_北斗二号模块,北斗三号模块

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 前言一、北斗系统概述1.1 空间段1.2 地面控制段1.3 用户段1.4 坐标系统1.5 时间系统 二、北斗系统定位导航授时服务2.1 服务概述2.2 服务区2.3 北斗信号频段2.4 北斗…

服务器中了Locked勒索病毒怎么解决,勒索病毒解密恢复方式与防护措施

服务器是企业重要数据存储和处理的关键设备,然而,众所周知,服务器系统并非完全免受网络攻击的。其中一种常见的威胁是勒索病毒,其中一种恶名昭彰的变种是Locked勒索病毒。Locked勒索病毒采用了对称AES与非对称RSA的加密形式&#…

【C++入门到精通】C++入门 —— 引用、内联函数

目录 一、引用 1.引用的概念 2.引用的特性 3.常引用 4.引用的使用场景 ⭕做参数 ⭕做返回值 5.传值、传引用效率比较 值和引用的作为返回值类型的性能比较 6.引用和指针的区别 引用和指针的不同点 二、内联函数 1.内联函数的概念 2.内联函数的特性 3.宏与内联函数 …

RocketMQ教程-(5)-功能特性-顺序消息

顺序消息为 Apache RocketMQ 中的高级特性消息,本文为您介绍顺序消息的应用场景、功能原理、使用限制、使用方法和使用建议。 应用场景​ 在有序事件处理、撮合交易、数据实时增量同步等场景下,异构系统间需要维持强一致的状态同步,上游的事…

13.4.2 【Linux】sudo

相对于 su 需要了解新切换的使用者密码 (常常是需要 root 的密码), sudo 的执行则仅需要自己的密码即可。sudo 可以让你以其他用户的身份执行指令 (通常是使用 root 的身份来执行指令),因此并非所有人都能够…

Spring 多数据源方法级别注解实现

Spring框架提供了多种数据源管理方式,其中多数据源管理是其中之一。多数据源管理允许应用程序使用多个数据源,而不是只使用一个数据源,从而提高了应用程序的灵活性和可靠性。 多数据源管理的主要目的是让应用程序能够在不同的数据库之间切换&…

SpringCache 框架使用以及序列化和缓存过期时间问题的解决

目录 为什么使用Spring Cache 如何使用Spring Cache 1 加依赖 2 开启缓存 3 加缓存注解 序列化以及过期时间等问题 解决方案:自定义序列化方式 1.自定义序列化方式并设置白名单 2.配置并设置缓存的过期时间 为什么使用Spring Cache 缓存有诸多的好处&#x…

YOLOv5(v7.0)网络修改实践二:把单分支head改为YOLOX的双分支解耦合head(DecoupleHead)

前面研究了一下YOLOX的网络结构,在YOLOv5(tag7.0)集成了yolox的骨干网络,现在继续下一步集成YOLOX的head模块。YOLOX的head模块是双分支解耦合网络,把目标置信度的预测和目标的位置预测分成两条支路,并验证双分支解耦合头性能要优…

为什么视频画质会变差,如何提升视频画质清晰度。

在数字时代,视频已经成为我们生活中不可或缺的一部分。然而,随着视频的传输和处理过程中的多次压缩,画质损失逐渐凸显,影响了我们对影像的真实感受。为了让视频画质更加清晰、逼真,我们需要采取一些措施来保护和修复视…

设计模式大白话——观察者模式

文章目录 一、概述二、示例三、模式定义四、其他 一、概述 ​ 与其叫他观察者模式,我更愿意叫他叫 订阅-发布模式 ,这种模式在我们生活中非常常见,比如:追番了某个电视剧,当电视剧有更新的时候会第一时间通知你。当你…

Zia和ChatGPT如何协同工作?

有没有集成ChatGPT的CRM系统推荐?Zoho CRM已经正式与ChatGPT集成。下面我们将从使用场景、使用价值和使用范围等方面切入讲述CRMAI的应用和作用。 Zia和ChatGPT如何协同工作? Zia和ChatGPT是不同的人工智能模型,在CRM中呈现出共生的关系。 …

荧光信号采集的2种方法

本文介绍荧光信号采集的2种方法。 荧光信号采集是生化类医疗设备(PCR,荧光免疫分析仪)常用的功能,针对不同类型的激发光和发射光采用的荧光信号采集方法也不一样。 1.基本概念 1)发光原理 当待测物质受到外接某一波长的入射光…

生物信息学_玉泉路_课堂笔记_02 第二章 序列比对和序列数据库搜索

🍅 课程:生物信息学_玉泉路_课堂笔记 中科院_2022秋季课 第一学期 🍅 个人笔记使用 🍅 2023/7/5 一、上周回顾 二、生物信息学的展望 —— 精准医学的发展 生物信息学的开拓者 三、双序列比对的常用算法 序列比对的需求 使用 b…

基于包围框回归的目标检测网络原理及Tensorflow实现

对象检测是对图像内的对象进行分类和定位。 换句话说,它是图像分类和对象定位的结合。 构建用于图像分类的机器学习模型更简单,我在我的一篇文章中对此进行了描述。 然而,图像分类器无法准确判断对象在图像内的位置。 为了实现这一目标&#…

opencv对相机进行畸变矫正,及从矫正后的图像坐标反求原来的对应坐标

1.背景 目前有个项目,需要用到热成像相机。但是这个热成像相机它的畸变比较厉害,因此需要用标定板进行标定,从而消除镜头畸变。 同时需要实现用户用鼠标点击矫正后的画面后,显示用户点击位置的像素所代表的温度。 2.难点 消除镜…

1-1 AUTOSAR是什么?

目录 一、AUTOSAR组织 二、AUTOSAR的版本 三、AUTOSAR的理念 四、AUTOSAR的动机 五、AUTOSAR目标 六、AUTOSAR的优势 6.1 商业优势 6.2 技术优势 一、AUTOSAR组织 AUTOSAR(Automotive Open System Architecture)是一个全球性的汽车行业标准化组织…

【流形和流形空间(姿态)】

定义 流形(Manifold)是一种广义的曲面概念,用于描述局部上类似于欧几里德空间的空间。简而言之,流形是一个局部与欧几里德空间同胚(homeomorphic)的空间,但并不一定是全局上同胚的。&#xff0…

Springboot项目打包war配置详解

Springboot项目打包war配置详解 1. 排除内置tomcat依赖2. 添加servlet依赖3. 修改打包方式4. 修改主启动类5. 完整pom.xml6. 效果图 1. 排除内置tomcat依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter…