加入收藏 | 设为首页 | 会员中心 | 我要投稿 源码网 (https://www.900php.com/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 服务器 > 系统 > 正文

windows – 除了ICON_BIG之外,如何让Delphi 10.2 Tokyo尊重ICON_

发布时间:2021-03-10 00:03:45 所属栏目:系统 来源:网络整理
导读:副标题#e# 如何在Delphi 10.2中实现以下目标:我需要Delphi自动设置大图标,而不是每个窗口的大小图标.我需要有机会,对于某些表单,以及TApplication,在运行时更改图标.我希望在不修改VCL.Forms.pas的情况下完成此操作(小图标是在窗口标题栏中显示的图标,从窗

procedure TBaseForm.CreateWnd;
var
  Big,Small: HICON;
begin
  inherited;
  if BorderStyle <> bsDialog then
  begin
    GetIconHandles(Big,Small);
    if Big <> 0 then
      SendMessage(Handle,LParam(Big));
    if Small <> 0 then
      SendMessage(Handle,LParam(Small));
  end;
end;

介绍两种虚拟方法:

procedure TBaseForm.GetIconResName(var Name: string);
begin
  Name := 'MAINICON';
end;

procedure TBaseForm.GetIconHandles(var Big,Small: HICON);
var
  ResName: string;
begin
  Big := 0;
  Small := 0;
  GetIconResName(ResName);
  if ResName = '' then Exit;

  Big := LoadImage(HInstance,PChar(ResName),GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),0);
  Small := LoadImage(HInstance,GetSystemMetrics(SM_CXSMICON),GetSystemMetrics(SM_CYSMICON),0);
end;

您在子类中所需要做的就是覆盖GetIconResName.

即:

TMyChildForm = class(TBaseForm)
protected 
  procedure GetIconResName(var Name: string); override;
end;

procedure TMyChildForm.GetIconResName(var Name: string);
begin
  Name := 'SPIDERMAN';
end;

This is not a complete solution…

我试图给你一些线索,以显示修补VCL源是不需要的.

在任何情况下,如果我使用Icon属性(包括应用程序和表单)并提供至少2个大小(16×16和32×32)32位深度的图标(如果需要使用其他格式),我没有任何问题,Windows将显示正确的图标.即系统在ALT TAB对话框中显示大图标,在窗口标题中显示小图标.即使只将ICON_BIG发送到表单/应用程序窗口句柄. (Delphi7的/ Win7的). (这就是我要求MCVE的原因.包括有关你的图标格式的信息.而不仅仅是你所做的代码碎片……)

由于我对您的确切要求感到困惑,并且您仍然拒绝提供MCVE,我将尝试提供另一种方法:

你说你还需要处理应用程序图标.创建应用程序时,应用程序图标会尽早设置 – 在表单中处理起来并不简单,因为它们尚未创建.但是每当Application.Icon被更改时,应用程序都会通过CM_ICONCHANGED通知表单(参见:procedure TApplication.IconChanged(Sender:TObject);).所以你可以通过SendMessage(Application.Handle,WM_SETICON ……(这不会触发CM_ICONCHANGED)或直接设置Application.Icon(也会触发CM_ICONCHANGED)重新设置该消息处理程序中的Application图标.通过WM_SETICON消息设置大小图标.您还需要设置类图标:

SetClassLong(Application.Handle,GCL_HICON,FIcon);

因此,无论何时更改应用程序图标,都会在表单中由CM_ICONCHANGED覆盖.

TBaseForm = class(TForm)
private
  procedure CMIconChanged(var Message: TMessage); message CM_ICONCHANGED;
...
procedure TBaseForm.CMIconChanged(var Message: TMessage);
...

如果您需要在应用程序的早期设置该图标(我认为不需要),请仅在主窗体创建中执行上述操作.

要捕获/处理表单图标,请使用表单中的WM_SETICON消息处理程序:

TBaseForm = class(TForm)
private
  procedure WMSetIcon(var Message: TWMSetIcon); message WM_SETICON;
...

procedure TBaseForm.WMSetIcon(var Message: TWMSetIcon);
begin
  if (Message.Icon <> 0) and (BorderStyle <> bsDialog) then
  begin    
    // this big icon is being set by the framework
    if Message.BigIcon then
    begin      
      // FBigIcon := LoadImage/LoadIcon...
      // if needed set Message.Icon to return a different big icon
      // Message.Icon := FBigIcon;
      // in practice create a virtual method to handle this section so your child forms can override it if needed
      inherited;

      FSmallIcon := LoadImage/LoadIcon...    
      // set small icon - this will also re-trigger WMSetIcon
      Perform(WM_SETICON,FSmallIcon);
    end else
      inherited;
  end
  else
    inherited;
end;

这应该可以让你了解所有情况.

(编辑:源码网)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

热点阅读