刚学习写钩子程序,写了一个简单的判断TAB键按下的钩子函数
function myHookProc(nCode:integer;wParam:wParam;lParam:lParam):LResult;
begin
showmessage('start');
if nCode<0 then
  begin
    result:=CallNextHookEx(myHook,nCode,wParam,lParam);
  end;
if wParam = VK_TAB then
   showmessage('aaaa');
result:=CallNextHookEx(myHook,nCode,wParam,lParam);
end;
下面是开启钩子函数
procedure TForm1.Button1Click(Sender: TObject);
begin
myHook:=setwindowshookex(WH_JOURNALRECORD,@myHookProc,Hinstance,GetCurrentThreadID);
end;
取消钩子函数
procedure TForm1.Button2Click(Sender: TObject);
begin
if myHook<>0 then
   begin
     unhookwindowshookex(myHook);
     myHook:=0;
   end;
end;请问问题出在哪儿??谢谢~

解决方案 »

  1.   

    if pEventMSG(lParam)^.message=WM_KEYDOWN then
      begin
        KeyValue:=pEventMSG(lParam)^.paramL mod 256;
        if Keyvalue=9 then
          showmessage('tab');  
        end;
      

  2.   

    还是不行啊~~
    没错误,但是没效果~
    可以肯定的是我定义的挂钩函数没有被执行~
    开始的showmessage都show不出来~
      

  3.   

    如果把
    myHook:=setwindowshookex(WH_JOURNALRECORD,@myHookProc,Hinstance,GetCurrentThreadID);
    改成
    myHook:=setwindowshookex(WH_JOURNALRECORD,@myHookProc,Hinstance,0);
    执行,show第一个start的时候,就出现错误,错误提示是:
    系统错误码:120。此功能只被此系统支持~
      

  4.   

    KbHook定义为全局函数
     Function KbHook( code: Integer; wparam: Word; lparam: LongInt ): LRESULT;stdcall;
    oldHook定义为全局变量即在
    var Form1:TForm1;
        oldHook:=hHook;
    implementation
    .............
    procedure TForm1.Button1Click(Sender: TObject);
    begin
     if oldHook=0 then
       oldHook := SetWindowsHookEx( WH_JOURNALRECORD, @KbHook, HInstance, 0);end;
    procedure TForm1.Button2Click(Sender: TObject);
    begin
      If oldHook <> 0 Then
      Begin
      UnhookWindowshookEx( oldHook );
      oldHook := 0;
    end;Function KbHook( code: Integer; wparam: Word; lparam: LongInt ): LRESULT;stdcall;
    var  KeyValue:UINT;
        ks: TkeyBoardState;
    Begin
      showmessage('start');
      result:=0;
      If code < 0 Then
      begin
        result:= CallNextHookEx( oldHook, code, wparam, lparam );
      end
      Else begin
        if pEventMSG(lParam)^.message=WM_KEYDOWN then
        begin
          KeyValue:=pEventMSG(lParam)^.paramL mod 256;
          if Keyvalue=9 then
            showmessage('tab');  
          end;
        end;
    end;
    /////////////////////////////
    再不行就不知道了,这个在我机上试过是可以的.
      

  5.   

    回复人: linzhengqun(风) ( )
    谢谢~~
    我现在出的问题还是:
    show第一个start的时候,就出现错误,错误提示是:
    系统错误码:120。此功能只被此系统支持~我也不知道,请问:
    KbHook定义为全局函数
     Function KbHook( code: Integer; wparam: Word; lparam: LongInt ): LRESULT;stdcall;
    函数声明是放在哪儿才算全局函数?
    可能是我位置放错了~
    谢谢了~
      

  6.   

    搞不明白,下面是我的原代码,窗口上只放了两个button~
    哪位兄弟能够帮我测试一下错在哪儿啊~
    感激不尽:
    unit Unit1;interface
    uses
      Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
      Dialogs, StdCtrls, ComCtrls;
    type
      TForm1 = class(TForm)
        Button1: TButton;
        Button2: TButton;
        procedure Button1Click(Sender: TObject);
        procedure FormClose(Sender: TObject; var Action: TCloseAction);
      private
        { Private declarations }
      public
      
        { Public declarations }
      end;
    var
      Form1: TForm1;
      myhook:HHook;implementation{$R *.dfm}
    function myHookProc(nCode:integer;wParam:wParam;lParam:lParam):LRESULT;stdcall;
    var  KeyValue:UINT;
        ks: TkeyBoardState;
    Begin
      //showmessage('start');
      result:=0;
      If ncode < 0 Then
      begin
        result:= CallNextHookEx( myHook, ncode, wparam, lparam );
      end
      Else begin
        if pEventMSG(lParam)^.message=WM_KEYDOWN then
        begin
          KeyValue:=pEventMSG(lParam)^.paramL mod 256;
          if Keyvalue=9 then
            showmessage('tab');
          end;
        end;end;
    procedure TForm1.Button1Click(Sender: TObject);
    begin
    if myhook = 0 then
    myHook:=setwindowshookex(WH_JOURNALRECORD,@myHookProc,HInstance,0);
    //myHook:=setwindowshookex(WH_KEYBOARD,@myHookProc,0,GetCurrentThreadId);
    end;procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
    begin
    if myHook<>0 then
       begin
         unhookwindowshookex(myHook);
         myHook:=0;
       end;
    end;end.
      

  7.   

    唉,想帮你试,不过前一阵子重装了系统,现在没有dephi.
    没办法,公司不用,我也快不会用dephi了...
      

  8.   

    不要用Showmeesage,用了就会出错了的,这样就可以了.unit Unit1;interfaceuses
      Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
      Dialogs, StdCtrls;type
      TForm1 = class(TForm)
        Button1: TButton;
        Edit1: TEdit;
        procedure Button1Click(Sender: TObject);
        procedure FormClose(Sender: TObject; var Action: TCloseAction);
      private
        { Private declarations }
      public
        { Public declarations }
      end;
    function myHookProc(nCode:integer;wParam:wParam;lParam:lParam):LRESULT;stdcall;var
      Form1: TForm1;
      myhook:HHook;implementation{$R *.dfm}
    function myHookProc(nCode:integer;wParam:wParam;lParam:lParam):LRESULT;
    var  KeyValue:UINT;
        ks: TkeyBoardState;
    Begin
      result:=0;
      If ncode < 0 Then
      begin
        result:= CallNextHookEx( myHook, ncode, wparam, lparam );
      end
      Else begin
        if pEventMSG(lParam)^.message=WM_KEYDOWN then
        begin
          KeyValue:=pEventMSG(lParam)^.paramL mod 256;
          if Keyvalue=9 then
            Form1.Edit1.text:='OK';
          end;
        end;end;procedure TForm1.Button1Click(Sender: TObject);
    begin
      if myhook = 0 then
    myHook:=setwindowshookex(WH_JOURNALRECORD,@myHookProc,HInstance,0);end;procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
    begin
       if myHook<>0 then
       begin
         unhookwindowshookex(myHook);
         myHook:=0;
       end;end;end.
      

  9.   

    linzhengqun(风) ( ) 
    谢谢了`
    恩~