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

C#如何将虚拟键码转换为char?

如何解决《C#如何将虚拟键码转换为char?》经验,为你挑选了4个好方法。

我正在尝试将虚拟键码映射到char.

我的代码使用ProcessCmdKey来监听WM_KEYDOWN,这使我可以访问按下的键.例如,当我按单引号时,我得到一个222的密钥,我希望它映射到keychar 39代表...你猜对了......单引号.

我的开发上下文是: - .net Framework 2.0 - UserControl放置在很多地方

你知道问题的答案吗?



1> Powerlord..:

这不是System.Windows.Form.KeysConverter类的用途吗?

KeysConverter kc = new KeysConverter();
string keyChar = kc.ConvertToString(keyData);


刚注意到我从来没有回复过...... [KeysConverter存在于.NET 2.0中](http://msdn.microsoft.com/en-us/library/system.windows.forms.keysconverter%28v=vs.80%29的.aspx).
嗯,但这只是部分工作.作为一个不起作用的例子:`(new KeysConverter()).ConvertToString(Keys.OemQuestion)`*(**Spoiler:**它会返回`OemQuestion`而不是`?`)*.此外,还不清楚如何处理*Shift*键.有工作的解决方案吗?

2> Horas..:

是的,我确实使用过该MapVirtualKey方法.但我期待有关如何使用它的更多细节:使用什么DllImport指令,enum映射到字符的具体内容等.

我不喜欢这些答案,你谷歌5秒,然后只是建议一个解决方案:真正的挑战是把所有的部分放在一起,而不必浪费你的时间与大量的无样本MSDN页面或其他编码论坛为了得到你的答案.没有冒犯的基础,但是你的回答(甚至是好的)是无法解决的,因为我甚至在论坛上发布我的问题之前就得到了这个答案!

所以,你去,我将发布我正在寻找的 - 一个开箱即用的C#解决方案:

1-将此指令放在您的类中:

[DllImport("user32.dll")]
static extern int MapVirtualKey(uint uCode, uint uMapType);

2-检索你的char这样:

  protected override bool ProcessCmdKey(ref Message msg, Keys keyData)      
  {
     const int WM_KEYDOWN = 0x100;

     if (msg.Msg == WM_KEYDOWN)
     {            
        // 2 is used to translate into an unshifted character value 
        int nonVirtualKey = MapVirtualKey((uint)keyData, 2);

        char mappedChar = Convert.ToChar(nonVirtualKey);
     }

     return base.ProcessCmdKey(ref msg, keyData);
  }

感谢关心...并享受!



3> 小智..:

我正在寻找类似的东西,但我需要将字符映射到当前的键盘布局.由于上述答案都没有满足我的要求,这就是我想出的.

        public string KeyCodeToUnicode(Keys key)
        {
            byte[] keyboardState = new byte[255];
            bool keyboardStateStatus = GetKeyboardState(keyboardState);

            if (!keyboardStateStatus)
            {
                return "";
            }

            uint virtualKeyCode = (uint)key;
            uint scanCode = MapVirtualKey(virtualKeyCode, 0);
            IntPtr inputLocaleIdentifier = GetKeyboardLayout(0);

            StringBuilder result = new StringBuilder();
            ToUnicodeEx(virtualKeyCode, scanCode, keyboardState, result, (int)5, (uint)0, inputLocaleIdentifier);

            return result.ToString();
        }

        [DllImport("user32.dll")]
        static extern bool GetKeyboardState(byte[] lpKeyState);

        [DllImport("user32.dll")]
        static extern uint MapVirtualKey(uint uCode, uint uMapType);

        [DllImport("user32.dll")]
        static extern IntPtr GetKeyboardLayout(uint idThread);

        [DllImport("user32.dll")]
        static extern int ToUnicodeEx(uint wVirtKey, uint wScanCode, byte[] lpKeyState, [Out, MarshalAs(UnmanagedType.LPWStr)] StringBuilder pwszBuff, int cchBuff, uint wFlags, IntPtr dwhkl);


我们需要的英雄,但不是我们应得的英雄!

4> SongWithoutW..:

在阅读并测试了所提供的一些答案之后,我想我会建议一个替代方案.

如MM所述,System.Windows.KeysConverter不提供键的字符表示,而是提供枚举的名称,例如"Enter"而不是'\n'.

Horas建议的MapVirtualKey方法在回答他自己的问题时是一个很好的起点,但仍然不支持大写,或者用shift键输入的字符,例如'!','$'和'>'.

我正在使用的MapVirtualKey方法的替代方法是Keys类的扩展方法:

public static char ToChar(this Keys key)
{
    char c = '\0';
    if((key >= Keys.A) && (key <= Keys.Z))
    {
        c = (char)((int)'a' + (int)(key - Keys.A));
    }

    else if((key >= Keys.D0) && (key <= Keys.D9))
    {
        c = (char)((int)'0' + (int)(key - Keys.D0));
    }

    return c;
}

上面显示的方法将提供对字母数字字符的支持.可以使用switch语句或查找表来实现对其他字符的支持.

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