Delphi t重新查看所选项目的自定义绘图

Delphi t重新查看所选项目的自定义绘图,delphi,windows-8,treeview,delphi-xe,Delphi,Windows 8,Treeview,Delphi Xe,我正在尝试为我的应用程序模拟Outlook 2013左窗格树视图菜单。我使用CustomDraw是因为我只想更改一些简单的字体和背景属性 以下是我想要的: 但是,我始终为选定节点和热跟踪节点获取默认的选定图形。我没有Windows 7或XP来查看这是否是正常行为,或者这是否与我的操作系统(Windows 8)有关 以下是我得到的: 这是我的密码: procedure TMainForm.TreeView1CustomDrawItem(Sender: TCustomTreeView; No

我正在尝试为我的应用程序模拟Outlook 2013左窗格树视图菜单。我使用CustomDraw是因为我只想更改一些简单的字体和背景属性

以下是我想要的:

但是,我始终为选定节点和热跟踪节点获取默认的选定图形。我没有Windows 7或XP来查看这是否是正常行为,或者这是否与我的操作系统(Windows 8)有关

以下是我得到的:

这是我的密码:

procedure TMainForm.TreeView1CustomDrawItem(Sender: TCustomTreeView;
  Node: TTreeNode; State: TCustomDrawState; var DefaultDraw: Boolean);
begin
  if Node.Level = 1 then
    Sender.Canvas.Font.Size := Sender.Canvas.Font.Size + 2;

  if cdsHot in State then
    Sender.Canvas.Brush.Color := $00F7E6CD
  else if (cdsSelected in State) or (cdsFocused in State) or
    (cdsChecked in State) then
    Sender.Canvas.Brush.Color := $00F2F2F2
  else
    Sender.Canvas.Brush.Color := $00DEDEDE;
  DefaultDraw := true;
end;
如何为选定项目和热门项目绘制不同颜色的背景?

请尝试以下操作:

type
  TTreeView = class(Vcl.ComCtrls.TTreeView)
  protected
    procedure CreateWnd; override;
  end;


uses uxtheme;

procedure TTreeView.CreateWnd;
begin
  inherited;
  SetWindowTheme(Handle, nil , nil);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin

   TreeView1.Font.Name := 'Segoe UI';
   TreeView1.HotTrack := True;
   TreeView1.Font.Size := TreeView1.Font.Size + 1;
   TreeView1.Color := $00DEDEDE;

end;

procedure TForm1.TreeView1CustomDrawItem(Sender: TCustomTreeView;
  Node: TTreeNode; State: TCustomDrawState; var DefaultDraw: Boolean);
begin

   if cdsFocused in State then begin
     Sender.Canvas.Brush.Color := $00F2F2F2;
     Sender.Canvas.Font.Color := clblack;
     Sender.Canvas.Font.Style := Sender.Canvas.Font.Style + [fsBold];
   end else if cdsHot in State then
    Sender.Canvas.Brush.Color := $00F7E6CD
   else
    Sender.Canvas.Brush.Color := $00DEDEDE;

end;


说明:

微软在这方面的文档非常模糊,我可以肯定地说,每当对一个项目(节点)执行一个操作(选择、热跟踪、取消选择等),就会发送一条特定的消息,此消息通过parameters标志包含节点的状态,parameters标志在最后内部决定如何根据当前Windows主题可视化地更新项目


这就是为什么禁用TreeView组件的主题会删除默认选择矩形和主题着色的可能原因。的文档部分支持这一理论。

我认为必须取消控件主题才能使其工作。禁用应用程序的运行时主题,或者至少在treeview上使用空字符串调用
SetWindowTheme
。也许您可以从VirtualStringTree开始?实际上,我认为我不正确。文档特别提到工具栏,您必须通过调用SetWindowTheme禁用视觉样式,但没有提到任何其他控件@SertacAkyuz,你应该发布一个答案,因为你基本上在评论中解决了它,甚至没有看到它,删除了我的答案。@Peter-没问题,我不发布答案,请恢复你的答案。事实上,如果有人不提出解释,我会投你的票。如果MS的文档不完整或是类似的话,我不会感到惊讶。有没有解释为什么你必须在控件上禁用主题化以使其着色?因为通过主题化,所选项目基本上被屏蔽了。他的颜色确实会被画出来,但是在实际的主题选择区域下。这是不正确的,但这也不是我想问的。不正确,因为这些颜色随NMTVCUSTOMDRAW结构的clrText和clrTextBk成员返回,系统在绘制时将使用这些颜色。该系统要么使用这些颜色,要么不使用,没有绘画结束。但无论如何,我想问的是,你有没有任何MS参考来禁用控件上的主题?否则,您观察到的行为也是我观察到的行为。+1因为我同意主题化将覆盖自定义图形。不过我更喜欢代码的答案。。在重新创建窗口的情况下,需要在CreateWnd中调用SetWindowTheme。