none
请教,关于C#模拟键盘输入(SendInput) RRS feed

  • 问题

  • 我想用SendInput来模拟键盘输入,但是遇到了奇怪的问题

    这是一个WinForm应用程序,代码都在Form1中,我的VS版本是VS2008,系统是XP

    常量定义:

    Code Snippet
    public const int INPUT_KEYBOARD = 1;
    public const int KEYEVENTF_KEYUP = 0x0002;

     

     

    WinAPI声明:

    Code Snippet

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

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

            [StructLayout(LayoutKind.Sequential)]
            public struct MOUSEINPUT
            {
                public Int32 dx;
                public Int32 dy;
                public Int32 mouseData;
                public Int32 dwFlags;
                public Int32 time;
                public IntPtr dwExtraInfo;
            }
            [StructLayout(LayoutKind.Sequential)]
            public struct KEYBDINPUT
            {
                public Int16 wVk;
                public Int16 wScan;
                public Int32 dwFlags;
                public Int32 time;
                public IntPtr dwExtraInfo;
            }
            [StructLayout(LayoutKind.Sequential)]
            public struct HARDWAREINPUT
            {
                public Int32 uMsg;
                public Int16 wParamL;
                public Int16 wParamH;
            }

     

     

    这个窗体只有两个控件,textBox1 和 button1

    button1的事件Click:

    Code Snippet

    private void button1_Click(object sender, EventArgs e)
            {
                textBox1.Focus();
                INPUT inDown = new INPUT();
                inDown.type = INPUT_KEYBOARD;
                inDown.ki.wVk = (int)Keys.A;

                INPUT inUp = new INPUT();
                inDown.type = INPUT_KEYBOARD;
                inDown.ki.wVk = (int)Keys.A;
                inDown.ki.dwFlags = KEYEVENTF_KEYUP;

                Text = SendInput(1, ref  inDown, Marshal.SizeOf(inDown)).ToString();
            }

     

     

    就是这段橘红色的代码,如果注释掉,那么textBox1里就会写入一个a,但是一旦取消注释,就不行了。。。PS:该函数返回的结果是1,就是说是成功的。

    求高手指点,谢谢

    2008年7月10日 9:02

答案

  • 在你的代码中inUp被new出来之后再没用过,而inDown的ki.wVk赋值了2次。是不是你的代码的inDown,inUp的使用有些错误啊。

    2008年7月10日 11:23
    版主

全部回复

  • 请问你一定要用这种方法模拟吗?

    .NET中有一个类System.Windows.Forms.SendKeys,可以模拟键盘输入。

    textBox1.Focus();

    System.Windows.Forms.SendKeys("A");

    就行了

    2008年7月10日 9:55
    版主
  • 这种方式如何实现Win键的输入呢;

    实际上keybd_event这个函数也可以实现的,但是MSDN说这个函数以后要被抛弃

    2008年7月10日 10:02
  • 在你的代码中inUp被new出来之后再没用过,而inDown的ki.wVk赋值了2次。是不是你的代码的inDown,inUp的使用有些错误啊。

    2008年7月10日 11:23
    版主
  • 我错啦。。。

    原谅我吧。。这么低级的错误

    2008年7月10日 13:38
  • 我想用SendInput来模拟键盘输入,但是遇到了奇怪的问题

    这是一个WinForm应用程序,代码都在Form1中,我的VS版本是VS2008,系统是XP

    常量定义:

    Code Snippet
    public const int INPUT_KEYBOARD = 1;
    public const int KEYEVENTF_KEYUP = 0x0002;

     

     

    WinAPI声明:

    Code Snippet

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

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

            [StructLayout(LayoutKind.Sequential)]
            public struct MOUSEINPUT
            {
                public Int32 dx;
                public Int32 dy;
                public Int32 mouseData;
                public Int32 dwFlags;
                public Int32 time;
                public IntPtr dwExtraInfo;
            }
            [StructLayout(LayoutKind.Sequential)]
            public struct KEYBDINPUT
            {
                public Int16 wVk;
                public Int16 wScan;
                public Int32 dwFlags;
                public Int32 time;
                public IntPtr dwExtraInfo;
            }
            [StructLayout(LayoutKind.Sequential)]
            public struct HARDWAREINPUT
            {
                public Int32 uMsg;
                public Int16 wParamL;
                public Int16 wParamH;
            }

     

     

    这个窗体只有两个控件,textBox1 和 button1

    button1的事件Click:

    Code Snippet

    private void button1_Click(object sender, EventArgs e)
            {
                textBox1.Focus();
                INPUT inDown = new INPUT();
                inDown.type = INPUT_KEYBOARD;
                inDown.ki.wVk = (int)Keys.A;

                INPUT inUp = new INPUT();
                inDown.type = INPUT_KEYBOARD;
                inDown.ki.wVk = (int)Keys.A;
                inDown.ki.dwFlags = KEYEVENTF_KEYUP;

                Text = SendInput(1, ref  inDown, Marshal.SizeOf(inDown)).ToString();
            }

     

     

    就是这段橘红色的代码,如果注释掉,那么textBox1里就会写入一个a,但是一旦取消注释,就不行了。。。PS:该函数返回的结果是1,就是说是成功的。

    求高手指点,谢谢


    2017年1月2日 0:45