4

我试图在组件内部的运行时临时更改提示文本,而不更改Hint属性本身。

我试过 catch CM_SHOWHINT,但这个事件似乎只是形成,而不是组件本身。

插入 CustomHint 也不起作用,因为它从Hint属性中获取文本。

我的组件是从TCustomPanel

这是我正在尝试做的事情:

procedure TImageBtn.WndProc(var Message: TMessage);
begin
  if (Message.Msg = CM_HINTSHOW) then
    PHintInfo(Message.LParam)^.HintStr := 'CustomHint';
end;

我在互联网的某个地方找到了这段代码,不幸的是它不起作用。

4

2 回答 2

11

CM_HINTSHOW确实正是您所需要的。这是一个简单的例子:

type
  TButton = class(Vcl.StdCtrls.TButton)
  protected
    procedure CMHintShow(var Message: TCMHintShow); message CM_HINTSHOW;
  end;

  TMyForm = class(TForm)
    Button1: TButton;
  end;

....

procedure TButton.CMHintShow(var Message: TCMHintShow);
begin
  inherited;
  if Message.HintInfo.HintControl=Self then
    Message.HintInfo.HintStr := 'my custom hint';
end;

问题中的代码无法调用inherited,这可能是它失败的原因。或者也许类声明省略了overrideon 指令WndProc。无论如何,我在这个答案中的方式更干净。

于 2012-10-11T11:31:31.653 回答
6

您可以使用 OnShowHint 事件

它有 HintInfo 参数:http ://docwiki.embarcadero.com/Libraries/XE3/en/Vcl.Forms.THintInfo

该参数允许您查询提示控件、提示文本和所有上下文 - 并在需要时覆盖它们。

如果您想过滤哪些组件来更改提示,例如,可以声明某种 ITemporaryHint 接口,例如

type 
  ITemporaryHint = interface 
  ['{1234xxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}']
    function NeedCustomHint: Boolean;
    function HintText: string;
  end;

然后您可以稍后一般检查您的任何组件,它们是否实现了该接口

procedure TForm1.DoShowHint(var HintStr: string; var CanShow: Boolean;
  var HintInfo: THintInfo);
var
  ih: ITemporaryHint;
begin
  if Supports(HintInfo.HintControl, {GUID for ITemporaryHint}, ih) then
    if ih.NeedCustomHint then
      HintInfo.HintStr := ih.HintText;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Application.ShowHint := True;
  Application.OnShowHint := DoShowHint;
end;  
于 2012-10-11T11:45:03.420 回答