【发布时间】:2017-01-22 07:05:02
【问题描述】:
我编写了一个函数来处理用户键盘以便在应用程序中写入文本。
为了做到这一点,我使用了 ToUnicodeEx 函数,该函数使用一组键状态。 该功能对于每个可能的输入都可以正常工作,除了一个:我无法显示“>”符号,它应该是“SHIFT +
是否有人已经经历过同样的事情并且知道问题出在哪里?
你会在下面找到我的功能代码:
void MyFunction(bool bCapsLockDown)
{
IOClass io = GetMyIOInstance();
HKL layout = GetKeyboardLayout( 0 );
uchar uKeyboardState[256];
WCHAR oBuffer[5] = {};
//Initialization of KeyBoardState
for (uint i = 0; i < 256; ++i)
{
uKeyBoardState[i] = 0;
}
// Use of my ConsultKeyState to get the status of pressed keys
if ( ConsultKeyState( VK_SHIFT ) || bCapsLockDown )
{
uKeyboardState[VK_CAPITAL] = 0xff;
}
if ( ConsultKeyState( VK_CONTROL ) )
{
uKeyboardState[VK_CONTROL] = 0xff;
}
if ( ConsultKeyState( VK_MENU ) )
{
uKeyboardState[VK_MENU] = 0xff;
}
if ( ConsultKeyState( VK_RMENU ) )
{
uKeyboardState[VK_MENU] = 0xff;
uKeyboardState[VK_CONTROL] = 0xff;
}
for ( uint iVK = 0; iVK < 256; ++iVK )
{
bool bKeyDown = ConsultKeyState( iVK ) != 0;
uint iSC = MapVirtualKeyEx( iVK, MAPVK_VK_TO_VSC, layout );
bool bKeyAlreadyDown = io.KeysDown[iVK];
io.KeysDown[iVK] = bKeyDown;
if ( io.KeysDown[iVK] && bKeyAlreadyDown == false )
{
int iRet = ToUnicodeEx( iVK, iSC, uKeyboardState, (LPWSTR)oBuffer, 4, 0, layout );
if( iRet > 0 && (iswgraph( (unsigned short) oBuffer[0] ) || oBuffer[0] == ' ') )
io.AddInputCharacter( (unsigned short) oBuffer[0] );
}
}
}
编辑: 总而言之,我的问题是: 显示“>”的 VirtualKey + KeyBoardState 的最佳组合是什么?
【问题讨论】:
-
@HansPassant “MAJ”信息包含在 uKeyBoardState 中! ToUnicodeEx 使用它来知道是否按下了其他键,如 MAJ、ALT、CTRL...
-
最好避免在英文网站上使用法语,我们在这里说“shift”。 GetKeyboardState() 很奇怪,您将检索自己进程的缓冲键盘状态。如果您不以其他方式发送消息循环,则它永远不会更新。看起来您通过使用 GetAsyncKeyState() 解决了该问题,但这也不正确,因为这不一定与您尝试戳的进程的键盘状态相匹配。使用 UI 自动化总是最好的解决这样的麻烦。
-
对 Shift 感到抱歉,马上编辑
-
@HansPassant 你是说使用 GetAsyncKeyState 我可能正在检索不适合应用程序的输入吗?否则如何获取更新后的 KeyBoardState?
-
它需要 SetWindowsHookEx() 来设置一个 WH_KEYBOARD。当我提到这一点时,程序员往往会变得很兴奋。当之无愧:)
标签: c++ windows input unicode keyboard