So I'm trying to run a simple code in C that prints the position of the mouse every time it moves. To keep the program running for a while and then exit, I use a for loop shown below. I want the hook to be associated with the current thread only. Here's the code:
#include <stdio.h>
#include <windows.h>
// Global hook handle
HHOOK hHook = NULL;
// Mouse hook callback
LRESULT CALLBACK MouseHookProc(int nCode, WPARAM wParam, LPARAM lParam) {
printf("Entered\n");
if (nCode >= 0) {
if ((nCode == HC_ACTION) && (wParam == WM_MOUSEMOVE)) {
MOUSEHOOKSTRUCT* pMouseStruct = (MOUSEHOOKSTRUCT*)lParam;
printf("Mouse X: %ld, Mouse Y: %ld\n", pMouseStruct->pt.x, pMouseStruct->pt.y);
}
}
return CallNextHookEx(hHook, nCode, wParam, lParam);
}
int main() {
// Install the mouse hook
hHook = SetWindowsHookEx(WH_MOUSE, (HOOKPROC) &MouseHookProc, NULL, GetCurrentThreadId());
if (hHook == NULL) {
printf("Hook installation failed\n");
return 1;
}
// Keep program running (edit 1)
MSG msg;
while (GetMessage(&msg, NULL, 0, 0) > 0) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
// Unhook and exit
UnhookWindowsHookEx(hHook);
return 0;
}
The printf statement never gets executed. Why is the proc not getting called even though the hook was set up successfully?
Edit: My apologies for not mentioning this explicitly but I had initially tried it with a message loop instead of the for
loop shown above, but the result was the same. It does however, work if I use a low level mouse hook WH_MOUSE_LL
instead. Why is this happening?
Update: I'll try to describe what I'm trying to achieve better. Firstly, I'm trying to make a standalone console executable, not a Windows app. I was initially trying to poll the mouse position a finite number of times but now I believe a better approach for my application would be to sample as long as the program is active, and then release the hooks along with with the other cleanup jobs to exit the program gracefully. The problem I'm facing is that I'm unable to use a normal mouse hook WM_MOUSE
as opposed to a low-level one WM_MOUSE_LL
. I read from some sources that the hook procedure must be injected into the executable through a DLL but I can't get that to work either. Right now the only thing that works is a low-level mouse hook which slows down my program and makes it almost unusable.
As I said in the comment,
WH_MOUSE
absolutely definitely works fine.Using the Monitoring System Events document sample.
Use UnhookWindowsHookEx.