2012-04-27 73 views
16

是否可以通過編程方式在另一個窗口中單擊某個位置而無需將鼠標移至該位置,即使該窗口不在頂部?我想發送一種消息到另一個窗口來模擬鼠標點擊一個位置。以編程方式在另一個窗口中單擊鼠標

我試着用PostMessage的做到這一點:

PostMessage(WindowHandle, 0x201, IntPtr.Zero, CreateLParam(300,300)); 
PostMessage(WindowHandle, 0x202, IntPtr.Zero, CreateLParam(300,300)); 

我做了CreateLParam功能是這樣的:

private static IntPtr CreateLParam(int LoWord, int HiWord) 
{ 
    return (IntPtr)((HiWord << 16) | (LoWord & 0xffff)); 
} 

的問題是,窗口被鎖定他的位置。我認爲我的應用程序點擊(1,1)座標。可以幫助我解決這個問題嗎?

編輯: 這是PostMessage的:

[return: MarshalAs(UnmanagedType.Bool)] 
[DllImport("user32.dll")] 
public static extern bool PostMessage(IntPtr WindowHandle, int Msg, IntPtr wParam, IntPtr lParam); 

和0x201和0x202分別WM_LBUTTONDOWN和WM_LBUTTONUP。

+0

這是您控制的另一個窗口嗎?如果不是,這似乎是一個非常奇怪的要求。 – Tejs 2012-04-27 17:38:08

+0

你試圖點擊什麼程序?一些程序(主要是遊戲)有機制來處理你想要做的事情並忽略它。在這種情況下,你最好的機會就是使用WinApi使遊戲最頂級,移動鼠標,點擊,移動鼠標,將遊戲移回到先前的z順序。 – SimpleVar 2012-04-27 17:38:23

+0

另外,在做'<< 16'之前嘗試將'HiWord'投射到'uint'。 – SimpleVar 2012-04-27 17:49:03

回答

22

你不能通過發送消息來實現,而是使用SendInput Windows API。

調用方法ClickOnPoint,這是一個從窗體點擊事件的例子,所以this.handle是窗體句柄,注意這些窗口上的客戶端座標是女巫手柄發送的,你可以很容易地改變這個併發送屏幕座標,並且在那種情況下下面不需要處理或ClientToScreen調用。

ClickOnPoint(this.Handle, new Point(375, 340)); 

更新:現在使用SendInput,tnx Tom。

