在Delphi中,当控件的父控件接收并失去焦点时,如何通知控件?
正如标题所说,我希望组件(例如,在Delphi中,当控件的父控件接收并失去焦点时,如何通知控件?,delphi,components,vcl,Delphi,Components,Vcl,正如标题所说,我希望组件(例如,标签)在其父组件(例如,面板)接收并失去焦点时得到通知。我在Delphi源代码中漫游了一下,希望使用TControl.Notify,但它只用于通知子控件一些属性更改,如字体和颜色。有什么建议吗?每当应用程序中的活动控件发生更改时,会向所有控件广播一条CM\u FOCUSCHANGED消息。简单地拦截它,并相应地采取行动 另外,我假设当其父控件(比如面板)接收并失去焦点时,您的意思是当其父控件/面板上的(嵌套)子控件接收或失去焦点时 type TLabel =
标签
)在其父组件(例如,面板
)接收并失去焦点时得到通知。我在Delphi源代码中漫游了一下,希望使用TControl.Notify
,但它只用于通知子控件一些属性更改,如字体和颜色。有什么建议吗?每当应用程序中的活动控件发生更改时,会向所有控件广播一条CM\u FOCUSCHANGED
消息。简单地拦截它,并相应地采取行动
另外,我假设当其父控件(比如面板)接收并失去焦点时,您的意思是当其父控件/面板上的(嵌套)子控件接收或失去焦点时
type
TLabel = class(StdCtrls.TLabel)
private
function HasCommonParent(AControl: TWinControl): Boolean;
procedure CMFocusChanged(var Message: TCMFocusChanged);
message CM_FOCUSCHANGED;
end;
procedure TLabel.CMFocusChanged(var Message: TCMFocusChanged);
const
FontStyles: array[Boolean] of TFontStyles = ([], [fsBold]);
begin
inherited;
Font.Style := FontStyles[HasCommonParent(Message.Sender)];
end;
function TLabel.HasCommonParent(AControl: TWinControl): Boolean;
begin
Result := False;
while AControl <> nil do
begin
if AControl = Parent then
begin
Result := True;
Break;
end;
AControl := AControl.Parent;
end;
end;
请注意,我选择了
TLabel
来演示此功能也适用于TControl
衍生产品。这是用于您自己的控件(标签)吗?在表单上,您可以简单地为父级(面板)编写OneNet和OnExit事件处理程序。面板是否实际接收焦点?为所有面板分配一组OneNet和OnExit事件处理程序。在处理程序内部,您可以通过发送方的子控件循环查找JvGradientHeader对象,然后根据需要进行更新。另一个选项是对每个面板进行子类化,以捕获CM_FOCUSCHANGED消息,然后向发送方的子控件广播自定义定义的CM_PARENTFOCUSCHANGED消息。然后,您可以对JvGradientHeader控件进行子类化以捕获该消息。这听起来是创建从TPanel继承并拥有JvGradientHeader的复合控件的好时机。然后可以覆盖Tpanel控件的exit和enter虚拟方法。面向对象编程是你的朋友。我学到了一些好东西。我一直认为只有表单才能有消息处理程序。非常感谢:-)
TForm1 = class(TForm)
procedure FormCreate(Sender: TObject);
procedure FormDestroy(Sender: TObject);
private
FHeaders: TList;
procedure ActiveControlChanged(Sender: TObject);
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
FHeaders := TList.Create;
FHeaders.Add(Label1);
FHeaders.Add(Label2);
Screen.OnActiveControlChange := ActiveControlChanged;
end;
procedure TForm1.FormDestroy(Sender: TObject);
begin
FHeaders.Free;
end;
function HasCommonParent(AControl: TWinControl; AMatch: TControl): Boolean;
begin
Result := False;
while AControl <> nil do
begin
if AControl = AMatch.Parent then
begin
Result := True;
Break;
end;
AControl := AControl.Parent;
end;
end;
procedure TForm1.ActiveControlChanged(Sender: TObject);
const
FontStyles: array[Boolean] of TFontStyles = ([], [fsBold]);
var
I: Integer;
begin
for I := 0 to FHeaders.Count - 1 do
TLabel(FHeaders[I]).Font.Style :=
FontStyles[HasCommonParent(Screen.ActiveControl, TLabel(FHeaders[I]))];
end;