SHIFT快捷方式显示为文化“nl-BE”的MAJ,它应该是SHIFT(C#.NET)

前端之家收集整理的这篇文章主要介绍了SHIFT快捷方式显示为文化“nl-BE”的MAJ,它应该是SHIFT(C#.NET)前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
经过与Infragistics的长时间讨论后,看来带有SHIFT的ShortCuts在我的文化“nl-BE”中显示为MAJ.首先,文化“nl-BE”和AZERTY有点奇怪.如果想了解更多,请阅读 http://en.wikipedia.org/wiki/AZERTY.重要的是:

The other keys are identical,even though traditionally the names of
special keys are printed on them in English. This is because Belgium
is predominantly bilingual (French-Dutch) and officially trilingual (a
third language,German,is spoken in the East Cantons).

所以MAJ印刷为SHIFT.例如,在Office中,带有SHIFT的快捷方式显示为SHIFT.在Infragistics控件中,它们显示为MAJ.这让我们的客户感到沮丧.

因此,在与Infragistics讨论后,他们声称这是一个Windows Api调用,它返回MAJ而不是SHIFT.我从他们那里得到了一个展示行为的示例项目.所以现在我的问题是为什么Windows Api调用不会返回SHIFT,如果它是正常的,那么Office如何才能正确显示它?

获取密钥文本的代码是:

  1. NativeWindowMethods.GetKeyNameText((int)scanCode,sb,256);

  1. class NativeWindowMethods
  2. {
  3. #region MapVirtualKey
  4. [DllImport("user32.dll")]
  5. internal static extern int MapVirtualKey(uint uCode,uint uMapType);
  6. #endregion //MapVirtualKey
  7.  
  8. #region GetKeyNameText
  9. [DllImport("user32.dll",CharSet = CharSet.Auto)]
  10. internal static extern int GetKeyNameText(
  11. int lParam,[MarshalAs(UnmanagedType.LPWStr),Out]System.Text.StringBuilder str,int size);
  12. #endregion //GetKeyNameText
  13. }

如果是Shiftkey,则扫描码为2752512(2a),并返回MAJ.

那么,我的问题是什么?

>为了“nl-BE”文化而归还MAJ是否正常?或者它是user32.dll中的错误
>如果Office能够做到正确,那么Infragistics是否也能做到正确呢?
> Infragistics是否使用正确的user32.dll api调用

为了完整性,我将粘贴Utilities类的完整代码.从Form下一次调用完成:

systemLocalizedString = Utilities.GetLocalizedShortcutString(shortcut);

使用快捷键= ShiftF12.调用后,systemLocalizedString等于“MAJ F12”.

更新:在Hans Passant的帮助下,我下载了Microsoft Keyboard Layout Creator并导出了我当前的键盘布局.在.klc文件中没有找到MAJ,只有Shift(例如2a Shift).那么为什么user32.dll会返回MAJ?甚至更奇怪的是,当我复制.klc文件并将其安装为新键盘时,突然user32.dll确实为新安装的键盘返回Shift(虽然它是一个精确的副本).

Utilities.cs:

  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Windows.Forms;
  6. using System.Runtime.InteropServices;
  7.  
  8. namespace WindowsFormsApplication1
  9. {
  10. class Utilities
  11. {
  12.  
  13. #region GetLocalizedShortcutString
  14.  
  15. /// <summary>
  16. /// Returns the localized string for the specified <b>Shortcut</b>
  17. /// </summary>
  18. /// <param name="shortcut">Shortcut to localize</param>
  19. /// <param name="separator">Character used to separate multiple keys in the shortcut</param>
  20. /// <returns>A string containing the localized description of the shortcut based on the currently mapped keyboard layout</returns>
  21. public static string GetLocalizedShortcutString(Shortcut shortcut,char separator = '+')
  22. {
  23. if (shortcut == Shortcut.None)
  24. return string.Empty;
  25.  
  26. return GetLocalizedKeyString((Keys)shortcut,separator);
  27. }
  28. #endregion //GetLocalizedShortcutString
  29.  
  30. #region GetLocalizedKeyString
  31.  
  32. /// <summary>
  33. /// Returns the localized string for the specified <b>Keys</b>
  34. /// </summary>
  35. /// <param name="keys">Keys to localize</param>
  36. /// <param name="separator">Character used to separate multiple keys</param>
  37. /// <returns>A string containing the localized description of the keys based on the currently mapped keyboard layout</returns>
  38. public static string GetLocalizedKeyString(Keys keys,char separator)
  39. {
  40. bool alt = ((long)keys & (long)Keys.Alt) != 0;
  41. bool ctrl = ((long)keys & (long)Keys.Control) != 0;
  42. bool shift = ((long)keys & (long)Keys.Shift) != 0;
  43.  
  44. // get the key involved
  45. long value = (long)keys & 0xffff;
  46.  
  47. Keys key = (Keys)Enum.ToObject(typeof(Keys),value);
  48. System.Text.StringBuilder sb = new System.Text.StringBuilder();
  49.  
  50. if (alt && key != Keys.Menu)
  51. {
  52. sb.Append(GetLocalizedKeyStringHelper(Keys.Menu));
  53. sb.Append(separator);
  54. }
  55.  
  56. if (ctrl && key != Keys.ControlKey)
  57. {
  58. sb.Append(GetLocalizedKeyStringHelper(Keys.ControlKey));
  59. sb.Append(separator);
  60. }
  61.  
  62. if (shift && key != Keys.ShiftKey)
  63. {
  64. sb.Append(GetLocalizedKeyStringHelper(Keys.ShiftKey));
  65. sb.Append(separator);
  66. }
  67.  
  68. sb.Append(GetLocalizedKeyStringHelper(key));
  69. return sb.ToString();
  70. }
  71. #endregion //GetLocalizedKeyString
  72.  
  73. #region GetLocalizedKeyStringHelper
  74. private static string GetLocalizedKeyStringHelper(Keys key)
  75. {
  76. string localizedKey = GetLocalizedKeyStringUnsafe(key);
  77.  
  78. if (localizedKey == null || localizedKey.Length == 0)
  79. return key.ToString();
  80.  
  81. return localizedKey;
  82. }
  83. #endregion //GetLocalizedKeyStringHelper
  84.  
  85. #region GetLocalizedKeyStringUnsafe
  86. private static string GetLocalizedKeyStringUnsafe(Keys key)
  87. {
  88. // strip any modifier keys
  89. long keyCode = ((int)key) & 0xffff;
  90.  
  91. System.Text.StringBuilder sb = new System.Text.StringBuilder(256);
  92.  
  93. long scanCode = NativeWindowMethods.MapVirtualKey((uint)keyCode,(uint)0);
  94.  
  95. // shift the scancode to the high word
  96. scanCode = (scanCode << 16);
  97.  
  98. if (keyCode == 45 ||
  99. keyCode == 46 ||
  100. keyCode == 144 ||
  101. (33 <= keyCode && keyCode <= 40))
  102. {
  103. // add the extended key flag
  104. scanCode |= 0x1000000;
  105. }
  106.  
  107. NativeWindowMethods.GetKeyNameText((int)scanCode,256);
  108. return sb.ToString();
  109. }
  110. #endregion //GetLocalizedKeyStringUnsafe
  111. }
  112.  
  113. class NativeWindowMethods
  114. {
  115. #region MapVirtualKey
  116. [DllImport("user32.dll")]
  117. internal static extern int MapVirtualKey(uint uCode,uint uMapType);
  118. #endregion //MapVirtualKey
  119.  
  120. #region GetKeyNameText
  121. [DllImport("user32.dll",CharSet = CharSet.Auto)]
  122. internal static extern int GetKeyNameText(int lParam,int size);
  123. #endregion //GetKeyNameText
  124. }
  125. }

解决方法

but even I am using AZERTY,that’s what is used in schools to learn how to type so…

是的,这就是问题所在.获得AZERTY布局的唯一方法是在控制面板语言中选择标题为“français(Belgique)”的键盘布局添加语言.与“Nederlands(België)”布局相反,它有QWERTY安排. GetKeyNameText()winapi函数返回在键盘布局文件中编码的字符串.对于名为français的键盘布局,法语当然是法语,因此MAJ是预期的结果. Windows没有提供带有AZERTY排列的荷兰语的键盘布局.

一切都没有丢失,Windows用户经常要求自定义键盘布局.所以微软开发了一个工具来创建你自己的Microsoft Keyboard Layout Creator.它主要用于重新安排按键,需要一点额外的肘部油脂才能让它做你想要的.该工具不允许您直接编辑密钥描述并默认使用英文名称.您将要从文件加载现有键盘开始.然后文件保存布局将布局保存到.klc文件.在文本编辑器中打开它,记事本很好,找到名为KEYNAME和KEYNAME_EXT的部分,并按照您希望的方式编辑键名.

重新启动该实用程序(不要跳过)并重新加载.klc文件.并使用Project Build DLL构建安装程序包.

猜你在找的C#相关文章