获取光标位置和 hwnd 的低级鼠标钩子
Low level mouse hook getting cursor position and hwnd
我有一个简短的问题。我从 MSDN 创建了一个标准 window 和 window api,创建了一个 window 站点。我想让程序做的是更改 window 当我按下键盘上的某个键时鼠标光标所在的标题。为此,我安装了一个低级鼠标挂钩,如下所示:
LRESULT CALLBACK LowLevelMouseProc(__in int nCode, __in WPARAM wParam, __in LPARAM lParam) {
MSLLHOOKSTRUCT* p = (MSLLHOOKSTRUCT*)lParam;
HWND hiWnd = WindowFromPoint(p->pt); //Get a handle to the top-most window
ScreenToClient(hiWnd, &p->pt); //Converts the cursor position from screen to the specified window
char buf[33];
switch (wParam) {
case WM_MOUSEMOVE:
snprintf(buf, sizeof(buf) - 1, "X:%ld, Y:%ld", p->pt.x, p->pt.y); //Put the cursor coordinates into a char buffer
SendMessage(hiWnd, WM_SETTEXT, 0, (LPARAM)buf); //Send a message to the other window to change the title
break;
}
return CallNextHookEx(0, nCode, wParam, lParam);
}
调用鼠标挂钩后,只有我的程序会更改文本。另外,文字是一堆汉字,不是一两个,而是一堆这样的:
藡覶 跾 瑍痸碚 齫儽戃 羭聧蔩, 圪妀 跾 鶀嚵巆 堔埧娾 爂犤繵 摿斠榱 軥軱逴 潫 徖梜, 薍薝
我是否必须弄乱前景 window 而获得背景 window?或者 window 当前鼠标位置在哪里?我假设
ScreenToClient(hiWnd, &p->pt)
感谢大家的帮助!
What I want the program to do is change the title of the window the mouse cursor is at when i press a key on the keyboard
那你为什么要使用 mouse hook 而不是 keyboard hook?在键盘挂钩中,您可以使用 GetCursorPos()
获取当前鼠标屏幕位置。
至于你的实际问题,你没有检查以确保 WindowFromPoint()
甚至根本没有找到 window,你没有将正确对齐的内存指针传递给 WM_SETTEXT
,并且您没有考虑目标 window 是 Ansi 还是 Unicode。
尝试更像这样的东西:
键盘挂钩:
LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
{
if ((nCode == HC_ACTION) && (wParam == WM_KEYUP))
{
KBDLLHOOKSTRUCT* p = (KBDLLHOOKSTRUCT*)lParam;
if (p->vkCode == ...) // whatever key you are looking for
{
POINT pt;
GetCursorPos(&pt);
HWND hiWnd = WindowFromPoint(pt);
if (hiWnd)
{
ScreenToClient(hiWnd, &pt);
if (IsWindowUnicode(hiWnd))
{
LPWSTR buf = (LPWSTR) GlobalAlloc(GMEM_FIXED, 33 * sizeof(WCHAR));
if (buf)
{
snwprintf(buf, 33, L"X:%ld, Y:%ld", pt.x, pt.y);
SendMessageW(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
else
{
LPSTR buf = (LPSTR) GlobalAlloc(GMEM_FIXED, 33);
if (buf)
{
snprintf(buf, 33, "X:%ld, Y:%ld", pt.x, pt.y);
SendMessageA(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
}
}
}
return CallNextHookEx(0, nCode, wParam, lParam);
}
鼠标挂钩:
LRESULT CALLBACK LowLevelMouseProc(int nCode, WPARAM wParam, LPARAM lParam)
{
if ((nCode == HC_ACTION) && (wParam == WM_MOUSEMOVE))
{
MSLLHOOKSTRUCT* p = (MSLLHOOKSTRUCT*)lParam;
HWND hiWnd = WindowFromPoint(p->pt);
if (hiWnd)
{
POINT pt = p->pt;
ScreenToClient(hiWnd, &pt);
if (IsWindowUnicode(hiWnd))
{
LPWSTR buf = (LPWSTR) GlobalAlloc(GMEM_FIXED, 33 * sizeof(WCHAR));
if (buf)
{
snwprintf(buf, 33, L"X:%ld, Y:%ld", pt.x, pt.y);
SendMessageW(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
else
{
LPSTR buf = (LPSTR) GlobalAlloc(GMEM_FIXED, 33);
if (buf)
{
snprintf(buf, 33, "X:%ld, Y:%ld", pt.x, pt.y);
SendMessageA(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
}
}
return CallNextHookEx(0, nCode, wParam, lParam);
}
我有一个简短的问题。我从 MSDN 创建了一个标准 window 和 window api,创建了一个 window 站点。我想让程序做的是更改 window 当我按下键盘上的某个键时鼠标光标所在的标题。为此,我安装了一个低级鼠标挂钩,如下所示:
LRESULT CALLBACK LowLevelMouseProc(__in int nCode, __in WPARAM wParam, __in LPARAM lParam) {
MSLLHOOKSTRUCT* p = (MSLLHOOKSTRUCT*)lParam;
HWND hiWnd = WindowFromPoint(p->pt); //Get a handle to the top-most window
ScreenToClient(hiWnd, &p->pt); //Converts the cursor position from screen to the specified window
char buf[33];
switch (wParam) {
case WM_MOUSEMOVE:
snprintf(buf, sizeof(buf) - 1, "X:%ld, Y:%ld", p->pt.x, p->pt.y); //Put the cursor coordinates into a char buffer
SendMessage(hiWnd, WM_SETTEXT, 0, (LPARAM)buf); //Send a message to the other window to change the title
break;
}
return CallNextHookEx(0, nCode, wParam, lParam);
}
调用鼠标挂钩后,只有我的程序会更改文本。另外,文字是一堆汉字,不是一两个,而是一堆这样的:
藡覶 跾 瑍痸碚 齫儽戃 羭聧蔩, 圪妀 跾 鶀嚵巆 堔埧娾 爂犤繵 摿斠榱 軥軱逴 潫 徖梜, 薍薝
我是否必须弄乱前景 window 而获得背景 window?或者 window 当前鼠标位置在哪里?我假设
ScreenToClient(hiWnd, &p->pt)
感谢大家的帮助!
What I want the program to do is change the title of the window the mouse cursor is at when i press a key on the keyboard
那你为什么要使用 mouse hook 而不是 keyboard hook?在键盘挂钩中,您可以使用 GetCursorPos()
获取当前鼠标屏幕位置。
至于你的实际问题,你没有检查以确保 WindowFromPoint()
甚至根本没有找到 window,你没有将正确对齐的内存指针传递给 WM_SETTEXT
,并且您没有考虑目标 window 是 Ansi 还是 Unicode。
尝试更像这样的东西:
键盘挂钩:
LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
{
if ((nCode == HC_ACTION) && (wParam == WM_KEYUP))
{
KBDLLHOOKSTRUCT* p = (KBDLLHOOKSTRUCT*)lParam;
if (p->vkCode == ...) // whatever key you are looking for
{
POINT pt;
GetCursorPos(&pt);
HWND hiWnd = WindowFromPoint(pt);
if (hiWnd)
{
ScreenToClient(hiWnd, &pt);
if (IsWindowUnicode(hiWnd))
{
LPWSTR buf = (LPWSTR) GlobalAlloc(GMEM_FIXED, 33 * sizeof(WCHAR));
if (buf)
{
snwprintf(buf, 33, L"X:%ld, Y:%ld", pt.x, pt.y);
SendMessageW(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
else
{
LPSTR buf = (LPSTR) GlobalAlloc(GMEM_FIXED, 33);
if (buf)
{
snprintf(buf, 33, "X:%ld, Y:%ld", pt.x, pt.y);
SendMessageA(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
}
}
}
return CallNextHookEx(0, nCode, wParam, lParam);
}
鼠标挂钩:
LRESULT CALLBACK LowLevelMouseProc(int nCode, WPARAM wParam, LPARAM lParam)
{
if ((nCode == HC_ACTION) && (wParam == WM_MOUSEMOVE))
{
MSLLHOOKSTRUCT* p = (MSLLHOOKSTRUCT*)lParam;
HWND hiWnd = WindowFromPoint(p->pt);
if (hiWnd)
{
POINT pt = p->pt;
ScreenToClient(hiWnd, &pt);
if (IsWindowUnicode(hiWnd))
{
LPWSTR buf = (LPWSTR) GlobalAlloc(GMEM_FIXED, 33 * sizeof(WCHAR));
if (buf)
{
snwprintf(buf, 33, L"X:%ld, Y:%ld", pt.x, pt.y);
SendMessageW(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
else
{
LPSTR buf = (LPSTR) GlobalAlloc(GMEM_FIXED, 33);
if (buf)
{
snprintf(buf, 33, "X:%ld, Y:%ld", pt.x, pt.y);
SendMessageA(hiWnd, WM_SETTEXT, 0, (LPARAM)buf);
GlobalFree(buf);
}
}
}
}
return CallNextHookEx(0, nCode, wParam, lParam);
}