C# winform 獲取滑鼠點擊位置

来源:https://www.cnblogs.com/ocean-wang/archive/2019/11/14/11855750.html
-Advertisement-
Play Games

說明:該篇隨筆的代碼內容並非出自本人,是在其他網站搜尋的,出處已經不記得了,本次隨筆只為記錄,目的幫助自己,幫助他人。 實現的原理也不做多的贅述,直接上代碼。 第一個類是需要用到的Windows API public class Win32Api { [StructLayout(LayoutKind ...


說明:該篇隨筆的代碼內容並非出自本人,是在其他網站搜尋的,出處已經不記得了,本次隨筆只為記錄,目的幫助自己,幫助他人。

實現的原理也不做多的贅述,直接上代碼。

 

第一個類是需要用到的Windows API

public class Win32Api
    {
        [StructLayout(LayoutKind.Sequential)]
        public class POINT
        {
            public int x;
            public int y;
        }
        [StructLayout(LayoutKind.Sequential)]
        public class MouseHookStruct
        {
            public POINT pt;
            public int hwnd;
            public int wHitTestCode;
            public int dwExtraInfo;
        }
        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);
    }
Windows API

第二個類是用於監控滑鼠移動,滑鼠點擊的

public class MouseHook
    {
        private Point point;
        private Point Point
        {
            get { return point; }
            set
            {
                if (point != value)
                {
                    point = value;
                    if (MouseMoveEvent != null)
                    {
                        var e = new MouseEventArgs(MouseButtons.None, 0, point.X, point.Y, 0);
                        MouseMoveEvent(this, e);
                    }
                }
            }
        }
        private int hHook;
        private const int WM_LBUTTONDOWN = 0x201;
        private const int WM_RBUTTONDOWN = 0x204;
        public const int WH_MOUSE_LL = 14;
        public Win32Api.HookProc hProc;
        public MouseHook()
        {
            this.Point = new Point();
        }
        public int SetHook()
        {
            hProc = new Win32Api.HookProc(MouseHookProc);
            hHook = Win32Api.SetWindowsHookEx(WH_MOUSE_LL, hProc, IntPtr.Zero, 0);
            return hHook;
        }
        public void UnHook()
        {
            Win32Api.UnhookWindowsHookEx(hHook);
        }
        private int MouseHookProc(int nCode, IntPtr wParam, IntPtr lParam)
        {
            Win32Api.MouseHookStruct MyMouseHookStruct = (Win32Api.MouseHookStruct)Marshal.PtrToStructure(lParam, typeof(Win32Api.MouseHookStruct));
            if (nCode < 0)
            {
                return Win32Api.CallNextHookEx(hHook, nCode, wParam, lParam);
            }
            else
            {
                if (MouseClickEvent != null)
                {
                    MouseButtons button = MouseButtons.None;
                    int clickCount = 0;
                    switch ((Int32)wParam)
                    {
                        case WM_LBUTTONDOWN:
                            button = MouseButtons.Left;
                            clickCount = 1;
                            break;
                        case WM_RBUTTONDOWN:
                            button = MouseButtons.Right;
                            clickCount = 1;
                            break;
                    }

                    var e = new MouseEventArgs(button, clickCount, point.X, point.Y, 0);
                    MouseClickEvent(this, e);
                }
                this.Point = new Point(MyMouseHookStruct.pt.x, MyMouseHookStruct.pt.y);
                return Win32Api.CallNextHookEx(hHook, nCode, wParam, lParam);
            }
        }

        public delegate void MouseMoveHandler(object sender, MouseEventArgs e);
        public event MouseMoveHandler MouseMoveEvent;

        public delegate void MouseClickHandler(object sender, MouseEventArgs e);
        public event MouseClickHandler MouseClickEvent;
    }
MouseHook

最後直接在窗體中調用重寫的事件即可

public getLocationForm()
        {
            InitializeComponent();
        }

        MouseHook mh;
        private void getLocationForm_Load(object sender, EventArgs e)
        {
            mh = new MouseHook();
            mh.SetHook();
            mh.MouseMoveEvent += mh_MouseMoveEvent;
            mh.MouseClickEvent += mh_MouseClickEvent;

        }

        private void mh_MouseClickEvent(object sender, MouseEventArgs e)
        {
            if (e.Button == MouseButtons.Right)
            {
                //MessageBox.Show(e.X + "-" + e.Y);

                textBox1.Text = e.X.ToString();
                textBox2.Text = e.Y.ToString();
            }
        }

        private void mh_MouseMoveEvent(object sender, MouseEventArgs e)
        {
            int x = e.Location.X;
            int y = e.Location.Y;
            textBox1.Text = x + "";
            textBox2.Text = y + "";
        }
        private void Form1_FormClosed(object sender, FormClosedEventArgs e)
        {
            mh.UnHook();
        }
getLocationForm

 

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 時區縮寫: 標準時間代碼 與GMT的偏移量 描述 NZDT +13:00 紐西蘭夏令時 IDLE +12:00 國際日期變更線,東邊 NZST +12:00 紐西蘭標準時間 NZT +12:00 紐西蘭時間 AESST +11:00 澳大利亞東部夏時制 CST(ACSST) +10:30 中澳大利亞 ...
  • 眾所周知,工欲善其事必先利其器,要想砍柴快一定得有把好刀,那麼要想代碼寫的有效率、質量高一個趁手的編輯器是必不可少的,寫代碼不可能就用系統自帶的文本編輯器(如果是大佬當我沒說),這裡我推薦各位使用微軟自家的編輯器(號稱宇宙最強的IDE Visual Studio) VS2017 下載地址:https ...
  • c#微信公眾號開發 基本設置 參考微信官方文檔 https://developers.weixin.qq.com/doc/offiaccount/Basic_Information/Access_Overview.html 開發→基本配置 公眾號開發信息 註:1.記錄好開發者密碼,會在程式中驗證過程 ...
  • 我們在開發中Json傳輸數據日益普遍,有很多關於Json字元串的序列化和反序列化的文章大多都告訴你怎麼用,但是卻不會告訴你用什麼更高效。因為有太多選擇,人們往往會陷入選擇難題。 相比.NET Framework有三種選擇而.net core下已經沒有JavaScriptSerializer,但是大家 ...
  • 例如想獲取尾碼名為.txt的文件 第一種方法獲取到的是對應的文件路徑 第二種方法可以獲取到文件的一些詳細信息 類似於"*.txt" 要與路徑中的文件名匹配的搜索字元串。這個參數可以包含有效的文本路徑和通配符(*和?)的組合人物,但它不支持正則表達式。 我是參照此路徑編寫的博客,用於自己查詢快速 ht ...
  • 這次的目標是實現通過標註Attribute實現緩存的功能,精簡代碼,減少緩存的代碼侵入業務代碼。 緩存內容即為Service查詢彙總的內容,不做其他高大上的功能,提升短時間多次查詢的響應速度,適當減輕資料庫壓力。 在做之前,也去看了EasyCaching的源碼,這次的想法也是源於這裡,AOP的方式讓 ...
  • 對於開發人員來說,常常需要在不藉助任何Microsoft Office及其他第三方軟體的情況下,打開、創建、修改、轉換、列印、瀏覽(Word、Excel、PowerPoint和PDF等)文檔,以及將數據從數據源轉換為常用的文檔格式,甚至一些其他的文檔操作。 在這裡,小編調查了業內許多開發人員,為大家 ...
  • 前言 在ASP.Net Core2.X調用的CreateWebHostBuilder和3.X的主要區別在於WebHost的調用,CreateDefaultBuilder被Host替換,另一個區別是對ConfigureWebHostDefaults()的調用; 由於新的主機生成器是通用主機生成器,因此 ...
一周排行
    -Advertisement-
    Play Games
  • 1. 說明 /* Performs operations on System.String instances that contain file or directory path information. These operations are performed in a cross-pla ...
  • 視頻地址:【WebApi+Vue3從0到1搭建《許可權管理系統》系列視頻:搭建JWT系統鑒權-嗶哩嗶哩】 https://b23.tv/R6cOcDO qq群:801913255 一、在appsettings.json中設置鑒權屬性 /*jwt鑒權*/ "JwtSetting": { "Issuer" ...
  • 引言 集成測試可在包含應用支持基礎結構(如資料庫、文件系統和網路)的級別上確保應用組件功能正常。 ASP.NET Core 通過將單元測試框架與測試 Web 主機和記憶體中測試伺服器結合使用來支持集成測試。 簡介 集成測試與單元測試相比,能夠在更廣泛的級別上評估應用的組件,確認多個組件一起工作以生成預 ...
  • 在.NET Emit編程中,我們探討了運算操作指令的重要性和應用。這些指令包括各種數學運算、位操作和比較操作,能夠在動態生成的代碼中實現對數據的處理和操作。通過這些指令,開發人員可以靈活地進行算術運算、邏輯運算和比較操作,從而實現各種複雜的演算法和邏輯......本篇之後,將進入第七部分:實戰項目 ...
  • 前言 多表頭表格是一個常見的業務需求,然而WPF中卻沒有預設實現這個功能,得益於WPF強大的控制項模板設計,我們可以通過修改控制項模板的方式自己實現它。 一、需求分析 下圖為一個典型的統計表格,統計1-12月的數據。 此時我們有一個需求,需要將月份按季度劃分,以便能夠直觀地看到季度統計數據,以下為該需求 ...
  • 如何將 ASP.NET Core MVC 項目的視圖分離到另一個項目 在當下這個年代 SPA 已是主流,人們早已忘記了 MVC 以及 Razor 的故事。但是在某些場景下 SSR 還是有意想不到效果。比如某些靜態頁面,比如追求首屏載入速度的時候。最近在項目中回歸傳統效果還是不錯。 有的時候我們希望將 ...
  • System.AggregateException: 發生一個或多個錯誤。 > Microsoft.WebTools.Shared.Exceptions.WebToolsException: 生成失敗。檢查輸出視窗瞭解更多詳細信息。 內部異常堆棧跟蹤的結尾 > (內部異常 #0) Microsoft ...
  • 引言 在上一章節我們實戰了在Asp.Net Core中的項目實戰,這一章節講解一下如何測試Asp.Net Core的中間件。 TestServer 還記得我們在集成測試中提供的TestServer嗎? TestServer 是由 Microsoft.AspNetCore.TestHost 包提供的。 ...
  • 在發現結果為真的WHEN子句時,CASE表達式的真假值判斷會終止,剩餘的WHEN子句會被忽略: CASE WHEN col_1 IN ('a', 'b') THEN '第一' WHEN col_1 IN ('a') THEN '第二' ELSE '其他' END 註意: 統一各分支返回的數據類型. ...
  • 在C#編程世界中,語法的精妙之處往往體現在那些看似微小卻極具影響力的符號與結構之中。其中,“_ =” 這一組合突然出現還真不知道什麼意思。本文將深入剖析“_ =” 的含義、工作原理及其在實際編程中的廣泛應用,揭示其作為C#語法奇兵的重要角色。 一、下劃線 _:神秘的棄元符號 下劃線 _ 在C#中並非 ...