开发者

Why does a simulated mouse click (using mouse_event) work on selected components only?

I have multiple cursors (which are actually forms) that can be controlled by their respective mouse. (1 cursor for 1 user).

I use SetCursorPos to position the default cursor (the original system cursor) in a position that will not take away the focus from my application, and use ShowCursor(false) to hide it.

I have a class that gets the handle of the mouse and the coordinates.

When the user clicks I use the SetCursorPos and the mouse_event to simulate the clicks in that particular position.

My simulated mouse clicks only work on certain components' OnClick event (It was supposed to be only buttons and labels, but I experimented with the stuff on my project just to know what will or won't work):

It works on:

  • Buttons (TButton, TBitBtn, TAdvSmoothButton)
  • T开发者_Python百科AdvGrid
  • TMenuItem (but the direct child of the TMainMenu only)
  • TRadioButton

It doesn't work on:

  • TLabel
  • Panels (TPanel, TAdvSmoothPanel)
  • TCoolBar
  • TMenuItem (not direct child of TMainMenu)

This is my code:

 SetCursorPos(currentX , currentY);
 mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0);
 mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);

Why doesn't it work on some components? Is there a workaround (because I would like to be able to click labels using mouse_event).

EDIT: I tried checking if the clicking function was really called, so I put ShowMessage('clicked'); before the SetCursorPos and mouse_event...but strangely everything (minor edit: everything except MenuItems) works fine now (except for the fact that I have a Message popping out everytime I try to click something). Does anybody have an idea why this behaves that way?


mouse_event is actually deprecated, you should use SendInput instead, see if that fixes anything (I would also suggest making the mouse move an input message, over using SetCursorPos), also, if your doing this for a specific application, PostMessage might be a much better and simpler alternative


Seems to work here;

procedure TForm1.Panel1Click(Sender: TObject);
begin
  ShowMessage('Click');
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  Pt: TPoint;
begin
  Pt := Panel1.ClientToScreen(Point(0, 0));
  SetCursorPos(Pt.x, Pt.y);
//  SetCursorPos(Panel1.ClientOrigin.x, Panel1.ClientOrigin.y);
  mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0);
  mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
end;

or, without SetCursorPos;

procedure TForm1.Button1Click(Sender: TObject);
var
  Pt: TPoint;
begin
  Pt := Panel1.ClientToScreen(Point(0, 0));
  Pt.x := Round(((Pt.x + 1) * 65535) / Screen.Width);
  Pt.y := Round(((Pt.y + 1) * 65535) / Screen.Height);
  mouse_event(MOUSEEVENTF_ABSOLUTE or MOUSEEVENTF_MOVE or MOUSEEVENTF_LEFTDOWN,
      Pt.x, Pt.y, 0, 0);
  mouse_event(MOUSEEVENTF_ABSOLUTE or MOUSEEVENTF_MOVE or MOUSEEVENTF_LEFTUP,
      Pt.x, Pt.y, 0, 0);
end;


It works by accident right now, those components have probably captured the mouse. You need to pass the mouse pointer coordinates in the 2nd and 3rd arguments. Thus:

 //SetCursorPos(currentX , currentY);
 mouse_event(MOUSEEVENTF_LEFTDOWN, currentX, currentY, 0, 0);
 mouse_event(MOUSEEVENTF_LEFTUP, currentX, currentY, 0, 0);
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