How to detect docking / undocking
Download
|
|
This is a Delphi function that waits for docking/undocking event.
It utilizes
TWmiSystemEvents component to wait for the event.
As noted in the help file, this will only work under Windows XP and higher.
Writing an event handler for the UI type application is pretty straight forward: drop
TWmiSystemEvents component on the form, go to the Events tab of
Object Inspector, double click on the OnDocking event.
The code below demonstrates how to create an event handler in the console application. The function WaitForDocking returns true if docking or undocking happened, and false if the specified time elapsed. |
type
// this object is required only in console applications.
// In UI applications the TWmiSystemEvents component can be
// dropped on the form, the event handler will be the form's method.
TWaitObject = class
private
FEventHappend: boolean;
private
procedure EventHandler(AObject: TObject);
public
property EventHappend: boolean read FEventHappend;
end;
procedure TWaitObject.EventHandler(AObject: TObject);
begin
FEventHappend := true;
end;
// this is needed to avoid blocking in the tight loop.
// it only needed in console application.
// UI type application is normally event-driven and does not have
// the tight loops.
procedure ProcessMessage;
var
Msg: TMsg;
begin
if PeekMessage(Msg, 0, 0, 0, PM_REMOVE) then
begin
TranslateMessage(Msg);
DispatchMessage(Msg);
end;
end;
// this function waits for docking/undocking event for specified time.
// it returns true if the event happed and false if the specified
// time elapsed.
function WaitForDocking(WaitTimeMillisec: integer): boolean;
var
vWmiEvents: TWmiSystemEvents;
vDeadline: TDateTime;
vWaitObject: TWaitObject;
vTime: double;
const
SECOND = 1/24/60/60;
begin
Result := false;
vTime := WaitTimeMillisec;
vDeadline := Now + (vTime/1000) * SECOND;
// setup: create and link the components together
vWaitObject := TWaitObject.Create;
vWmiEvents := TWmiSystemEvents.Create(nil);
try
vWmiEvents.PoolingInterval := 100;
vWmiEvents.OnDocking := vWaitObject.EventHandler;
// try to activate. It may fail if the computer does not have
// WMI (like windows 95, 98, NT without WMI core installed)
try
vWmiEvents.Active := true;
except
Exit;
end;
while Now < vDeadline do
if vWaitObject.EventHappend then
begin
Result := true;
Exit;
end else
begin
Sleep(100);
ProcessMessage; // avoids tight loop.
end;
finally
vWmiEvents.Free;
vWaitObject.Free;
end;
end;
|