关于超想
本站导航
邮件列表
  首页 | 本站产品 | Delphi资料 | 免费资源 | 程序人生 | 软件工程 | 网站设计 | 推荐网站
你所在的位置 -> 主页 -> 超想软件 -> 编程资料 -> delphi -> 开发技巧 -> API相关 ->详细
相关内容  
 
 
在Delphi程序中应用IE浏览器控件
 
【新品推荐】

  详细内容
 

Hook的制作
作者: 评价: 上站日期: 2001-09-05
内容说明:
来源:


 
> 这样说好了,,我写了一支 A 程式,A 程式执行时若按 F1 则 run a1.exe 
>  按 F2 则 run a2.exe 
>  
> 现在我的 A 程式成被摆到背景去了..不管 User 怎麽按 F1/F2 
> 我写的 A.exe 就是没法子知道....因为我没有控制权了,, 
> 我猜要拦 Windows95 的 Keyboard Event,类似萤幕保护程式的作法 
> ..只是不知要怎麽作...:) 

您的问题看来只好挂上 WH_KEYBOARD 这型的 HOOK 才行了, 我试了一 
下, 可以用, 目前设定成每次按下 Ctrl+B, 记事本就会被启动. 有时 
间的话, 说不定又可以包装一个元件出来, 提供一些诸如OnXXXKeyHit 
之类的事件出来.... :) 

Delphi 真是太可爱了, 用它来实作 HOOK 竟然如此简单. :) 

大家可以按下列步骤试试看: 

1. 将以下的文字剪贴存成 HKTest.DPR 

--- Cut Here --- 
library HKTest; 

uses 
HKProc in 'HKProc.pas'; 

exports 
EnableHotKeyHook, 
DisableHotKeyHook; 

begin 
hNextHookProc := 0; 
procSaveExit := ExitProc; 
ExitProc := @HotKeyHookExit; 
end. 
--- Cut Here --- 


2. 将以下的文字剪贴存成 HKProc.PAS 
(Note: HKTest.DPR 与 HKProc.PAS 建议储存在同一个目录) 

--- Cut Here --- 
unit HKProc; 

interface 

uses 
Windows, Messages; 

var 
hNextHookProc: HHook; 
procSaveExit: Pointer; 

function KeyboardHookHandler(iCode: Integer; 
wParam: WPARAM; 
lParam: LPARAM): LRESULT; stdcall; export; 
function EnableHotKeyHook: BOOL; export; 
function DisableHotKeyHook: BOOL; export; 
procedure HotKeyHookExit; far; 

implementation 

function KeyboardHookHandler(iCode: Integer; 
wParam: WPARAM; 
lParam: LPARAM): LRESULT; stdcall; export; 
const 
_KeyPressMask = $80000000; 
begin 
Result := 0; 
If iCode <  0 Then 
begin 
Result := CallNextHookEx(hNextHookProc, iCode, wParam, lParam); 
Exit; 
end; 
// 侦测 Ctrl + B 组合键 
if ((lParam and _KeyPressMask) = 0) and 
(GetKeyState(vk_Control) <  0) and (wParam = Ord('B')) then 
begin 
Result := 1; 
WinExec('Notepad.exe', sw_Normal); // 记事本 
end; 
end; 

function EnableHotKeyHook: BOOL; export; 
begin 
Result := False; 
if hNextHookProc < >  0 then Exit; 
// 挂上 WH_KEYBOARD 这型的 HOOK, 同时, 传回值必须保留下 
// 来, 免得 HOOK 呼叫链结断掉 
hNextHookProc := SetWindowsHookEx(WH_KEYBOARD, 
KeyboardHookHandler, 
HInstance, 
0); 
Result := hNextHookProc < >  0; 
end; 

function DisableHotKeyHook: BOOL; export; 
begin 
if hNextHookProc < >  0 then 
begin 
UnhookWindowshookEx(hNextHookProc); // 解除 Keyboard Hook 
hNextHookProc := 0; 
MessageBeep(0); 
MessageBeep(0); 
end; 
Result := hNextHookProc = 0; 
end; 

procedure HotKeyHookExit; 
begin 
// 如果忘了解除 HOOK, 自动代理解除的动作 
if hNextHookProc < >  0 then DisableHotKeyHook; 
ExitProc := procSaveExit; 
end; 

end. 
--- Cut Here --- 

3. 启动 Delphi 2.0 

4. 开启 HKTest.DPR, 然後 Project | Build All 以产生 HKTest.DLL 

