使用SendKeys.SendWait()与Electron交互:如何设置DOM3键盘事件code属性?
解决Electron游戏键盘自动化中DOM事件code属性为空的问题
问题核心
用C#的SendKeys.SendWait("a")给Electron游戏模拟按键时,虽然DOM事件触发了,但事件的code属性是空字符串,游戏因为校验这个属性直接忽略了输入;而物理键盘按"A"时,code会被正确设为KeyA,游戏能正常响应。这是因为SendKeys是高层API,生成的事件缺少硬件级的扫描码数据,Chromium(Electron基于它)无法据此填充code字段。
可行方案:用Win32 API的SendInput模拟硬件级按键
SendInput能生成更接近物理键盘的输入事件,关键是要设置扫描码和KEYEVENTF_SCANCODE标志,让Chromium识别并填充正确的code属性。
实现步骤
- 导入Win32 API的结构体和函数定义:
using System; using System.Runtime.InteropServices; public class HardwareKeyboardSimulator { [StructLayout(LayoutKind.Sequential)] private struct INPUT { public uint Type; public INPUTUNION Data; } [StructLayout(LayoutKind.Explicit)] private struct INPUTUNION { [FieldOffset(0)] public KEYBDINPUT Keyboard; } [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_SCANCODE = 0x0008; 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 PressKey(ushort scanCode) { INPUT downEvent = new INPUT { Type = INPUT_KEYBOARD, Data = new INPUTUNION { Keyboard = new KEYBDINPUT { Scan = scanCode, Flags = KEYEVENTF_SCANCODE } } }; INPUT upEvent = new INPUT { Type = INPUT_KEYBOARD, Data = new INPUTUNION { Keyboard = new KEYBDINPUT { Scan = scanCode, Flags = KEYEVENTF_SCANCODE | KEYEVENTF_KEYUP } } }; INPUT[] events = new[] { downEvent, upEvent }; SendInput((uint)events.Length, events, Marshal.SizeOf(typeof(INPUT))); } }
- 调用方法模拟按键
比如模拟"A"键,直接传入它的扫描码0x1E:
// 触发A键对应的游戏技能 HardwareKeyboardSimulator.PressKey(0x1E);
扫描码获取
常用按键的扫描码可以查标准键盘扫描码表,或者用Win32的MapVirtualKey函数转换虚拟键码得到:
- A: 0x1E
- S: 0x1F
- D: 0x20
- W: 0x11
注意事项
- 如果游戏以管理员权限运行,你的C#程序也必须用管理员权限启动,否则
SendInput可能无法生效。 - 部分游戏有反作弊机制,可能会拦截模拟输入,这种情况下需要进一步调整(比如使用驱动级模拟,但难度更高)。
- Chromium会给
SendInput生成的事件设isTrusted=true,能避开大部分基于该属性的校验。
内容的提问来源于stack exchange,提问作者ben_makes_stuff
相关产品推荐
相关产品推荐

