
先贴代码
Codeusing System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace MouseHook
{
public partial class Form1 : Form
{
int hHook;//用来保存钩子句柄。
HookProc hook;//用来存放消息处理函数。
public Form1()
{
InitializeComponent();
}
/// <summary>
/// 该函数用于安装钩子。
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void button1_Click(object sender, EventArgs e)
{
//所谓安装钩子就是调用SetWindowsHookEx方法。
hook=new HookProc(MouseHookProc);
hHook = SetWindowsHookEx(14,hook , IntPtr.Zero, 0); ;
if (hHook > 0) { MessageBox.Show("钩子安装成功!"); } else { MessageBox.Show("钩子安装失败!"); }
}
/// <summary>
/// 使用完必须卸载钩子。
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void button2_Click(object sender, EventArgs e)
{
//所谓卸载钩子就是调用UnhookWindowsHookEx方法
if (hHook > 0)
{
UnhookWindowsHookEx(hHook);
}
else
{
MessageBox.Show("尚未安装钩子!");
}
}
/// <summary>
/// 钩到消息后用这个函数来处理。
/// </summary>
/// <param name="nCode"></param>
/// <param name="wParam"></param>
/// <param name="lParam"></param>
/// <returns></returns>
private int MouseHookProc(int nCode, IntPtr wParam, IntPtr lParam)
{
//钩到的鼠标消息就存放在地址为lParam的地方,Marshal.PtrToStructure方法就是用来把相应内存处的数据转换为.Net能够方便处理的数据结构(类)。
var mhs = (MouseHookStruct)Marshal.PtrToStructure(lParam, typeof(MouseHookStruct));
if (nCode < 0)
{
return CallNextHookEx(hHook, nCode, wParam, lParam);//调用钩子链中的下一个钩子
}
else
{
//开始处理消息
textBox1.Text = string.Format("当前鼠标位置为:({0},{1})", mhs.Point.X, mhs.Point.Y);
//结束处理消息
return CallNextHookEx(hHook, nCode, wParam, lParam);////调用钩子链中的下一个钩子
}
}
#region Win32API
#region 系统接口
public delegate int HookProc(int nCode, IntPtr wParam, IntPtr lParam);//钩子回调函数的委托(或签名)
//安装钩子
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
public static extern int SetWindowsHookEx(int idHook, HookProc lpfn, IntPtr hInstance, int threadId);
//卸载钩子
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
public static extern bool UnhookWindowsHookEx(int idHook);
//调用下一个钩子
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
public static extern int CallNextHookEx(int idHook, int nCode, IntPtr wParam, IntPtr lParam);
#endregion
#region 数据结构
[StructLayout(LayoutKind.Sequential)]
public class POINT
{
public int X;
public int Y;
}
[StructLayout(LayoutKind.Sequential)]
public class MouseHookStruct
{
public POINT Point;
public int hWnd;
public int wHitTestCode;
public int dwExtraInfo;
}
#endregion
#endregion
}
}
使用鼠标钩子只须要调用SetWindowsHookEx函数便可,该函数是操做系统给咱们的API,经过引用外部函数的形式来引用。该函数须要参数有:一、钩子的类型(WH_MOUSE_LL=14为鼠标低级钩子),二、钩子的回调函数(即钩到消息后怎么处理,该函数的类型用HookProc表示),三、应用程序句柄(这里设为0),四、线程句柄(也设为0)。安装以后钩子就应该能够运行了,贴下结果:this