5. File | New Application 开启一个新的专案 

6. 将此专案 unit1 与 project1 存档, 请注意: 请存到与 HKTest.DLL 
相同的目录中. 

7. 在 Form1 上安置二个 TButton, 并撰写 OnClick 程式, 同时, 
在 implementation 节中宣告 EnableHotKeyHook() 与 
DisableHotKeyHook(), 修改後的程式应类似: 
... 
... 
implementation 

{$R *.DFM} 

function EnableHotKeyHook: BOOL; external 'HKTEST.DLL'; 
function DisableHotKeyHook: BOOL; external 'HKTEST.DLL'; 

procedure TForm1.Button1Click(Sender: TObject); 
begin 
if EnableHotKeyHook then 
ShowMessage('HotKey Testing...'); 
end; 

procedure TForm1.Button2Click(Sender: TObject); 
begin 
if DisableHotKeyHook then 
ShowMessage('HotKey Testing..., DONE!!'); 
end; 

end. 

8. 专案再存档一次, 执行. 

OK! 执行後, 滑鼠点一下 Button1, 然後, 不管 form1 在不在前景, 极小化 
也可以, 按下 Ctrl + B 这个组合键, 记事本就启动了. 

regards, 
Wolfgang Chien 


X-Sender: wolfgang@ms2.hinet.net 
Date: Sat, 19 Oct 1996 02:48:32 +0800 
To: delphichat@ibmsrv.cc.nthu.edu.tw 
From: Wolfgang Chien 
Subject: Re: [Delphi][Form] 如何拦截 Windows95 的按键 ? 
Sender: owner-delphichat@ibmsrv.cc.nthu.edu.tw 
Reply-To: delphichat@ibmsrv.cc.nthu.edu.tw 

earthian wrote: 
> >  您的问题看来只好挂上 WH_KEYBOARD 这型的 HOOK 才行了, 我试了一 
> >  下, 可以用, 目前设定成每次按下 Ctrl+B, 记事本就会被启动. 有时 
> >  间的话, 说不定又可以包装一个元件出来, 提供一些诸如OnXXXKeyHit 
> >  之类的事件出来.... :) 
> >  Delphi 真是太可爱了, 用它来实作 HOOK 竟然如此简单. :) 
> >  大家可以按下列步骤试试看: 
> >  1. 将以下的文字剪贴存成 HKTest.DPR 
> >  --- Cut Here --- 
> >  library HKTest; 
> >  : 
> >  
> 试了一下.. 
> 如果把 DLL 的程式码一并放到 Project1 里面, 合并成一个 .exe 时, 
> 当 Focus 不是 Project1 时, 就无法栏到 Hot key...为甚麽呢?? 

HOOK可分成 task scope 与 system scope 两种, Windows 系统会先呼 
叫 task scope 的函式, 然後才呼叫 system scope 的函式; 但如果当 
时挂上 task scope hook 的程式不在前景, 则其所属的 task scope 
hook 当然没有作用. (不然怎麽叫 task scope 嘛! :p) 

以您的情形, 如果不是实作成 DLL, 而是将之移入 .exe 的Project中, 
那它就从 system scope 变成 task scope 的 hook, 当程式在背景时, 
Windows 当然就不理会这个 hook 函式了. 

换句话说, system scope 的 HOOK 必须实作成 DLL. 而且, 某些类型 
的 HOOK 还必须要求只能以 system scope 的方式挂上去, 像是 
WH_JOURNALPLAYBACK, 就是其中一个. 进一步的资讯, 您可以参考Win 
SDK Reference. 市面上讲 Windows 程式设计比较深入的我认为应该要 
涵盖这个题目. 

>  
> 另外.. 
> 如何 Hook 到 Mouse 同时按下 Left & Right Button.. 
> 或者其中任意两键同时按.. 
>  

上次我举的是 WH_KEYBOARD 这型的例子, 如果要过滤 Mouse Message, 
那您可以考虑 WH_MOUSE 或 WH_HARDWARE 型. 

 

 
你所在的位置 -> 主页 -> 超想软件 -> 编程资料 -> delphi -> 开发技巧 -> API相关 ->详细
  首页 | 本站产品 | Delphi资料 | 免费资源 | 程序人生 | 软件工程 | 网站设计 | 推荐网站
声明:本站内容除注明原创以外均从网上摘抄,如有侵权请指明。
  如果您对我们的网站有什么意见或者建议,请与我们联系
powered by 建站易上手- V2.0