zoukankan      html  css  js  c++  java
  • 添加钩子监听全局鼠标或键盘事件

      1 using System;
      2 using System.Collections.Generic;
      3 using System.Linq;
      4 using System.Reflection;
      5 using System.Runtime.InteropServices;
      6 using System.Text;
      7 using System.Threading.Tasks;
      8 using System.Windows.Forms;
      9 
     10 namespace WinGPChat
     11 {
     12     ///   <summary> 
     13     ///   这个类可以让你得到一个在运行中程序的所有键盘或鼠标事件 
     14     ///   并且引发一个带KeyEventArgs参数的.NET事件以便你很容易使用这些信息 
     15     ///   </summary>
     16     public class KeyBordHook
     17     {
     18         private const int WM_KEYDOWN = 0x100;
     19         private const int WM_KEYUP = 0x101;
     20         private const int WM_SYSKEYDOWN = 0x104;
     21         private const int WM_SYSKEYUP = 0x105;
     22         //全局的事件 
     23         public event KeyEventHandler OnKeyDownEvent;
     24         public event KeyEventHandler OnKeyUpEvent;
     25         public event KeyPressEventHandler OnKeyPressEvent;
     26         static int hKeyboardHook = 0;   //键盘钩子句柄 
     27         //鼠标常量 
     28         public const int WH_KEYBOARD_LL = 13;   //keyboard   hook   constant   
     29         HookProc KeyboardHookProcedure;   //声明键盘钩子事件类型. 
     30         //声明键盘钩子的封送结构类型 
     31         [StructLayout(LayoutKind.Sequential)]
     32         public class KeyboardHookStruct
     33         {
     34             public int vkCode;   //表示一个在1到254间的虚似键盘码 
     35             public int scanCode;   //表示硬件扫描码 
     36             public int flags;
     37             public int time;
     38             public int dwExtraInfo;
     39         }
     40         //装置钩子的函数 
     41         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
     42         public static extern int SetWindowsHookEx(int idHook, HookProc lpfn, IntPtr hInstance, int threadId);
     43         //卸下钩子的函数 
     44         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
     45         public static extern bool UnhookWindowsHookEx(int idHook);
     46         //下一个钩挂的函数 
     47         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
     48         public static extern int CallNextHookEx(int idHook, int nCode, Int32 wParam, IntPtr lParam);
     49         [DllImport("user32 ")]
     50         public static extern int ToAscii(int uVirtKey, int uScanCode, byte[] lpbKeyState, byte[] lpwTransKey, int fuState);
     51         [DllImport("user32 ")]
     52         public static extern int GetKeyboardState(byte[] pbKeyState);
     53         public delegate int HookProc(int nCode, Int32 wParam, IntPtr lParam);
     54         ///   <summary> 
     55         ///   墨认的构造函数构造当前类的实例并自动的运行起来. 
     56         ///   </summary> 
     57         public KeyBordHook()
     58         {
     59             Start();
     60         }
     61         //析构函数. 
     62         ~KeyBordHook()
     63         {
     64             Stop();
     65         }
     66         public void Start()
     67         {
     68             //安装键盘钩子   
     69             if (hKeyboardHook == 0)
     70             {
     71                 KeyboardHookProcedure = new HookProc(KeyboardHookProc);
     72                 hKeyboardHook = SetWindowsHookEx(WH_KEYBOARD_LL, KeyboardHookProcedure, Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().ManifestModule), 0);
     73                 if (hKeyboardHook == 0)
     74                 {
     75                     Stop();
     76                     throw new Exception("SetWindowsHookEx   ist   failed. ");
     77                 }
     78             }
     79         }
     80         public void Stop()
     81         {
     82             bool retKeyboard = true;
     83             if (hKeyboardHook != 0)
     84             {
     85                 retKeyboard = UnhookWindowsHookEx(hKeyboardHook);
     86                 hKeyboardHook = 0;
     87             }
     88             //如果卸下钩子失败 
     89             if (!(retKeyboard)) throw new Exception("UnhookWindowsHookEx   failed. ");
     90         }
     91         private int KeyboardHookProc(int nCode, Int32 wParam, IntPtr lParam)
     92         {
     93             if ((nCode >= 0) && (OnKeyDownEvent != null || OnKeyUpEvent != null || OnKeyPressEvent != null))
     94             {
     95                 KeyboardHookStruct MyKeyboardHookStruct = (KeyboardHookStruct)Marshal.PtrToStructure(lParam, typeof(KeyboardHookStruct));
     96                 //引发OnKeyDownEvent 
     97                 if (OnKeyDownEvent != null && (wParam == WM_KEYDOWN || wParam == WM_SYSKEYDOWN))
     98                 {
     99                     Keys keyData = (Keys)MyKeyboardHookStruct.vkCode;
    100                     KeyEventArgs e = new KeyEventArgs(keyData);
    101                     OnKeyDownEvent(this, e);
    102                 }
    103                 //引发OnKeyPressEvent 
    104                 if (OnKeyPressEvent != null && wParam == WM_KEYDOWN)
    105                 {
    106                     byte[] keyState = new byte[256];
    107                     GetKeyboardState(keyState);
    108                     byte[] inBuffer = new byte[2];
    109                     if (ToAscii(MyKeyboardHookStruct.vkCode,
    110                       MyKeyboardHookStruct.scanCode,
    111                       keyState,
    112                       inBuffer,
    113                       MyKeyboardHookStruct.flags) == 1)
    114                     {
    115                         KeyPressEventArgs e = new KeyPressEventArgs((char)inBuffer[0]);
    116                         OnKeyPressEvent(this, e);
    117                     }
    118                 }
    119                 //引发OnKeyUpEvent 
    120                 if (OnKeyUpEvent != null && (wParam == WM_KEYUP || wParam == WM_SYSKEYUP))
    121                 {
    122                     Keys keyData = (Keys)MyKeyboardHookStruct.vkCode;
    123                     KeyEventArgs e = new KeyEventArgs(keyData);
    124                     OnKeyUpEvent(this, e);
    125                 }
    126             }
    127             return CallNextHookEx(hKeyboardHook, nCode, wParam, lParam);
    128         }
    129     }
    130 
    131     ///   <summary> 
    132     ///   这个类可以让你得到一个在运行中程序的所有鼠标事件 
    133     ///   并且引发一个带MouseEventArgs参数的.NET鼠标事件以便你很容易使用这些信息 
    134     ///   </summary> 
    135     public class MouseHook
    136     {
    137         private const int WM_MOUSEMOVE = 0x200;
    138         private const int WM_LBUTTONDOWN = 0x201;
    139         private const int WM_RBUTTONDOWN = 0x204;
    140         private const int WM_MBUTTONDOWN = 0x207;
    141         private const int WM_LBUTTONUP = 0x202;
    142         private const int WM_RBUTTONUP = 0x205;
    143         private const int WM_MBUTTONUP = 0x208;
    144         private const int WM_LBUTTONDBLCLK = 0x203;
    145         private const int WM_RBUTTONDBLCLK = 0x206;
    146         private const int WM_MBUTTONDBLCLK = 0x209;
    147         //全局的事件 
    148         public event MouseEventHandler OnMouseActivity;
    149         static int hMouseHook = 0;   //鼠标钩子句柄 
    150         //鼠标常量 
    151         public const int WH_MOUSE_LL = 14;   //mouse   hook   constant 
    152         HookProc MouseHookProcedure;   //声明鼠标钩子事件类型. 
    153         //声明一个Point的封送类型 
    154         [StructLayout(LayoutKind.Sequential)]
    155         public class POINT
    156         {
    157             public int x;
    158             public int y;
    159         }
    160         //声明鼠标钩子的封送结构类型 
    161         [StructLayout(LayoutKind.Sequential)]
    162         public class MouseHookStruct
    163         {
    164             public POINT pt;
    165             public int hWnd;
    166             public int wHitTestCode;
    167             public int dwExtraInfo;
    168         }
    169         //装置钩子的函数 
    170         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
    171         public static extern int SetWindowsHookEx(int idHook, HookProc lpfn, IntPtr hInstance, int threadId);
    172         //卸下钩子的函数 
    173         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
    174         public static extern bool UnhookWindowsHookEx(int idHook);
    175         //下一个钩挂的函数 
    176         [DllImport("user32.dll ", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
    177         public static extern int CallNextHookEx(int idHook, int nCode, Int32 wParam, IntPtr lParam);
    178         public delegate int HookProc(int nCode, Int32 wParam, IntPtr lParam);
    179         ///   <summary> 
    180         ///   墨认的构造函数构造当前类的实例. 
    181         ///   </summary> 
    182         public MouseHook()
    183         {
    184             //Start(); 
    185         }
    186         //析构函数. 
    187         ~MouseHook()
    188         {
    189             Stop();
    190         }
    191         public void Start()
    192         {
    193             //安装鼠标钩子 
    194             if (hMouseHook == 0)
    195             {
    196                 //生成一个HookProc的实例. 
    197                 MouseHookProcedure = new HookProc(MouseHookProc);
    198                 hMouseHook = SetWindowsHookEx(WH_MOUSE_LL, MouseHookProcedure, Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0]), 0);
    199                 //如果装置失败停止钩子 
    200                 if (hMouseHook == 0)
    201                 {
    202                     Stop();
    203                     throw new Exception("SetWindowsHookEx failed. ");
    204                 }
    205             }
    206         }
    207         public void Stop()
    208         {
    209             bool retMouse = true;
    210             if (hMouseHook != 0)
    211             {
    212                 retMouse = UnhookWindowsHookEx(hMouseHook);
    213                 hMouseHook = 0;
    214             }
    215             //如果卸下钩子失败 
    216             if (!(retMouse)) throw new Exception("UnhookWindowsHookEx   failed. ");
    217         }
    218         private int MouseHookProc(int nCode, Int32 wParam, IntPtr lParam)
    219         {
    220             //如果正常运行并且用户要监听鼠标的消息 
    221             if ((nCode >= 0) && (OnMouseActivity != null))
    222             {
    223                 MouseButtons button = MouseButtons.None;
    224                 int clickCount = 0;
    225                 switch (wParam)
    226                 {
    227                     case WM_LBUTTONDOWN:
    228                         button = MouseButtons.Left;
    229                         clickCount = 1;
    230                         break;
    231                     case WM_LBUTTONUP:
    232                         button = MouseButtons.Left;
    233                         clickCount = 1;
    234                         break;
    235                     case WM_LBUTTONDBLCLK:
    236                         button = MouseButtons.Left;
    237                         clickCount = 2;
    238                         break;
    239                     case WM_RBUTTONDOWN:
    240                         button = MouseButtons.Right;
    241                         clickCount = 1;
    242                         break;
    243                     case WM_RBUTTONUP:
    244                         button = MouseButtons.Right;
    245                         clickCount = 1;
    246                         break;
    247                     case WM_RBUTTONDBLCLK:
    248                         button = MouseButtons.Right;
    249                         clickCount = 2;
    250                         break;
    251                 }
    252                 //从回调函数中得到鼠标的信息 
    253                 MouseHookStruct MyMouseHookStruct = (MouseHookStruct)Marshal.PtrToStructure(lParam, typeof(MouseHookStruct));
    254                 MouseEventArgs e = new MouseEventArgs(button, clickCount, MyMouseHookStruct.pt.x, MyMouseHookStruct.pt.y, 0);
    255                 OnMouseActivity(this, e);
    256             }
    257             return CallNextHookEx(hMouseHook, nCode, wParam, lParam);
    258         }
    259     }
    260 }
     /// <summary>
            /// 钩子类型监听鼠标键盘等事件句柄
            /// </summary>
            private enum HookType : int
            {
                WH_JOURNALRECORD = 0,
                WH_JOURNALPLAYBACK = 1,
                WH_KEYBOARD = 2,
                WH_GETMESSAGE = 3,
                WH_CALLWNDPROC = 4,
                WH_CBT = 5,
                WH_SYSMSGFILTER = 6,
                WH_MOUSE = 7,//局部 线程级别
                WH_HARDWARE = 8,
                WH_DEBUG = 9,
                WH_SHELL = 10,
                WH_FOREGROUNDIDLE = 11,
                WH_CALLWNDPROCRET = 12,
                WH_KEYBOARD_LL = 13,
                WH_MOUSE_LL = 14 //全局
            }
    
            /// <summary>
            /// 鼠标或键盘事件常量值
            /// </summary>
            private const int WM_MOUSEMOVE = 0x200;
            private const int WM_LBUTTONDOWN = 0x201;
            private const int WM_RBUTTONDOWN = 0x204;
            private const int WM_MBUTTONDOWN = 0x207;
            private const int WM_LBUTTONUP = 0x202;
            private const int WM_RBUTTONUP = 0x205;
            private const int WM_MBUTTONUP = 0x208;
            private const int WM_LBUTTONDBLCLK = 0x203;
            private const int WM_RBUTTONDBLCLK = 0x206;
            private const int WM_MBUTTONDBLCLK = 0x209;

    转载:http://blog.163.com/epeda@126/blog/static/418034782012798394905/

  • 相关阅读:
    TextVew中文空格
    java中String字符串的替换函数:replace与replaceAll的区别
    朝花夕拾
    Eclipse启动时卡死在"Android SDK: Resolving error markers"的解决方法
    签名“未签名”apk文件命令
    TODO
    完全卸载AndroidStudio
    Gradle
    经受时间沉淀的15 个 Android 通用流行框架大全
    jquery 获取 新添加元素 点击后 的子元素
  • 原文地址:https://www.cnblogs.com/jieliu726/p/5013739.html
Copyright © 2011-2022 走看看