Событие изменения состава окон в системе
Как это сделать?
SetWindowsHookEx(WH_SHELL,ShellProc,...
LRESULT CALLBACK ShellProc( int nCode,
WPARAM wParam,
LPARAM lParam
);
Parameters
nCode
[in] Specifies the hook code. If nCode is less than zero, the hook procedure must pass the message to the CallNextHookEx function without further processing and should return the value returned by CallNextHookEx. This parameter can be one of the following values.
HSHELL_WINDOWACTIVATED
The activation has changed to a different top-level, unowned window.
HSHELL_WINDOWCREATED
A top-level, unowned window has been created. The window exists when the system calls this hook.
HSHELL_WINDOWDESTROYED
A top-level, unowned window is about to be destroyed. The window still exists when the system calls this hook.
HSHELL_WINDOWREPLACED
Windows XP: A top-level window is being replaced. The window exists when the system calls this hook.
За остальным в MSDN
А обязательно выносить этот хук в отдельную dll?
Ну если это глобальный хук то нужно выносить в отдельную длл. Поэксперементируй. Еще можеш посмотреть хук типа WH_CBT
Ну если это глобальный хук то нужно выносить в отдельную длл. Поэксперементируй. Еще можеш посмотреть хук типа WH_CBT
Пробовал по-разному, ниче нормально не получилось.
Например:
LRESULT CALLBACK CBTProc(int nCode,WPARAM wParam,LPARAM lParam)
{
//пока пусть так
MessageBox(NULL,"hh","hh",MB_OK);
return true;
}
int APIENTRY WinMain(HINSTANCE hInst,HINSTANCE hPrev,LPSTR lpCmdLine,int nCmdShow)
{
..
hook=SetWindowsHookEx(WH_SHELL,ShellProc,NULL,GetCurrentThreadId());
..
}
Может есть нормальный работающий пример?
Вот здесь:
hkprcSysMsg = (HOOKPROC)GetProcAddress(hinstDLL, "ShellProc");
адрес получается неправильно, GetLastError дает 127. Почему так?
В dll поцедура:
LRESULT CALLBACK ShellProc(int nCode,WPARAM wParam,LPARAM lParam)
{
MessageBox(NULL,"hh","hh",MB_OK);
return true;
}
Попробовал через dll.
Вот здесь:
hkprcSysMsg = (HOOKPROC)GetProcAddress(hinstDLL, "ShellProc");
адрес получается неправильно, GetLastError дает 127. Почему так?
}
Да потому что ты походу даже не имееш прелставления о том что используется декорация имен при сборке твоего проекта. Т.е к примеру у тебя есть функция ShellProc,а в исходном файле она будет экспортироваться как _ShellProc@12 или что то подобное.
Попробуй сделать следующее:
int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
//создаем что нить
.............................
MYHOOKPROC hkprcSysMsg;
HMODULE hinstDLL = LoadLibrary((LPCTSTR) "hook.dll");
if(hinstDLL)
hkprcSysMsg = (MYHOOKPROC)GetProcAddress(hinstDLL, "MySetHook");
if(hkprcSysMsg)
hkprcSysMsg(1);
// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd,hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
if(hkprcSysMsg)
hkprcSysMsg(0);
return 0;
}
//Dll проект hookdll
//hookdll.h
#ifdef HOOKDLL_EXPORTS
#define HOOKDLL_API __declspec(dllexport)
#else
#define HOOKDLL_API __declspec(dllimport)
#endif
extern "C" HOOKDLL_API bool MySetHook(int mode);
//hookdll.cpp
#include "hookdll.h"
HHOOK g_hhok=0;
HANDLE g_Hins=0;
BOOL APIENTRY DllMain( HANDLE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
g_Hins=hModule;
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
LRESULT CALLBACK CBTProc(int nCode,WPARAM wParam,LPARAM lParam)
{
//а надо так
if(nCode>0)
{
//не советую MesageBox здесь вызывать
//MessageBox(NULL,"hh","hh",MB_OK);
}
//и соответственно в твоем случае всегда необходимо вызывать CallNextHookEx
return CallNextHookEx(0,nCode,wParam,lParam);
}
HOOKDLL_API bool MySetHook(int mode)
{
if(mode)
{
g_hhok=SetWindowsHookEx(WH_CBT,CBTProc,(HINSTANCE) g_Hins,0);
}
else
{
if(g_hhok)
UnhookWindowsHookEx(g_hhok);
}
return false;
}
Ты писал CallNextHookEx(0,nCode,wParam,lParam), но в большинстве примеров первый параметр ставят HHOOK, это имеет значение? С нулем проще реализовать вариант, когда SetWindowsHookEx находится в программе, а не dll-ке.
Насчет PROC - тупил, надо было писать typedef bool (__cdecl* FUNC1)(HWND). С CALLBACK, как в примере в MSDN, не пашет.
The CallNextHookEx function passes the hook information to the next hook procedure in the current hook chain. A hook procedure can call this function either before or after processing the hook information.
Syntax
LRESULT CallNextHookEx( HHOOK hhk,
int nCode,
WPARAM wParam,
LPARAM lParam
);
Parameters
hhk
[COLOR=purple]Ignored[/COLOR]
nCode
[in] Specifies the hook code passed to the current hook procedure. The next hook procedure uses this code to determine how to process the hook information.
wParam
[in] Specifies the wParam value passed to the current hook procedure. The meaning of this parameter depends on the type of hook associated with the current hook chain.
lParam
[in] Specifies the lParam value passed to the current hook procedure. The meaning of this parameter depends on the type of hook associated with the current hook chain.
Return Value
Т.е первый парметр данной функции игнорируется и поэтому туда можно писать что угодно ну я пишу туда 0.