Advanced Windows API - RegisterShellHook()
For receiving shell notification messages the normal way would be to use the SetWindowsHookEx API function which requires the usage of an external dll file. All this just for receiving shell notification message always is a lot of work. However there is an undocumented windows api function called RegisterShellHook which makes this very easy. All you have to do is call this API function with the handle to the window which should receive shell message notification. Once called your window will receive a WM_SHELLHOOK message in its wndproc (message handler).
The RegisterShellHook() function is exported by shell32.dll. It is definetly working with Windows 2000 and newer windows version (haven't tested it on Win9x and NT4.0).
Of couse this API function isn't included in the default Delphi header files. To use it include this right before the implementation part of your unit.
function RegisterShellHook(wnd : hwnd; param : dword) : boolean; stdcall; external 'shell32.dll' index 181;
Next thing which has to be done is to register the WM_SHELLHOOK message (it doesn't exist by default). Do this one time in your project, best in the FormCreate event.
var WM_SHELLHOOK : integer; [...] WM_SHELLHOOK := RegisterWindowMessage('SHELLHOOK');
Now you can register your window for receiving shell hooks
RegisterShellHook(0,1); // Enabled the shell hook RegisterShellHook(HandleToWindow,3);
In order to Unregister your window from receivning shell hooks call the same function again with a different parameter
RegisterShellHook(HandleToWindow,0);
Once registered your window will receive the WM_SHELlHOOK message. To catch this message either use a custom wndproc or the OnMessage event of the TApplicationEvents component.
The LParam of the received message contains the handle to the target window which is related to the shell notification.
The WParam is the notification type. See Shell Proc on MSDN for details about the HSHELL_ params.
example how to use the WM_SHELLHOOK message:
var wnd : THandle; [...] if msg = WM_SHELLHOOK then begin wnd := msg.LParam; case msg.WParam of HSHELL_WINDOWCREATED : // A New window has been created HSHELL_REDRAW : // The caption of the window has changed HSHELL_REDRAW + 32768 : // The window is flashing in the taskbar HSHELL_WINDOWDESTROYED : // A window was destroyed HSHELL_WINDOWACTIVATED : // A non full screen window was activated HSHELL_WINDOWACTIVATED + 32768 : // A window was activated and is now in full screen mode HSHELL_GETMINRECT : // A window is being minimized or maximized end; end;