BTW。我以前只需要此示例的聲明,什麼更多的有一個很好的圖書館:Windows Input Simulator (C# SendInput Wrapper - Simulate Keyboard and Mouse)

public class ClickOnPointTool 
    { 

    [DllImport("user32.dll")] 
    static extern bool ClientToScreen(IntPtr hWnd, ref Point lpPoint); 

    [DllImport("user32.dll")] 
    internal static extern uint SendInput(uint nInputs, [MarshalAs(UnmanagedType.LPArray), In] INPUT[] pInputs, int cbSize); 

#pragma warning disable 649 
    internal struct INPUT 
    { 
     public UInt32 Type; 
     public MOUSEKEYBDHARDWAREINPUT Data; 
    } 

    [StructLayout(LayoutKind.Explicit)] 
    internal struct MOUSEKEYBDHARDWAREINPUT 
    { 
     [FieldOffset(0)] 
     public MOUSEINPUT Mouse; 
    } 

    internal struct MOUSEINPUT 
    { 
     public Int32 X; 
     public Int32 Y; 
     public UInt32 MouseData; 
     public UInt32 Flags; 
     public UInt32 Time; 
     public IntPtr ExtraInfo; 
    } 

#pragma warning restore 649 


    public static void ClickOnPoint(IntPtr wndHandle , Point clientPoint) 
    { 
     var oldPos = Cursor.Position; 

     /// get screen coordinates 
     ClientToScreen(wndHandle, ref clientPoint); 

     /// set cursor on coords, and press mouse 
     Cursor.Position = new Point(clientPoint.X, clientPoint.Y); 

     var inputMouseDown = new INPUT(); 
     inputMouseDown.Type = 0; /// input type mouse 
     inputMouseDown.Data.Mouse.Flags = 0x0002; /// left button down 

     var inputMouseUp = new INPUT(); 
     inputMouseUp.Type = 0; /// input type mouse 
     inputMouseUp.Data.Mouse.Flags = 0x0004; /// left button up 

     var inputs = new INPUT[] { inputMouseDown, inputMouseUp }; 
     SendInput((uint)inputs.Length, inputs, Marshal.SizeOf(typeof(INPUT))); 

     /// return mouse 
     Cursor.Position = oldPos; 
    } 

    } 
+0

謝謝,這個工程很棒。我還補充說,窗口在被點擊時會變爲活動狀態。 – Dagob 2012-04-27 19:54:28

+0

什麼是Point?(什麼名字空間)? – 2013-06-24 21:34:35

+1

System.Drawing(http://msdn.microsoft.com/en-us/library/system.drawing.point.aspx) – 2013-06-24 22:09:14

13

我在過去發現,一種方法來發送消息給的Windows Media Player 所以我用的是模擬點擊我想要的應用程序!

使用this class(代碼見下)找到窗口併發送你想要的信息!

using System; 
using System.Runtime.InteropServices; 

namespace Mouse_Click_Simulator 
{ 
    /// <summary> 
    /// Summary description for Win32. 
    /// </summary> 
    public class Win32 
    { 
     // The WM_COMMAND message is sent when the user selects a command item from 
     // a menu, when a control sends a notification message to its parent window, 
     // or when an accelerator keystroke is translated. 
     public const int WM_KEYDOWN = 0x100; 
     public const int WM_KEYUP = 0x101; 
     public const int WM_COMMAND = 0x111; 
     public const int WM_LBUTTONDOWN = 0x201; 
     public const int WM_LBUTTONUP = 0x202; 
     public const int WM_LBUTTONDBLCLK = 0x203; 
     public const int WM_RBUTTONDOWN = 0x204; 
     public const int WM_RBUTTONUP = 0x205; 
     public const int WM_RBUTTONDBLCLK = 0x206; 

     // The FindWindow function retrieves a handle to the top-level window whose 
     // class name and window name match the specified strings. 
     // This function does not search child windows. 
     // This function does not perform a case-sensitive search. 
     [DllImport("User32.dll")] 
     public static extern int FindWindow(string strClassName, string strWindowName); 

     // The FindWindowEx function retrieves a handle to a window whose class name 
     // and window name match the specified strings. 
     // The function searches child windows, beginning with the one following the 
     // specified child window. 
     // This function does not perform a case-sensitive search. 
     [DllImport("User32.dll")] 
     public static extern int FindWindowEx(
      int hwndParent, 
      int hwndChildAfter, 
      string strClassName, 
      string strWindowName); 


     // The SendMessage function sends the specified message to a window or windows. 
     // It calls the window procedure for the specified window and does not return 
     // until the window procedure has processed the message. 
     [DllImport("User32.dll")] 
     public static extern Int32 SendMessage(
      int hWnd,    // handle to destination window 
      int Msg,    // message 
      int wParam,    // first message parameter 
      [MarshalAs(UnmanagedType.LPStr)] string lParam); // second message parameter 

     [DllImport("User32.dll")] 
     public static extern Int32 SendMessage(
      int hWnd,    // handle to destination window 
      int Msg,    // message 
      int wParam,    // first message parameter 
      int lParam);   // second message parameter 
    } 
} 

例如:

Win32.SendMessage(iHandle, Win32.WM_LBUTTONDOWN, 0x00000001, 0x1E5025B); 

Here's My Application Source Code我創建自動點擊在 「藍疊」 應用程序在一個特定的時間間隔!

對於FindWindow,wParam,lParam等,你可以隨時問我該怎麼做!這不是太難:);) 希望它有幫助! :)

+0

看起來,鼠標點擊已發佈,未發送。 PostMessage將是一個更好的解決方案。至少Spy ++聲稱發佈了點擊。 – Tom 2014-09-25 09:46:46

+0

來到這裏試圖發送點擊BlueStacks,並沒有失望! – RW4 2015-02-05 01:10:49

+1

如何爲點擊提供座標?我需要點擊某個位置,而不是點擊未知的位置。 – Kosmos 2015-12-11 17:42:37

相關問題