WPF .NET Core 6自动化项目:如何向其他进程发送按键?
问题描述
我正在开发一个基于WPF(.NET Core 6)的自动化项目,需要向系统中运行的另一个应用程序发送按键指令。程序启动后会通过后台工作线程循环监听预设按键,检测到按键按下时向目标进程发送指定按键。由于WPF项目限制,无法直接使用System.Windows.Forms及SendKeys.Send("{ENTER}")方法。
已尝试的两种方案均未成功:
- 使用InputManager:后台线程遇到
[STAThread]错误,解决后仍无法成功发送按键,相关代码如下:
public static void Send(Key key) { if (Keyboard.PrimaryDevice != null) { if (Keyboard.PrimaryDevice.ActiveSource != null) { var e = new KeyEventArgs(Keyboard.PrimaryDevice, Keyboard.PrimaryDevice.ActiveSource, 0, key) { RoutedEvent = Keyboard.KeyDownEvent }; InputManager.Current.ProcessInput(e); // Note: Based on your requirements you may also need to fire events for: // RoutedEvent = Keyboard.PreviewKeyDownEvent // RoutedEvent = Keyboard.KeyUpEvent // RoutedEvent = Keyboard.PreviewKeyUpEvent } } }
- 添加System.Windows.Forms引用:尝试引用后使用
SendKeys.SendWait,但Visual Studio无法识别该函数,手动添加引用也未生效。
请问是否存在无需复杂实现的方案,可在WPF .NET Core项目中替代SendKeys.Send的功能?
可行解决方案
1. 使用Windows API的SendInput函数
这是底层且可靠的系统级模拟方式,无需依赖WinForms,直接调用系统API实现按键发送。先导入相关API:
using System; using System.Runtime.InteropServices; public static class KeyboardSimulator { [StructLayout(LayoutKind.Sequential)] private struct INPUT { public uint Type; public InputUnion Data; } [StructLayout(LayoutKind.Explicit)] private struct InputUnion { [FieldOffset(0)] public MOUSEINPUT Mouse; [FieldOffset(0)] public KEYBDINPUT Keyboard; [FieldOffset(0)] public HARDWAREINPUT Hardware; } [StructLayout(LayoutKind.Sequential)] private struct KEYBDINPUT { public ushort Vk; public ushort Scan; public uint Flags; public uint Time; public IntPtr ExtraInfo; } private const uint INPUT_KEYBOARD = 1; private const uint KEYEVENTF_KEYUP = 0x0002; [DllImport("user32.dll", SetLastError = true)] private static extern uint SendInput(uint nInputs, INPUT[] pInputs, int cbSize); public static void SendKey(ushort virtualKeyCode) { // 模拟按键按下 INPUT downInput = new INPUT { Type = INPUT_KEYBOARD, Data = new InputUnion { Keyboard = new KEYBDINPUT { Vk = virtualKeyCode, Flags = 0 } } }; // 模拟按键松开 INPUT upInput = new INPUT { Type = INPUT_KEYBOARD, Data = new InputUnion { Keyboard = new KEYBDINPUT { Vk = virtualKeyCode, Flags = KEYEVENTF_KEYUP } } }; INPUT[] inputs = new INPUT[] { downInput, upInput }; SendInput((uint)inputs.Length, inputs, Marshal.SizeOf(typeof(INPUT))); } }
使用示例(发送回车键):
// VK_RETURN对应回车键的虚拟键码 KeyboardSimulator.SendKey(0x0D);
2. 使用NuGet包InputSimulator
这是封装了SendInput的开源库,使用更简洁,无需手动编写API导入代码:
- 安装NuGet包:在NuGet包管理器中搜索
InputSimulator并安装,或执行命令Install-Package InputSimulator - 使用示例:
using WindowsInput; var simulator = new InputSimulator(); // 发送回车键 simulator.Keyboard.KeyPress(WindowsInput.Native.VirtualKeyCode.RETURN); // 发送组合键(比如Ctrl+C) simulator.Keyboard.ModifiedKeyStroke(WindowsInput.Native.VirtualKeyCode.CONTROL, WindowsInput.Native.VirtualKeyCode.VK_C);
3. 正确引用System.Windows.Forms使用SendKeys
如果坚持使用SendKeys,需在.NET Core WPF项目中完成以下配置:
- 右键项目→管理NuGet包,安装
System.Windows.Forms包 - 编辑项目文件(.csproj),添加配置:
<PropertyGroup> <UseWindowsForms>true</UseWindowsForms> </PropertyGroup>
- 使用时需确保在STA线程调用(可通过
Dispatcher切换到UI线程):
using System.Windows.Forms; // 发送回车键 SendKeys.SendWait("{ENTER}");
内容的提问来源于stack exchange,提问作者BasicallyDaniel
相关产品推荐
相关产品推荐

