WH_FOREGROUNDIDLE
Windows вызывает этот хук, когда к текущему потоку не поступает пользовательский ввод для обработки. Когда хук установлен как локальный, Windows вызывает его только при условии отсутствия пользовательского ввода у потока, к которому прикреплен хук. Данный хук является уведомительным, оба параметра – и wParam , и lParam – равны нулю.
WH_GETMESSAGE
Windows вызывает этот хук перед выходом из функций GetMessageи PeekMessage. Фильтрующие функции получают указатель на структуру с сообщением, которое затем (вместе со всеми изменениями) посылается приложению, вызвавшему GetMessageили PeekMessage. В lParam находится указатель на структуру MSG:
typedef struct tagMSG { /* msg */
HWND hwnd; // Окно, чья Winproc получит сообщение
UINT message; // Номер сообщения
WPARAM wParam;
LPARAM lParam;
DWORD time; // Время посылки сообщения
POINT pt; // Позиция указателя мыши (в экранных координатах)
// для этого сообщения
} MSG;
WH_HARDWARE
Этот хук в Win32 пока не реализован.
Регистрационные хуки
Регистрационные хуки (journal hooks) используются для записи и воспроизведения событий. Они могут устанавливаться только как системные, и, следовательно, должны использоваться как можно реже. Эти хуки воздействуют на все приложения Windows; хотя десктоп и не позволяет такого другим хукам, регистрационные хуки могут записывать и воспроизводить последовательности событий и от десктопа, и для десктопа. Другой побочный эффект регистрационных хуков в том, что все системные входные очереди проходят через один поток, который установил такой хук.
В Win32 предусмотрена специальная последовательность действий, с помощью которой пользователь может убрать регистрационный хук (например, в случае, если он завесил систему). Windows отключит записывающий или воспроизводящий регистрационный хук, когда пользователь нажмет CTRL+ESC, ALT+ESC, или CTRL+ALT+DEL. Windows оповестит приложение, установившее этот хук, посылкой ему сообщения WM_CANCELJOURNAL.
WM_CANCELJOURNAL
Это сообщение посылается с хэндлом окна, равным NULL, чтобы оно не попало в оконную процедуру. Лучший способ получить это сообщение – прикрепить к WH_GETMESSAGE фильтрующую функцию, которая бы следила за входящими сообщениями. В документация по Win32 упоминается, что приложение может получить сообщение WM_CANCELJOURNAL между вызовами функций GetMessage(или PeekMessage) и DispatchMessage. Хотя это и так, нет гарантий, что приложение будет вызывать эти функции, когда будет послано сообщение. Например, если приложение занято показом диалогового окна, главный цикл обработки сообщений не получит управление.
Комбинации клавиш CTRL+ESC, ALT+ESC, и CTRL+ALT+DEL встроены в систему, чтобы пользователь всегда смог остановить регистрационный хук. Было бы неплохо, если каждое приложение, использующее регистрационные хуки, также предусматривало для пользователя способ остановки тотальной регистрации. Рекомендуемый способ – использовать код VK_CANCEL (CTRL+BREAK).
WH_JOURNALRECORD
Windows вызывает этот хук при удалении события из системной очереди. Таким образом, фильтры этого хука вызываются для всех мышиных и клавиатурных событий, кроме тех, которые проигрываются регистрационным хуком на воспроизведение. Фильтрующие функции могут обработать сообщение (то есть, записать или сохранить событие в памяти, на диске, или и там, и там), но не могут изменять или отменять его. Фильтры этого хука могут находиться и внутри DLL, и в .EXE-файле. В Win32 для этого хука реализован только код HC_ACTION.
HC_ACTION
Windows вызывает хук WH_JOURNALRECORD с этим кодом при удалении события из системной очереди. Этот код сигнализирует фильтрующей функции о том, что это событие является нормальным. В lParam при этом передается указатель на структуру EVENTMSG. Обычная процедура записи состоит в сохранении всех пришедших хуку структур EVENTMSG в памяти или на диске.
Структура EVENTMSG описана в WINDOWS.H следующим образом:
typedef struct tagEVENTMSG {
UINT message;
UINT paramL;
UINT paramH;
DWORD time;
HWND hwnd;
} EVENTMSG;
typedefstruct tagEVENTMSG *PEVENTMSG, NEAR *NPEVENTMSG, FAR *LPEVENTMSG;
Элемент message является идентификатором сообщения, одним из значений WM_*. Значения paramL и paramH зависят от источника события – мышь это или клавиатура. Если это событие мыши, в paramL и paramH передаются координаты x и y события. Если это клавиатурное событие, в paramL находятся два значения: скан-код клавиши в HIBYTE и виртуальный код клавиши в LOBYTE, а paramH содержит число повторений. 15-й бит числа повторений служит индикатором дополнительной клавиши. В элементе time хранится системное время (наступления события), которое возвращается функцией GetTickCount. hwnd – это хэндл окна, получившего событие.
Читать дальше