First off, let me explain why you'd want to use this rather than GetAsyncKeyState(). I used to use GetAsyncKeyState all the time, however, the possibility of figuring out if a key was really 'pressed' (not held down, not up) took far too much work (keeping track of keystates yourself, it's very hackish). Using this method you can notify your application when a key is 'pressed' (down and then up), when a key is down (held down) or when a key is up (released).
Without further delay, here is the source.
HotkeyListener.h
Code:
#pragma once
extern HHOOK hHotkeyHook;
LRESULT CALLBACK HotkeyMessageProc(int code, WPARAM wParam, LPARAM lParam);
void InstallHotkeyHook();
void RemoveHotkeyHook();
HotkeyListener.cpp
Code:
#include "stdafx.h"
#include "HotkeyListener.h"
HHOOK hHotkeyHook;
#define HK_IS_PRESSED ((DWORD)lParam & 0x40000000)
#define HK_IS_HELD ((DWORD)lParam & 0x40000000)
#define HK_IS_RELEASED (!((DWORD)lParam & 0x40000000))
LRESULT CALLBACK HotkeyMessageProc(int code, WPARAM wParam, LPARAM lParam)
{
if (code > 0) return CallNextHookEx(hHotkeyHook, code, wParam, lParam);
else if (code == HC_ACTION)
{
if (HK_IS_PRESSED)
{
// Key was pressed, VK_KEY code is in wParam.
}
else if (HK_IS_HELD)
{
}
else if (HK_IS_RELEASED)
{
}
}
return CallNextHookEx(hHotkeyHook, code, wParam, lParam);
}
void InstallHotkeyHook()
{
hHotkeyHook = SetWindowsHookEx(WH_KEYBOARD, HotkeyMessageProc, GetModuleHandle(NULL), GetCurrentThreadId());
}
void RemoveHotkeyHook()
{
UnhookWindowsHookEx(hHotkeyHook);
}
Example DLLMain.cpp
Code:
#include "stdafx.h"
#include "HotkeyListener.h"
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
if (ul_reason_for_call == DLL_PROCESS_ATTACH)
{
InstallHotkeyHook();
}
else if (ul_reason_for_call == DLL_PROCESS_DETACH)
{
RemoveHotkeyHook();
}
return TRUE;
}
Code should be relatively self explanatory.
Questions? Ask them.