How to show hint using Application.ActivateHint on Delphi?

只愿长相守 提交于 2020-01-04 05:57:08

问题


I have the following code trying to show a hint:

procedure TMyGrid.OnGridMouseMove(Sender: TObject; Shift: TShiftState;
  X, Y: Integer);
var
  aPoint: TPoint;
begin
  inherited;
  //Application.Hint := 'Hint Text';
  //Application.ShowHint := True;
  Grid.Hint := 'Hint Text';
  Grid.ShowHint := True;
  aPoint.X := X;
  aPoint.Y := Y;
  Application.ActivateHint(aPoint);
end;

But there is no hint appears. What's wrong?


回答1:


ActivateHint wants your point in screen coordinates, not in client coordinates.

From doc:

ActivateHint locates the control or menu item at the position specified by CursorPos, where CursorPos represents a screen coordinates in pixels. After locating the control, ActivateHint displays the control's Hint in a hint window.

So, you have to change your method like this:

procedure TMyGrid.OnGridMouseMove(Sender: TObject; Shift: TShiftState;
  X, Y: Integer);
var
  aPoint: TPoint;
begin
  inherited;
  //Application.Hint := 'Hint Text';
  Grid.Hint := 'Hint Text';
  Grid.ShowHint := True;
  aPoint.X := X;
  aPoint.Y := Y;
  aPoint := ClientToScreen(aPoint);
  Application.ActivateHint(aPoint);
end;



回答2:


Rather than trying to force TApplication to display a new Hint in your grid control's OnMouseMove event, the correct approach is to instead have your grid process the CM_HINTSHOW message to customize the current Hint whenever it is shown normally.

The CM_HINTSHOW message provides you with a pointer to a THintInfo record in its LPARAM value. THintInfo has a CursorPos member that tells you the current mouse position within the control's client area, and a CursorRect member that allows you to define a rectangle within the control's client area that the current hint should be valid for (THintInfo has other members for customizing the hint further, suh as text, color, window class, show/hide timeouts, etc). When the mouse moves outside of that rectangle but is still within the control's client area, the CM_HINTSHOW message is generated again to obtain new information to update the current Hint with.

If you need to update the hint on every mouse move, you can define a custom CursorRect that only contains the current CursorPos, for example:

type
  TMyGrid = class(...)
  private
    procedure CMHintShow(var Message: TCMHintShow); message CM_HINTSHOW;
  end;

procedure TMyGrid.CMHintShow(var Message: TCMHintShow);
begin
  with Message.HintInfo^ do
  begin
    HintStr := Format('Hint Text (%d,%d)', [CursorPos.X, CursorPos.Y]);
    CursorRect := Rect(CursorPos.X, CursorPos.Y, CursorPos.X, CursorPos.Y);
  end;
end;


来源:https://stackoverflow.com/questions/15030998/how-to-show-hint-using-application-activatehint-on-delphi

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!