我想通过SendInput API发送一些密钥

时间:2012-01-12 12:31:09

标签: c# windows winapi

我想通过C#上的SendInput API向游戏发送一些键。 (我的环境是Windows 7 64位)

我写了一些代码如下:

   [DllImport("user32.dll")]
   static extern int SendInput(int nInputs, INPUT[] pInputs, int cbSize);       

    [StructLayout(LayoutKind.Sequential)]
    private struct MOUSEINPUT
    {
        public int dx;
        public int dy;
        public uint mouseData;
        public uint dwFlags;
        public uint time;
        public IntPtr dwExtraInfo;
    }

    [StructLayout(LayoutKind.Sequential)]
    private struct KEYBDINPUT
    {
        public short wVk;
        public short wScan;
        public int dwFlags;
        public int time;            
        public IntPtr dwExtraInfo;
    }

    [StructLayout(LayoutKind.Sequential)]
    private struct HARDWAREINPUT
    {
        public uint uMsg;
        public ushort wParamL;
        public ushort wParamH;
    }

    [StructLayout(LayoutKind.Explicit)]
    private struct INPUT
    {
        [FieldOffset(0)]
        public uint type;
        [FieldOffset(4)]
        public MOUSEINPUT mi;
        [FieldOffset(4)]
        public KEYBDINPUT ki;
        [FieldOffset(4)]
        public HARDWAREINPUT hi;
    }        

    public static void WalkFront()
    {
        INPUT[] inputs = new INPUT[1];

        Keys virtualKeycode = (Keys)0x15;            

        inputs[0].type = INPUT_KEYBOARD;            
        inputs[0].ki.wVk = (short)virtualKeycode;
        inputs[0].ki.wScan = (short)MapVirtualKey((int)virtualKeycode, 0);            
        inputs[0].ki.dwFlags = KEYEVENTF_SCANCODE;            
        inputs[0].ki.time = 0;
        inputs[0].ki.dwExtraInfo = GetMessageExtraInfo();

        SendInput(1, inputs, Marshal.SizeOf(inputs[0]));        
    }

[DllImport("user32.dll")] static extern int SendInput(int nInputs, INPUT[] pInputs, int cbSize); [StructLayout(LayoutKind.Sequential)] private struct MOUSEINPUT { public int dx; public int dy; public uint mouseData; public uint dwFlags; public uint time; public IntPtr dwExtraInfo; } [StructLayout(LayoutKind.Sequential)] private struct KEYBDINPUT { public short wVk; public short wScan; public int dwFlags; public int time; public IntPtr dwExtraInfo; } [StructLayout(LayoutKind.Sequential)] private struct HARDWAREINPUT { public uint uMsg; public ushort wParamL; public ushort wParamH; } [StructLayout(LayoutKind.Explicit)] private struct INPUT { [FieldOffset(0)] public uint type; [FieldOffset(4)] public MOUSEINPUT mi; [FieldOffset(4)] public KEYBDINPUT ki; [FieldOffset(4)] public HARDWAREINPUT hi; } public static void WalkFront() { INPUT[] inputs = new INPUT[1]; Keys virtualKeycode = (Keys)0x15; inputs[0].type = INPUT_KEYBOARD; inputs[0].ki.wVk = (short)virtualKeycode; inputs[0].ki.wScan = (short)MapVirtualKey((int)virtualKeycode, 0); inputs[0].ki.dwFlags = KEYEVENTF_SCANCODE; inputs[0].ki.time = 0; inputs[0].ki.dwExtraInfo = GetMessageExtraInfo(); SendInput(1, inputs, Marshal.SizeOf(inputs[0])); }

但是它无法正常工作。

显然,此代码可以向游戏发送 BackSpace 。实际上,此代码可以删除Notepad.exe上的字符。

奇怪的是,此代码仅向应用程序发送 BackSpace 。我在这段代码中更改了密码(我试过0x14,0x13,0x12 ......等)。 但是,此代码仅发送BackSpace

我想向应用程序发送另一个密钥(J,K,L ......等),但我不能。

有什么建议吗? 感谢

1 个答案:

答案 0 :(得分:3)

请记住,按键事件包括按键事件和之后的按键事件。这意味着发送退格"你需要调用SendInput两次,一次按下键,一次释放键。 如果您在释放密钥时无法调用SendInput,则大多数应用程序很可能会忽略后续按键操作。