使用C#在另一个应用程序上执行鼠标Click事件 [英] Perform a mouse Click event on another Application using C#
问题描述
我需要做的是使用我的自定义应用程序来控制安装在同一台计算机上的另一个应用程序.例如,如果我需要使用标准的Windows计算器,则只需将输入事件发送到计算器.我使用了一些代码片段来实现这一点,现在我已经触发了鼠标和键盘事件.但是问题是我可以确定键盘事件会击中目标应用程序,因为它具有进程句柄.但是我不确定鼠标.而且,如果目标应用程序进入后台,则无法启动鼠标单击.我需要帮助,以找到一种确保仅在应用程序上单击鼠标的方法.
what i need to do is that I need to control another application installed on the same machine using my custom application. For example if i needed to use the standard windows calculator I would simply send the input events to the calculator. I have used some code snippets to make this possible and I have now triggered both mouse and keyboard events. but the problem is that i can be sure that the keyboard event will hit the target application because it has the process handle. but i cannot be sure about the mouse. and also if the target application goes into background, i cannot initiate mouse clicks on it. I need help to find a way to make sure that the mouse click is done on the application only.
我需要发送鼠标坐标并单击.例如"sendMouseClick("Notepad", 100, 400);
,即使它保持最小化,它也会将单击发送到记事本.
I need to send mouse co-ordinates and click as well. for example "sendMouseClick("Notepad", 100, 400);
which will send a click to Notepad, even though it stays minimized.
*************************************************** ****** 重要的提示****************************************** *********** 之前已经回答了一个类似的问题,但这是指首先找到另一个应用程序的状态,然后将输入发送给键盘或鼠标,我需要做的是向应用程序发送一组指令,无论该应用程序是否有效是否在前台. 对于其他人" ::如果您不想提供帮助或不能提供帮助,那没关系,但是请务必知道我还没有偷到问题或任何东西.我只想在C#中完成此任务.
***************************************************** IMPORTANT NOTE***************************************************** A similar question is answered previously but that is in reference to first finding the state of the other application and then sending the inputs either keyboard or mouse, what i need to do is to send an application a set of instructions that must work whether the application is in foreground or not. For "The other Guys":: if you dont want to help or cant help, thats okay but please do know that i havent stolen the question or anything. I simply want to achieve this task in C#.
我要模拟键盘按键的代码是:
The code I have to simulate keyboard key Press is:
using System;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.Drawing;
using System.Windows.Forms;
namespace SimulateKeyPress
{
partial class Form1 : Form
{
private Button button1 = new Button();
private Button button2 = new Button();
private Button button3 = new Button();
[STAThread]
public static void Main()
{
Application.EnableVisualStyles();
Application.Run(new Form1());
}
public Form1()
{
button1.Location = new Point(10, 10);
button1.TabIndex = 1;
button1.Text = "Click to automate Calculator";
button1.AutoSize = true;
button1.Click += new EventHandler(button1_Click);
button2.Location = new Point(150, 140);
button2.TabIndex = 0;
button2.Text = "Click to Exit Calculator";
button2.AutoSize = true;
button2.Location = new Point(80, 80);
button2.TabIndex = 2;
button2.Text = "Click to Run Calculator";
button2.AutoSize = true;
button2.Click += new EventHandler(button2_Click);
this.DoubleClick += new EventHandler(Form1_DoubleClick);
this.Controls.Add(button1);
this.Controls.Add(button2);
// this.Controls.Add(button3);
}
// Get a handle to an application window.
[DllImport("USER32.DLL", CharSet = CharSet.Unicode)]
public static extern IntPtr FindWindow(string lpClassName,
string lpWindowName);
// Activate an application window.
[DllImport("USER32.DLL")]
public static extern bool SetForegroundWindow(IntPtr hWnd);
// Send a series of key presses to the Calculator application.
private void button1_Click(object sender, EventArgs e)
{
// Get a handle to the Calculator application. The window class
// and window name were obtained using the Spy++ tool.
IntPtr calculatorHandle = FindWindow("CalcFrame", "Calculator");
//Process firstProc = new Process();
//firstProc.StartInfo.FileName = "calc.exe";
//firstProc.EnableRaisingEvents = true;
//firstProc.Start();
// Verify that Calculator is a running process.
if (calculatorHandle == IntPtr.Zero)
{
MessageBox.Show("Calculator is not running.");
return;
}
// Make Calculator the foreground application and send it
// a set of calculations.
SetForegroundWindow(calculatorHandle);
SendKeys.SendWait("1024");
SendKeys.SendWait("*");
SendKeys.SendWait("32");
SendKeys.SendWait("=");
}
private void button2_Click(object sender, EventArgs e)
{
System.Diagnostics.Process.Start("calc.exe");
}
private void button3_Click(object sender,EventArgs e)
{
Process [] proc =Process.GetProcessesByName("Calculator");
proc[0].Kill();
}
// Send a key to the button when the user double-clicks anywhere
// on the form.
private void Form1_DoubleClick(object sender, EventArgs e)
{
// Send the enter key to the button, which raises the click
// event for the button. This works because the tab stop of
// the button is 0.
SendKeys.Send("{ENTER}");
}
}
}
有关堆栈溢出,msdn和其他站点的先前帮助提供了用于在同一应用程序中模拟鼠标单击的代码.但是我需要将鼠标点击发送到另一个应用程序.
the previous help on stack overflow, msdn and other sites provides the code to simulate a mouse click in the same application. But i need to send mouse hits to another application.
推荐答案
也许可以帮助您
任务
- 获取鼠标的当前位置
- 发送鼠标事件
...
using System.Runtime.InteropServices;
namespace yournamespace
{
public partial class yourclassname
{
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
public static extern void mouse_event(uint dwFlags, uint dx, uint dy, uint cButtons, uint dwExtraInfo);
private const int MOUSEEVENTF_LEFTDOWN = 0x02;
private const int MOUSEEVENTF_LEFTUP = 0x04;
private const int MOUSEEVENTF_RIGHTDOWN = 0x08;
private const int MOUSEEVENTF_RIGHTUP = 0x10;
int X = Cursor.Position.X;
int Y = Cursor.Position.Y;
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, X, Y, 0, 0);
}
}
WPF
在WPF中,事情有些困难
WPF
Things are a bit harder in WPF
double mousePointX;
double mousePointY;
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetCursorPos(out POINT lpPoint);
[StructLayout(LayoutKind.Sequential)]
public struct POINT
{
public int X;
public int Y;
public POINT(int x, int y)
{
this.X = x;
this.Y = y;
}
}
private void WritePoint(object sender, RoutedEventArgs e)
{
POINT p;
if (GetCursorPos(out p))
{
System.Console.WriteLine(Convert.ToString(p.X) + ";" + Convert.ToString(p.Y));
}
}
[DllImport("User32.dll")]
static extern IntPtr GetDC(IntPtr hwnd);
[DllImport("gdi32.dll")]
static extern int GetDeviceCaps(IntPtr hdc, int nIndex);
[DllImport("user32.dll")]
static extern bool ReleaseDC(IntPtr hWnd, IntPtr hDC);
private Point ConvertPixelsToUnits(int x, int y)
{
// get the system DPI
IntPtr dDC = GetDC(IntPtr.Zero); // Get desktop DC
int dpi = GetDeviceCaps(dDC, 88);
bool rv = ReleaseDC(IntPtr.Zero, dDC);
// WPF's physical unit size is calculated by taking the
// "Device-Independant Unit Size" (always 1/96)
// and scaling it by the system DPI
double physicalUnitSize = (1d / 96d) * (double)dpi;
Point wpfUnits = new Point(physicalUnitSize * (double)x,
physicalUnitSize * (double)y);
return wpfUnits;
}
private void WriteMouseCoordinatesInWPFUnits()
{
POINT p;
if (GetCursorPos(out p))
{
Point wpfPoint = ConvertPixelsToUnits(p.X, p.Y);
System.Console.WriteLine(Convert.ToString(wpfPoint.X) + ";" + Convert.ToString(wpfPoint.Y));
mousePointY = wpfPoint.Y;
mousePointX = wpfPoint.X
}
}
现在是代码中最重要的部分
Now the most important part of the code
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
public static extern void mouse_event(uint dwFlags, uint dx, uint dy, uint cButtons, uint dwExtraInfo);
private const int MOUSEEVENTF_LEFTDOWN = 0x02;
private const int MOUSEEVENTF_LEFTUP = 0x04;
private const int MOUSEEVENTF_RIGHTDOWN = 0x08;
private const int MOUSEEVENTF_RIGHTUP = 0x10;
...
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, Convert.ToUInt32(mousePointX), Convert.ToUInt32(mousePointY), 0, 0);
...
警告
- 代码已通过测试
- 该代码不是复制并粘贴代码"
- The code is tested
- The code is not a "copy & paste code
Warning
这篇关于使用C#在另一个应用程序上执行鼠标Click事件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!