鼠标Hook<br><br><br><br> 利用HOOK建立鼠标增强程序<br>在Windows系统中提供了一种系统消息挂钩的(Message hook)功能,使用消息挂钩,可以实时监视处理系统中的各种消息。很多鼠标增强软件就是利用消息挂钩来拦截所有的鼠标消息进行处理的。<br>要设置鼠标消息挂钩,一般先建立一个使用鼠标消息挂钩的动态连接库(DLL)文件,然后就可以在其它程序中使用这个DLL文件处理鼠标消息。<br>下面的程序介绍通过鼠标消息挂钩监视鼠标消息,从而实现类似于一些鼠标增强软件一样的使窗口上下左右滚动的功能。<br>1.建立动态连接库<br>选择菜单 File|New ,选择DLL产生一个DLL模版,保存为 MHook.Dpr<br>//MHook.Dpr源程序<br>library MHook;<br>uses SysUtils,Classes,hkproc in 'hkproc.pas';<br>exports<br>EnableMouseHook,<br>DisableMouseHook;<br>begin<br>hNextHookProc:=0;<br>procSaveExit:=ExitProc;<br>ExitProc:=@HotKeyHookExit;<br>end.<br><br>再选择菜单 File|New ,选择Unit建立一个Pas文件,保存为 HKProc.pas<br>//HKProc.pas源程序<br>unit hkproc;<br>interface<br>uses Windows,Messages;<br>const<br>Move_Up = 0;<br>Move_Down=1;<br>Move_Left=2;<br>Move_Right=3;<br>var<br>hNextHookProc:HHook;<br>procSaveExit
ointer;<br>M_Direct:Integer;<br>LPoint:TPoint;<br>NowWindow:Integer;<br><br>function MouseProc(iCode:Integer;wParam:WPARAM;lParam
ointer):<br>LRESULT; stdcall;export;<br>function EnableMouseHook(WndHandle:integer):BOOL;export;<br>function DisableMouseHook:BOOL;export;<br>function GetDirect(FPoint : TPoint;LPoint : TPoint):integer;<br>procedure HotKeyHookExit;far;<br>implementation<br>//GetDirect函数根据光标的移动决定窗口滚动的方向。<br>function GetDirect(FPoint : TPoint;LPoint : TPoint):integer;<br>var<br>iWidth,iHeight:integer;<br>begin<br>iWidth:=LPoint.x-FPoint.x;<br>iHeight:=lPoint.y-FPoint.y;<br>Result:=-1;<br>if ((iWidth=0)or(iHeight=0))then exit;<br>if ((abs(iWidth) div abs(iHeight))>=2) then<br>if iWidth<0 then //Move to left<br>Result:=Move_Left<br>else<br>Result:=Move_Right<br>else if ((abs(iHeight) div abs(iWidth))>=2) then<br>if iHeight<0 then //Move to top<br>Result:=Move_Up<br>else<br>Result:=Move_Down;<br>end;<br><br>function MouseProc(iCode:Integer;wParam:WPARAM;<br>lParam
ointer):LRESULT; stdcall;export;<br>var<br>pMouse:^MOUSEHOOKSTRUCT;<br>l:integer;<br>begin<br>//如果用户按下鼠标右键同时Scroll Lock键为按下状态则滚动窗口。<br>if ((wParam=WM_RBUTTONDOWN) and Boolean(GetKeyState(145))) then<br>begin<br>pMouse:=lParam;<br>l:=GetDirect(lPoint,pMouse.pt);<br>if l>=0 then M_Direct:=l;<br>lPoint:=pMouse.pt;<br><br>NowWindow:=WindowFromPoint(lPoint);<br>if M_Direct=Move_Up then<br>SendMessage(NowWindow,WM_VSCROLL,SB_PAGEUP,0)<br>else if M_Direct=Move_Down then<br><br>SendMessage(NowWindow,WM_VSCROLL,SB_PAGEDOWN,0)<br>else if M_Direct=Move_Left then<br>SendMessage(NowWindow,WM_HSCROLL,SB_PAGELEFT,0)<br>else if M_Direct=Move_Right then<br>SendMessage(NowWindow,WM_HSCROLL,SB_PAGERIGHT,0);<br>Result:=1;<br>exit;<br>end<br>else if ((wParam=WM_RBUTTONUP) and Boolean(GetKeyState(145))) then<br>Result:=1<br>else<br>begin<br>Result:=0;<br>if iCode<0 then<br>begin<br>Result:=CallNextHookEx(hNextHookProc,iCode,wParam,integer(lParam));<br>Exit;<br>end;<br>end;<br>end;<br>function EnableMouseHook(WndHandle:integer):BOOL;export;<br>begin<br>GetCursorPos(lPoint);<br>Result:=False;<br>if hNextHookProc<>0 then exit;<br>//设置Mouse hook<br>hNextHookProc:=SetWindowsHookEx(WH_MOUSE,@MouseProc,Hinstance,0);<br>Result:=hNextHookProc<>0;<br>end;<br>function DisableMouseHook:BOOL;export;<br>begin<br>if hNextHookProc<>0 then<br>begin<br>UnHookWindowsHookEx(hNextHookProc);<br>hNextHookProc:=0;<br>end;<br>Result:=hNextHookProc=0;<br>end;<br>procedure HotKeyHookExit;<br>begin<br>if hNextHookProc<>0 then<br>DisableMouseHook;<br>ExitProc:=procSaveExit;<br>end;<br>end.<br>在菜单中选择 Project|Build MHook建立DLL文件。<br>2.建立程序调用动态连接库<br>在这里我们还是使用Delphi建立程序,当然也可以使用诸如VB等调用动态连接库。在菜单中选 File|New Application建立一个新程序,将工程文件保存为Project1.dpr<br>//project1的源程序<br>program Project1;<br>uses Forms, Sample1 in 'Sample1.pas' {Form1};<br>{$R *.RES}<br>begin<br>Application.Initialize;<br>//隐藏窗口<br>Application.ShowMainForm := False;<br>Application.CreateForm(TForm1, Form1);<br>Application.Run;<br>end. <br>将Form1的源程序文件保存成Sample1.pas<br>//Form1的源程序<br>unit Sample1;<br>interface<br>uses Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,<br>StdCtrls, Menus, ImgList,ShellApi, ExtCtrls;<br>const<br>WM_ICONMESSAGE=WM_USER+$100;<br>type<br>TForm1 = class(TForm)<br>procedure FormClose(Sender: TObject; var Action: TCloseAction);<br>procedure FormCreate(Sender: TObject);<br>private<br>procedure WMBarIcon(var Message:TMessage);message WM_ICONMESSAGE;<br>public<br>end;<br>function EnableMouseHook(WndHandle:integer):BOOL;external 'MHook.DLL';<br>function DisableMouseHook:BOOL;external'MHook.DLL';<br>var<br>Form1: TForm1;<br>implementation<br>{$R *.DFM}<br>procedure TForm1.WMBarIcon (var Message:TMessage);<br>begin<br>//用户双击任务栏图标则关闭程序 <br>if Message.LParam = WM_LBUTTONDBLCLK then close;<br>end;<br>procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);<br>var<br>lpData
NotifyIconData;<br>begin<br>//删除任务栏图标<br>lpData := new(PNotifyIconDataA);<br>lpData.cbSize := 88;//SizeOf(PNotifyIconDataA);<br>lpData.Wnd := Form1.Handle;<br>lpData.hIcon := Form1.Icon.Handle;<br>lpData.uCallbackMessage := WM_ICONMESSAGE;<br>lpData.uID :=0;<br>lpData.szTip := '鼠标演示';<br>lpData.uFlags := NIF_ICON or NIF_MESSAGE or NIF_TIP;<br>Shell_NotifyIcon(NIM_DELETE,lpData);<br>dispose(lpData);<br>//解除Mouse hook<br>DisableMouseHook;<br>end;<br>procedure TForm1.FormCreate(Sender: TObject);<br>var<br>lpData
NotifyIconData;<br>begin<br>EnableMouseHook(Form1.Handle);<br>Form1.Visible := False;<br>lpData := new(PNotifyIconDataA);<br>lpData.cbSize := 88;//SizeOf(PNotifyIconDataA);<br>lpData.Wnd := Form1.Handle;<br>lpData.hIcon := Form1.Icon.Handle;<br>lpData.uCallbackMessage := WM_ICONMESSAGE;<br>lpData.uID :=0;<br>lpData.szTip := '鼠标演示';<br>lpData.uFlags := NIF_ICON or NIF_MESSAGE or NIF_TIP;<br>Shell_NotifyIcon(NIM_ADD,lpData);<br>dispose(lpData);<br>end;<br>end.<br>运行程序,按下Scroll Lock键使其有效,将光标移动到文本窗口中(如IE、Word),移动鼠标,点击鼠标右键,窗口就可以依上一次移动的方向滚动。<br>利用上面的原理,将程序做一些改动,就可以象专业的鼠标增强程序一样做出例如缩放窗口,运行程序等很多鼠标增强效果来。上面的程序在Windows95,Delphi4.0下运行通过。<br>