Announcement

Collapse

Forum Guidelines

This forum is for finished source code that is working properly. If you have questions about this or any other source code, please post it in one of the Discussion Forums, not here.
See more
See less

Sample of global hook

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Sample of global hook

    Sample of global keyboard hook

    Exe

    Code:
       #Compile Exe
       #Dim All
       #Register None
       #Include "Win32Api.Inc"
    
       %IDC_LABEL     = 1000
       %IDC_LINE      = 1100
    
       $UniqueName = "My Hook"
    
       Declare Function SetHook Lib "HookD.Dll" Alias "SetHook" (hWnd As Long) As Long
    
       CallBack Function DlgProc
       
          Dim Ansi                                    As Local  Byte
          Dim hHook                                   As Local  Dword
          Dim Switches                                As Local  Dword
          Dim szText                                  As Local  String
          
          Select Case CbMsg
             Case %WM_INITDIALOG
                Control Add Label,  CbHndl, %IDC_LABEL + 1,  "Type something in external program", 5, 3, 130, 10, %WS_CHILD Or %WS_VISIBLE Or %WS_BORDER Or %SS_CENTER, %WS_EX_LEFT Or %WS_EX_LTRREADING
    
                Control Add Label,  CbHndl, %IDC_LABEL + 2,  "Ansi",              5, 20, 60, 10, %WS_CHILD Or %WS_VISIBLE Or %SS_RIGHT,  0
                Control Add Label,  CbHndl, %IDC_LABEL + 3,  "",                 75, 19, 60, 12, %WS_CHILD Or %WS_VISIBLE Or %SS_CENTER, %WS_EX_CLIENTEDGE
                Control Set Color   CbHndl, %IDC_LABEL + 3,  %Blue, %White
    
                Control Add Label,  CbHndl, %IDC_LABEL + 4,  "VirtualKeyCode",    5, 35, 60, 10, %WS_CHILD Or %WS_VISIBLE Or %SS_RIGHT,  0
                Control Add Label,  CbHndl, %IDC_LABEL + 5,  "",                 75, 34, 60, 12, %WS_CHILD Or %WS_VISIBLE Or %SS_CENTER, %WS_EX_CLIENTEDGE
                Control Set Color   CbHndl, %IDC_LABEL + 5,  %Blue, %White
    
                Control Add Line,   CbHndl, %IDC_LINE + 1,   "", 2, 50, 175, 1
                    
                Control Add Label,  CbHndl, %IDC_LABEL + 6,  "Shift",             5, 55, 60, 10, %WS_CHILD Or %WS_VISIBLE Or %SS_RIGHT,  0
                Control Add Label,  CbHndl, %IDC_LABEL + 7,  "",                 75, 54, 60, 12, %WS_CHILD Or %WS_VISIBLE Or %SS_CENTER, %WS_EX_CLIENTEDGE
                Control Set Color   CbHndl, %IDC_LABEL + 7,  %Blue, %White
    
                Control Add Label,  CbHndl, %IDC_LABEL + 8,  "Alt",               5, 70, 60, 10, %WS_CHILD Or %WS_VISIBLE Or %SS_RIGHT,  0
                Control Add Label,  CbHndl, %IDC_LABEL + 9,  "",                 75, 69, 60, 12, %WS_CHILD Or %WS_VISIBLE Or %SS_CENTER, %WS_EX_CLIENTEDGE
                Control Set Color   CbHndl, %IDC_LABEL + 9,  %Blue, %White
    
                Control Add Label,  CbHndl, %IDC_LABEL + 10, "Ctrl",              5, 85, 60, 10, %WS_CHILD Or %WS_VISIBLE Or %SS_RIGHT,  0
                Control Add Label,  CbHndl, %IDC_LABEL + 11, "",                 75, 84, 60, 12, %WS_CHILD Or %WS_VISIBLE Or %SS_CENTER, %WS_EX_CLIENTEDGE
                Control Set Color   CbHndl, %IDC_LABEL + 11, %Blue, %White
                           
                SetHook CbHndl
                
             Case %WM_USER + 1
                Ansi = LoByt(CbWParam)
                If Ansi < 32 Then szText = Hex$(Ansi, 2) + " (hex)" Else szText = Chr$(Ansi)
                Control Set Text CbHndl, %IDC_LABEL + 3, szText
    
                Control Set Text CbHndl, %IDC_LABEL + 5, Hex$(HiByt(LoWrd(CbWParam)), 2) + " (hex)"
    
                Switches = CbLParam
    
                If Bit(Switches, 1) Then szText = "Left"  Else szText = ""
                If Bit(Switches, 2) Then szText = "Right"
                Control Set Text CbHndl, %IDC_LABEL + 7, szText
    
                If Bit(Switches, 3) Then szText = "Left" Else szText = ""
                If Bit(Switches, 4) Then szText = "Right"
                Control Set Text CbHndl, %IDC_LABEL + 9, szText
                    
                If Bit(Switches, 5) Then szText = "Left" Else szText = ""
                If Bit(Switches, 6) Then szText = "Right"
                Control Set Text CbHndl, %IDC_LABEL + 11, szText
    
             Case %WM_DESTROY
                hHook = GetProp(CbHndl, ByVal 1)
                If hHook Then UnhookWindowsHookEx hHook
                
          End Select
    
       End Function
    
       Function PBMain
          
          Dim hDlg                                    As Local Dword
          
          Dialog New 0, $UniqueName, , , 140, 100, %WS_CAPTION Or %DS_MODALFRAME Or %WS_SYSMENU, %WS_EX_TOPMOST To hDlg
          Dialog Show Modal hDlg Call DlgProc
          
       End Function
    Dll

    Code:
       #Compile Dll "HookD.Dll"
       #Register None
       #Dim All
       #Include "Win32Api.Inc"
       $UniqueName = "My Hook"
    
       Global hInstDLL As Long, MainDll As Long
    
       Function LibMain(ByVal hInstance As Dword, ByVal fwdReason As Dword, ByVal lpvReserved As Dword) Export As Long
    
          If fwdReason = %DLL_PROCESS_ATTACH Then hInstDLL = hInstance
          LibMain = 1
    
       End Function
    
       Function HookProc(ByVal nCode As Long, ByVal wParam As Dword, ByVal lParam As Long) Export As Long
    
          Dim Ansi                                    As Local  Word
          Dim ControlButton                           As Static Byte
          Dim hDlg                                    As Static Dword
          Dim hHook                                   As Static Dword
          Dim KeyState(255)                           As Local  Byte
          Dim MenuButton                              As Static Byte
          Dim ShiftButton                             As Static Byte
          Dim ScanCode                                As Local  Byte
          Dim Switches                                As Local  Dword
          Dim VirtualKeyCode                          As Local  Byte
          Dim Vk1                                     As Local  Byte
          Dim Vk2                                     As Local  Byte
          
          hDlg = FindWindow("", $UniqueName)
          
          If hHook = 0 Then If hDlg Then hHook = GetProp(hDlg, ByVal 1)
          
          If hHook Then Function = CallNextHookEx(ByVal hHook, ByVal nCode, ByVal wParam, ByVal lParam)
          
          If IsFalse(MainDll) And (IsFalse(hDlg) Or IsFalse(hHook)) Then
             FreeLibrary hInstDll
          
          Else
             GetKeyBoardState KeyState(0)
             VirtualKeyCode = LoByt(wParam)
             ScanCode       = LoByt(HiWrd(lParam))
             If VirtualKeyCode = %VK_SHIFT Then
                If ScanCode = &H36 Then ShiftButton = 1 Else ShiftButton = 0
             ElseIf VirtualKeyCode = %VK_MENU Then
                If (lParam And &H01000000) Then MenuButton = 1 Else MenuButton = 0
    
             ElseIf VirtualKeyCode = %VK_CONTROL Then
                If (lParam And &H01000000) Then ControlButton = 1 Else ControlButton = 0
             End If
    
             If ShiftButton Then Vk1 = %VK_RSHIFT: Vk2 = %VK_LSHIFT Else Vk1 = %VK_LSHIFT: Vk2 = %VK_RSHIFT
             KeyState(Vk1) = KeyState(%VK_SHIFT)
             KeyState(Vk2) = 0
    
             If MenuButton Then Vk1 = %VK_RMENU: Vk2 = %VK_LMENU Else Vk1 = %VK_LMENU: Vk2 = %VK_RMENU
             KeyState(Vk1) = KeyState(%VK_MENU)
             KeyState(Vk2) = 0
    
             If ControlButton Then Vk1 = %VK_RCONTROL: Vk2 = %VK_LCONTROL Else Vk1 = %VK_LCONTROL: Vk2 = %VK_RCONTROL
             KeyState(Vk1) = KeyState(%VK_CONTROL)
             KeyState(Vk2) = 0
    
             If ToAsciiEx (VirtualKeyCode, ScanCode, ByRef KeyState(0), _
                ByVal VarPtr(Ansi), 0, GetKeyboardLayout(0)) <> 1 Then Ansi = 0
                
             If (KeyState(%VK_LSHIFT)   And &H80) Then Bit Set Switches, 1
             If (KeyState(%VK_RSHIFT)   And &H80) Then Bit Set Switches, 2
             If (KeyState(%VK_LMENU)    And &H80) Then Bit Set Switches, 3
             If (KeyState(%VK_RMENU)    And &H80) Then Bit Set Switches, 4
             If (KeyState(%VK_LCONTROL) And &H80) Then Bit Set Switches, 5
             If (KeyState(%VK_RCONTROL) And &H80) Then Bit Set Switches, 6
        
             SendMessage hDlg, %WM_USER + 1, MakWrd(Ansi, VirtualKeyCode), Switches
          End If
    
       End Function
    
       Function SetHook Alias "SetHook" (hWnd As Long) Export As Long
    
          Local hHook As Long
    
          hHook = SetWindowsHookEx (%WH_KEYBOARD, CodePtr(HookProc), ByVal hInstDLL, ByVal 0)
          SetProp hWnd, ByVal 1, ByVal hHook
          MainDll = 1
    
       End Function


    [This message has been edited by Semen Matusovski (edited April 27, 2005).]

    #2
    Sample #2. Retrieving name of desktop icon, when mouse moves over it.
    (12.05 - additional features)
    Spy-Dll
    Code:
       #Compile Dll "HookMs.Dll"
       #Register None
       #Dim All
       #Include "Win32Api.Inc"
       #Include "COMMCTRL.INC"
    
       Type COPYDATASTRUCT
        dwData As Dword Ptr
        cbData As Dword
        lpData As Dword
       End Type
    
       Global LastInfo As Long
       
       $HookFile = "C:\HookMs.Id"
       Global hInstDll As Long, TmpAsciiz As Asciiz * %MAX_PATH
       Global tRectExp As RECT, hWndLV As Long, hDlg As Long, hHook As Long
    
       Function LibMain(ByVal hInstance As Long, ByVal fwdReason As Long, _
          ByVal lpvReserved As Long) Export As Long
          Static hWnd As Long
          Select Case fwdReason
             Case %DLL_PROCESS_ATTACH: hInstDll = hInstance: LibMain = 1
             Case %DLL_PROCESS_DETACH: LibMain = 1
          End Select
       End Function
    
       Function HookProc(ByVal nCode As Long, ByVal wParam As Long, ByVal lParam As Long) Export As Long
          Static id As Long, i As Long, hWnd As Long
          Static TmpAsciizC As Asciiz * %MAX_PATH
          Static pt As PointApi, ptc As pointApi, Cdt As COPYDATASTRUCT
    
          Function = CallNextHookEx(hHook, nCode, wParam, ByVal lParam)
    
          If nCode < 0 Then Exit Function
          If hDlg = 0 Then Open $HookFile For Input Shared As #1: _
             Input #1, hDlg, hWndLv: Close #1: ptc.x = -1000
          If IsWindow(hDlg) = %False Then FreeLibrary hInstDLL: Exit Function
          GetCursorPos pt: If pt.x = ptc.x And pt.y = ptc.y Then Exit Function
          ptc.x = pt.x: ptc.y = pt.y: hWnd = WindowFromPoint (pt.x,pt.y)
          If hWndLV = 0 Then Exit Function
          If hWnd <> hWndLV Then
             If LastInfo <> 1 Then PostMessage hDlg, %WM_USER + 1, 0, 0: LastInfo = 1
             Exit Function
          End If
          If GetWindowThreadProcessId(hWndLv, ByVal 0) <> GetCurrentThreadId Then Exit Function
          ScreenToClient hWndLv, pt
          id = -1
          For i = 0 To ListView_GetItemCount(hWndLv) - 1
             tRectExp.nLeft = %LVIR_BOUNDS
             ListView_GetItemRect hwndLv, i, tRectExp, %LVIR_BOUNDS
             If pt.x >= tRectExp.nLeft And pt.x < tRectExp.nRight And _
                pt.y >= tRectExp.nTop And pt.y < tRectExp.nBottom Then id = i
          Next
          ListView_GetItemText hwndLv, id, 0, TmpAsciiz, SizeOf(TmpAsciiz)
          If LastInfo <> 2 Or TmpAsciiz <> TmpAsciizC Then
             TmpAsciizC = TmpAsciiz
             Cdt.cbdata = Len(TmpAsciiz) + 1
             Cdt.lpData  = VarPtr(TmpAsciiz)
             SendMessage hDlg, %WM_COPYDATA, 0, VarPtr(Cdt)
             LastInfo = 2
          End If
       End Function
    
       Function ENCW(ByVal hWnd As Long, ByVal lParam As Long) As Long
          Static tRect As RECT
          GetClassName hWnd, TmpAsciiz, SizeOf(TmpAsciiz): Function = 1
          If UCase$(TmpAsciiz) <> "SYSLISTVIEW32" Then
          Else
             GetClientRect hWnd, tRect
             If (tRect.nRight - tRect.nLeft) = (tRectExp.nRight - tRectExp.nLeft) And _
                (tRect.nBottom - tRect.nTop) = (tRectExp.nBottom - tRectExp.nTop) Then _
                hWndLV = hWnd: Function = 0
          End If
       End Function
    
       Function SetHookMouseWindow Alias "SetHookMouseWindow" (hWnd As Long) Export As Long
          InitCommonControls
          SystemParametersInfo %SPI_GETWORKAREA, 0, ByVal VarPtr(tRectExp), 0
          EnumChildWindows FindWindow ("Progman", ""), CodePtr(ENCW), 0
          hHook = SetWindowsHookEx (%WH_MOUSE, CodePtr(HookProc), ByVal hInstDLL, ByVal 0)
          Open "C:\HookMs.Id" For Output As #1: Print #1, hWnd, hWndLv;: Close
       End Function
    
       Function UnHookMouseWindow Alias "UnHookMouseWindow" Export As Long
          UnhookWindowsHookEx hHook: Kill $HookFile
       End Function
    Spy-Exe
    Code:
       #Compile Exe
       #Register None
       #Dim All
       #Include "Win32Api.Inc"
    
       Type COPYDATASTRUCT
           dwData As Dword Ptr
           cbData As Dword
           lpData As Asciiz Ptr
       End Type
       Declare Function SetHookMouseWindow Lib "HookMs.Dll" _
          Alias "SetHookMouseWindow" (hWnd As Long) As Long
       Declare Function UnHookMouseWindow  Lib "HookMs.Dll" _
          Alias "UnHookMouseWindow" As Long
       %ID_Text = 201
    
       CallBack Function DlgProc
          Static Id1 As Long, id2 As Long
          Select Case CbMsg
             Case %WM_INITDIALOG:
                SetHookMouseWindow CbHndl
             Case %WM_DESTROY : UnHookMouseWindow
             Case %WM_USER + 1
                Incr Id1: SetWindowText CbHndl, "Empty message #" + Str$(Id1)
                Control Set Text CbHndl, %ID_Text, "<---- Outside ---->"
             Case %WM_COPYDATA
                Dim cdt As COPYDATASTRUCT Ptr
                cdt = CbLparam
                Incr Id2: SetWindowText CbHndl, "Hook #" + Str$(Id2)
                Control Set Text CbHndl, %ID_Text, @cdt.@lpData
                Function = 1: Exit Function
          End Select
       End Function
    
       Function PbMain
          Local hDlg As Long
          Dialog New 0, "Icons",,, 250, 25, %WS_SYSMENU Or %WS_BORDER, %WS_EX_TOPMOST Or %WS_EX_TOOLWINDOW To hDlg
          Control Add Label, hDlg, %ID_Text, "", 5, 0, 240, 15
          Dialog Show Modal hDlg Call DlgProc
       End Function
    [This message has been edited by Semen Matusovski (edited May 13, 2000).]

    Comment


      #3
      Semen --

      I tried to run your Sample #1 program on a Windows 98 system, and it crashed the operating system.

      -- Eric

      ------------------
      Perfect Sync: Perfect Sync Development Tools
      Email: mailto:[email protected][email protected]</A>

      "Not my circus, not my monkeys."

      Comment


        #4
        Sample #3. How to retrieve a window, which receives a focus.

        Compile Dll, start Exe, switch to another app and watch it's caption.
        Some appa change their caption "on fly" (for example, Word).
        That's why sometimes you will not see an information about activation of new window.
        But this is a defect of the demonstration, not of the hook.

        Dll

        Code:
           #Compile Dll "Hook.Dll"
           #Register None
           #Dim All
           #Include "Win32Api.Inc"
        
           $TrayWndNm = "Any unique name"
           %NotifyId = %WM_USER + 401
        
           Global hHook As Long, hInstDLL As Long
           Function LibMain(ByVal hInstance As Long, ByVal fwdReason As Long, _
              ByVal lpvReserved As Long) Export As Long
               Select Case fwdReason
                 Case %DLL_PROCESS_ATTACH: hInstDLL = hInstance: LibMain = 1
                 Case %DLL_PROCESS_DETACH: LibMain = 1
              End Select
           End Function
        
           Function HookProc(ByVal nCode As Long, ByVal wParam As Long, ByVal lParam As Long) Export As Long
              Static hDlg As Long, NotFirstTime As Long
              Function = CallNextHookEx(ByVal hHook, ByVal nCode, ByVal wParam, ByVal lParam)
              If hDlg = 0 Then hDlg = FindWindow("", $TrayWndNm)
              If IsWindow(hDlg) = %False Then  FreeLibrary hInstDll Else _
               If (nCode = %HCBT_SETFOCUS) Or IsFalse(NotFirstTime) Then _
                 PostMessage hDlg, %NotifyId, GetForegroundWindow, wParam: NotFirstTime = %True
           End Function
        
           Function SetHookWindow Alias "SetHookWindow" (hWnd As Long) Export As Long
              hHook = SetWindowsHookEx (%WH_CBT, CodePtr(HookProc), ByVal hInstDLL, ByVal 0)
           End Function
        
           Function UnHookWindow Alias "UnHookWindow" Export As Long
              UnhookWindowsHookEx hHook
           End Function
        Exe
        Code:
           #Compile Exe
           #Dim All
           #Register None
           #Include "Win32Api.Inc"
        
           $TrayWndNm = "Any unique name"
           %NotifyId = %WM_USER + 401
                  
           Declare Function SetHookWindow Lib "Hook.Dll" Alias "SetHookWindow" (hWnd As Long) As Long
           Declare Function UnHookWindow Lib "Hook.Dll" Alias "UnHookWindow" As Long
        
           CallBack Function DlgProc
              Select Case CbMsg
                 Case %WM_INITDIALOG: SetHookWindow CbHndl
                 Case %WM_DESTROY   : UnHookWindow
                 Case %NotifyId
                    Static LastGetForegroundWindow As Long, LastGetFocus As Long
                    If CbWparam <> CbHndl Then
                       LastGetForegroundWindow = CbWparam: LastGetFocus = CbLparam
                       ' Demonstration
                       SetWindowText LastGetForegroundWindow, "hWnd with focus is &H" + Hex$(CbLparam)
                    End If
                    Function = 1: Exit Function
              End Select
           End Function
        
           Function PbMain()
              Local hDlg As Long
              Dialog New 0, $TrayWndNm, 0, 0, 100, 0, %WS_CAPTION Or %WS_SYSMENU, %WS_EX_TOPMOST To hDlg
              Dialog Show Modal hDlg Call DlgProc
           End Function


        [This message has been edited by Semen Matusovski (edited October 06, 2000).]

        Comment


          #5
          [deleted]

          [This message has been edited by Eric Pearson (edited May 08, 2000).]
          "Not my circus, not my monkeys."

          Comment

          Working...
          X
          😀
          🥰
          🤢
          😎
          😡
          👍
          👎