当前位置:  开发笔记 > 编程语言 > 正文

用C#更改按下的键

如何解决《用C#更改按下的键》经验,为你挑选了1个好方法。

嘿,我正在尝试用C#编写一个程序来跟踪某些键的按下(使用键盘钩子),然后发送不同的键.

例如,当我按下A键时,它将发送Q键.

我使用http://www.codeproject.com/KB/cs/CSLLKeyboardHook.aspx这个用于我的钩子并试图使用SendKeys函数,但是我得到一个关于垃圾收集器的例外,它破坏了钩子类中的一些对象.



1> BrunoLM..:

首先,您需要连接键.

使用此类,您可以注册一个全局快捷方式,我正在跳过解释,但您可以在此处阅读.

public class KeyboardHook
{
    [DllImport("user32.dll")]
    private static extern bool RegisterHotKey(IntPtr hWnd, int id, int fsModifiers, int vk);

    [DllImport("user32.dll")]
    private static extern bool UnregisterHotKey(IntPtr hWnd, int id);

    public enum Modifiers
    {
        None = 0x0000,
        Alt = 0x0001,
        Control = 0x0002,
        Shift = 0x0004,
        Win = 0x0008
    }

    int modifier;
    int key;
    IntPtr hWnd;
    int id;

    public KeyboardHook(int modifiers, Keys key, Form f)
    {
        this.modifier = modifiers;
        this.key = (int)key;
        this.hWnd = f.Handle;
        id = this.GetHashCode();
    }

    public override int GetHashCode()
    {
        return modifier ^ key ^ hWnd.ToInt32();
    }


    public bool Register()
    {
        return RegisterHotKey(hWnd, id, modifier, key);
    }
    public bool Unregister()
    {
        return UnregisterHotKey(hWnd, id);
    }
}

然后在您的表单上,您必须注册快捷方式

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        KeyboardHook hook = new KeyboardHook((int)KeyboardHook.Modifiers.None, Keys.A, this);

        hook.Register(); // registering globally that A will call a method
    }

    protected override void WndProc(ref Message m)
    {
        if (m.Msg == 0x0312)
            HandleHotkey(); // A, which was registered before, was pressed
        base.WndProc(ref m);
    }

    private void HandleHotkey()
    {
        // instead of A send Q
        KeyboardManager.PressKey(Keys.Q);
    }
}

这里是管理Keyboard新闻发布活动的课程.

public class KeyboardManager
{
    public const int INPUT_KEYBOARD = 1;
    public const int KEYEVENTF_KEYUP = 0x0002;

    public struct KEYDBINPUT
    {
        public Int16 wVk;
        public Int16 wScan;
        public Int32 dwFlags;
        public Int32 time;
        public Int32 dwExtraInfo;
        public Int32 __filler1;
        public Int32 __filler2;
    }

    public struct INPUT
    {
        public Int32 type;
        public KEYDBINPUT ki;
    }

    [DllImport("user32")]
    public static extern int SendInput(int cInputs, ref INPUT pInputs, int cbSize);

    public static void HoldKey(Keys vk)
    {
        INPUT input = new INPUT();
        input.type = INPUT_KEYBOARD;
        input.ki.dwFlags = 0;
        input.ki.wVk = (Int16)vk;
        SendInput(1, ref input, Marshal.SizeOf(input));
    }

    public static void ReleaseKey(Keys vk)
    {
        INPUT input = new INPUT();
        input.type = INPUT_KEYBOARD;
        input.ki.dwFlags = KEYEVENTF_KEYUP;
        input.ki.wVk = (Int16)vk;
        SendInput(1, ref input, Marshal.SizeOf(input));
    }

    public static void PressKey(Keys vk)
    {
        HoldKey(vk);
        ReleaseKey(vk);
    }
}

我已经在我正在写的textarea上测试了它,当我按下A它发送时Q.

我不确定魔兽争霸III会有什么行为,也许他们已经封锁了以防止某种机器人或什么......

推荐阅读
贾志军
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有