C# 在用户单击鼠标按钮后发布消息
我使用SetWindowsHookEx监视另一个应用程序。当用户在程序中单击鼠标时,我使用PostMessage向程序发送消息 我遇到的问题是,有时我的信息在WM_LBUTTONUP之前到达。如何确保我的信息在WM_LBUTTONUP之后到达 我使用以下代码来监视和发送消息:C# 在用户单击鼠标按钮后发布消息,c#,c++,api,winapi,C#,C++,Api,Winapi,我使用SetWindowsHookEx监视另一个应用程序。当用户在程序中单击鼠标时,我使用PostMessage向程序发送消息 我遇到的问题是,有时我的信息在WM_LBUTTONUP之前到达。如何确保我的信息在WM_LBUTTONUP之后到达 我使用以下代码来监视和发送消息: HookManager.MouseUp += HookManagerMouseUp; void HookManagerMouseUp(object sender, MouseEventArgs e) { uint
HookManager.MouseUp += HookManagerMouseUp;
void HookManagerMouseUp(object sender, MouseEventArgs e)
{
uint ret;
uint attachedThredId = GetCurrentThreadId();
uint attachedProcessId = GetWindowThreadProcessId(ActiveWindow, out ret);
AttachThreadInputSafe(attachedThredId, attachedProcessId, true);
PostMessage(ActiveControlInWindow, Message.KeyDown, 'A', 0x1);
PostMessage(ActiveControlInWindow, Message.KeyUp, 'A', 0xC0010001);
AttachThreadInputSafe(attachedThredId, attachedProcessId, false);
}
我使用PostMessage发送击键是因为我想这样做,即使主机应用程序未处于活动状态
Gma.UserActivityMonitor中的钩子如下所示:
s_MouseDelegate = MouseHookProc;
s_MouseHookHandle = SetWindowsHookEx(
WH_MOUSE_LL,
s_MouseDelegate,
Marshal.GetHINSTANCE(
Assembly.GetExecutingAssembly().GetModules()[0]),
0);
我使用Spy++监视到达应用程序的消息。当消息以正确的顺序到达时,我得到以下结果:
S WM_MOUSEACTIVATE hwndTopLevel:00030A46 nHittest:HTCLIENT uMsg:WM_LBUTTONDOWN
R WM_MOUSEACTIVATE fuActivate:MA_ACTIVATE
S WM_KILLFOCUS hwndGetFocus:00020A32
R WM_KILLFOCUS
S WM_IME_SETCONTEXT fSet:1 iShow:C000000F
R WM_IME_SETCONTEXT
S WM_SETFOCUS hwndLoseFocus:00030A46
R WM_SETFOCUS
P WM_LBUTTONDOWN fwKeys:MK_LBUTTON xPos:278 yPos:73
S WM_ERASEBKGND hdc:0E010DEE
R WM_ERASEBKGND fErased:True
P WM_LBUTTONUP fwKeys:0000 xPos:278 yPos:73
S WM_CAPTURECHANGED hwndNewCapture:00000000
R WM_CAPTURECHANGED
P WM_KEYDOWN nVirtKey:VK_OEM_5 cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:VK_OEM_5 cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_CHAR chCharCode:'167' (167) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYDOWN nVirtKey:'2' cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:'2' cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_KEYDOWN nVirtKey:'2' cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:'2' cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_CHAR chCharCode:'50' (50) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_CHAR chCharCode:'50' (50) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
S WM_KILLFOCUS hwndGetFocus:(null)
R WM_KILLFOCUS
S WM_IME_SETCONTEXT fSet:0 iShow:C000000F
R WM_IME_SETCONTEXT
当消息以错误的顺序到达时,我得到以下结果(请注意,WM_LBUTTONUP在处理完WM_CHAR后到达):
我能看到的是,当其中一个发生时,它是随机的。如果我在发布消息之前加上延迟,它就会起作用。但是我不想使用延迟。使用鼠标挂钩,在收到
WM*BUTTONUP
时发布消息
您看到这种行为的原因有很多(其他钩子、系统模态循环),但最明显的一个原因是,在WM_nBUTTONUP消息发布到线程之前,钩子会收到通知
获得所需行为的唯一可靠方法是使用全局钩子,以便在获取消息的进程中执行。您可能需要使用WH_CALLWNDPROCRET hook,以便在处理消息后调用您的hook。为什么不在此处发布相关代码,以便我们了解您是如何操作的?@Nawaz我添加了简化的代码,说明了我正在尝试做的事情和我所做的事情,但它只是有时起作用,不幸的是,你有比“有时”更好的标准吗?(例如,窗口需要处于活动状态,…)是否执行PostMessage?这些方法有失败的吗?用什么密码?ActiveControlInWindow是正确的窗口句柄吗?我能看到的是,当一个或另一个出现时,它是随机的。我已经编辑了这个问题,用spy++显示了结果。并且KEYUP和KEYDOWN会根据您的需要到达应用程序。所以这不可能有任何错误。
S WM_MOUSEACTIVATE hwndTopLevel:00030A46 nHittest:HTCLIENT uMsg:WM_LBUTTONDOWN
R WM_MOUSEACTIVATE fuActivate:MA_ACTIVATE
S WM_KILLFOCUS hwndGetFocus:00020A32
R WM_KILLFOCUS
S WM_IME_SETCONTEXT fSet:1 iShow:C000000F
R WM_IME_SETCONTEXT
S WM_SETFOCUS hwndLoseFocus:00030A46
R WM_SETFOCUS
P WM_LBUTTONDOWN fwKeys:MK_LBUTTON xPos:329 yPos:166
S WM_ERASEBKGND hdc:1E0117FD
R WM_ERASEBKGND fErased:True
P WM_KEYDOWN nVirtKey:VK_OEM_5 cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:VK_OEM_5 cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_KEYDOWN nVirtKey:'2' cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:'2' cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_KEYDOWN nVirtKey:'2' cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_KEYUP nVirtKey:'2' cRepeat:1 ScanCode:01 fExtended:0 fAltDown:0 fRepeat:1 fUp:1
P WM_CHAR chCharCode:'167' (167) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_CHAR chCharCode:'50' (50) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_CHAR chCharCode:'50' (50) cRepeat:1 ScanCode:00 fExtended:0 fAltDown:0 fRepeat:0 fUp:0
P WM_LBUTTONUP fwKeys:0000 xPos:329 yPos:166
S WM_CAPTURECHANGED hwndNewCapture:00000000
R WM_CAPTURECHANGED
S WM_KILLFOCUS hwndGetFocus:(null)
R WM_KILLFOCUS
S WM_IME_SETCONTEXT fSet:0 iShow:C000000F
R WM_IME_SETCONTEXT