mirror of
https://github.com/jart/cosmopolitan.git
synced 2025-01-31 03:27:39 +00:00
Improve Windows keyboard translation to Linux
This commit is contained in:
parent
982dc4db87
commit
af7cb3c82f
4 changed files with 302 additions and 11 deletions
|
@ -25,6 +25,7 @@
|
|||
#include "libc/errno.h"
|
||||
#include "libc/fmt/itoa.h"
|
||||
#include "libc/intrin/atomic.h"
|
||||
#include "libc/intrin/describeflags.internal.h"
|
||||
#include "libc/intrin/dll.h"
|
||||
#include "libc/intrin/kprintf.h"
|
||||
#include "libc/intrin/nomultics.internal.h"
|
||||
|
@ -160,24 +161,57 @@ static textwindows int ProcessKeyEvent(const struct NtInputRecord *r, char *p) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
#if 0
|
||||
kprintf("bKeyDown=%hhhd wVirtualKeyCode=%s wVirtualScanCode=%s "
|
||||
"UnicodeChar=%#x[%#lc] dwControlKeyState=%s\n",
|
||||
r->Event.KeyEvent.bKeyDown,
|
||||
DescribeVirtualKeyCode(r->Event.KeyEvent.wVirtualKeyCode),
|
||||
DescribeVirtualKeyCode(r->Event.KeyEvent.wVirtualScanCode),
|
||||
r->Event.KeyEvent.uChar.UnicodeChar,
|
||||
r->Event.KeyEvent.uChar.UnicodeChar,
|
||||
DescribeControlKeyState(r->Event.KeyEvent.dwControlKeyState));
|
||||
#endif
|
||||
|
||||
// process arrow keys, function keys, etc.
|
||||
int n = 0;
|
||||
if (!c) {
|
||||
int w;
|
||||
w = GetVirtualKey(vk, !!(cks & kNtShiftPressed),
|
||||
!!(cks & (kNtLeftCtrlPressed | kNtRightCtrlPressed)));
|
||||
if (!w) return 0;
|
||||
int v = GetVirtualKey(vk, !!(cks & kNtShiftPressed),
|
||||
!!(cks & (kNtLeftCtrlPressed | kNtRightCtrlPressed)));
|
||||
if (v) {
|
||||
p[n++] = 033;
|
||||
if (cks & (kNtLeftAltPressed | kNtRightAltPressed)) {
|
||||
p[n++] = 033;
|
||||
}
|
||||
if (w > 0) {
|
||||
if (v > 0) {
|
||||
p[n++] = '[';
|
||||
} else {
|
||||
w = -w;
|
||||
v = -v;
|
||||
}
|
||||
do p[n++] = w;
|
||||
while ((w >>= 8));
|
||||
do p[n++] = v;
|
||||
while ((v >>= 8));
|
||||
return n;
|
||||
}
|
||||
|
||||
// ^/ should be interpreted as ^_
|
||||
if (vk == kNtVkOem_2 && (cks & (kNtLeftCtrlPressed | kNtRightCtrlPressed))) {
|
||||
p[n++] = 037;
|
||||
return n;
|
||||
}
|
||||
|
||||
// everything needs a unicode mapping from here on out
|
||||
// handle some stuff microsoft doesn't encode, e.g. ctrl+alt+b
|
||||
if (!c) {
|
||||
if (isgraph(vk) && (cks & (kNtLeftCtrlPressed | kNtRightCtrlPressed))) {
|
||||
c = CTRL(vk);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
// shift-tab is backtab or ^[Z
|
||||
if (vk == kNtVkTab && (cks & (kNtShiftPressed))) {
|
||||
p[n++] = 033;
|
||||
p[n++] = '[';
|
||||
p[n++] = 'Z';
|
||||
return n;
|
||||
}
|
||||
|
||||
|
@ -230,7 +264,6 @@ static textwindows int ProcessKeyEvent(const struct NtInputRecord *r, char *p) {
|
|||
|
||||
// insert esc prefix when alt is held
|
||||
if ((cks & (kNtLeftAltPressed | kNtRightAltPressed)) &&
|
||||
!(cks & (kNtLeftCtrlPressed | kNtRightCtrlPressed)) &&
|
||||
r->Event.KeyEvent.bKeyDown) {
|
||||
p[n++] = 033;
|
||||
}
|
||||
|
|
38
libc/intrin/describecontrolkeystate.c
Normal file
38
libc/intrin/describecontrolkeystate.c
Normal file
|
@ -0,0 +1,38 @@
|
|||
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
|
||||
│vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi│
|
||||
╞══════════════════════════════════════════════════════════════════════════════╡
|
||||
│ Copyright 2022 Justine Alexandra Roberts Tunney │
|
||||
│ │
|
||||
│ Permission to use, copy, modify, and/or distribute this software for │
|
||||
│ any purpose with or without fee is hereby granted, provided that the │
|
||||
│ above copyright notice and this permission notice appear in all copies. │
|
||||
│ │
|
||||
│ THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL │
|
||||
│ WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED │
|
||||
│ WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE │
|
||||
│ AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL │
|
||||
│ DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR │
|
||||
│ PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER │
|
||||
│ TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR │
|
||||
│ PERFORMANCE OF THIS SOFTWARE. │
|
||||
╚─────────────────────────────────────────────────────────────────────────────*/
|
||||
#include "libc/intrin/describeflags.internal.h"
|
||||
#include "libc/macros.internal.h"
|
||||
#include "libc/nt/struct/inputrecord.h"
|
||||
|
||||
static const struct DescribeFlags kControlKeyState[] = {
|
||||
{kNtRightAltPressed, "RightAltPressed"}, //
|
||||
{kNtLeftAltPressed, "LeftAltPressed"}, //
|
||||
{kNtRightCtrlPressed, "RightCtrlPressed"}, //
|
||||
{kNtLeftCtrlPressed, "LeftCtrlPressed"}, //
|
||||
{kNtShiftPressed, "ShiftPressed"}, //
|
||||
{kNtNumlockOn, "NumlockOn"}, //
|
||||
{kNtScrolllockOn, "ScrolllockOn"}, //
|
||||
{kNtCapslockOn, "CapslockOn"}, //
|
||||
{kNtEnhancedKey, "EnhancedKey"}, //
|
||||
};
|
||||
|
||||
const char *(DescribeControlKeyState)(char buf[64], uint32_t x) {
|
||||
return DescribeFlags(buf, 64, kControlKeyState, ARRAYLEN(kControlKeyState),
|
||||
"kNt", x);
|
||||
}
|
|
@ -16,6 +16,7 @@ const char *DescribeArchPrctlCode(char[12], int);
|
|||
const char *DescribeCancelState(char[12], int, int *);
|
||||
const char *DescribeCapability(char[32], int);
|
||||
const char *DescribeClockName(char[32], int);
|
||||
const char *DescribeControlKeyState(char[64], uint32_t);
|
||||
const char *DescribeDirfd(char[12], int);
|
||||
const char *DescribeDnotifyFlags(char[80], int);
|
||||
const char *DescribeErrno(char[20], int);
|
||||
|
@ -44,7 +45,6 @@ const char *DescribeNtPipeOpenFlags(char[64], uint32_t);
|
|||
const char *DescribeNtProcAccessFlags(char[256], uint32_t);
|
||||
const char *DescribeNtStartFlags(char[128], uint32_t);
|
||||
const char *DescribeNtSymlinkFlags(char[64], uint32_t);
|
||||
const char *DescribeThreadCreateFlags(char[64], uint32_t);
|
||||
const char *DescribeOpenFlags(char[128], int);
|
||||
const char *DescribeOpenMode(char[15], int, int);
|
||||
const char *DescribePersonalityFlags(char[128], int);
|
||||
|
@ -66,6 +66,8 @@ const char *DescribeSocketProtocol(char[12], int);
|
|||
const char *DescribeSocketType(char[64], int);
|
||||
const char *DescribeStdioState(char[12], int);
|
||||
const char *DescribeStringList(char[300], char *const[]);
|
||||
const char *DescribeThreadCreateFlags(char[64], uint32_t);
|
||||
const char *DescribeVirtualKeyCode(char[32], uint32_t);
|
||||
const char *DescribeWhence(char[12], int);
|
||||
const char *DescribeWhichPrio(char[12], int);
|
||||
|
||||
|
@ -73,6 +75,7 @@ const char *DescribeWhichPrio(char[12], int);
|
|||
#define DescribeCancelState(x, y) DescribeCancelState(alloca(12), x, y)
|
||||
#define DescribeCapability(x) DescribeCapability(alloca(32), x)
|
||||
#define DescribeClockName(x) DescribeClockName(alloca(32), x)
|
||||
#define DescribeControlKeyState(x) DescribeControlKeyState(alloca(64), x)
|
||||
#define DescribeDirfd(x) DescribeDirfd(alloca(12), x)
|
||||
#define DescribeDnotifyFlags(x) DescribeDnotifyFlags(alloca(80), x)
|
||||
#define DescribeErrno(x) DescribeErrno(alloca(20), x)
|
||||
|
@ -120,6 +123,7 @@ const char *DescribeWhichPrio(char[12], int);
|
|||
#define DescribeStdioState(x) DescribeStdioState(alloca(12), x)
|
||||
#define DescribeStringList(x) DescribeStringList(alloca(300), x)
|
||||
#define DescribeThreadCreateFlags(x) DescribeThreadCreateFlags(alloca(64), x)
|
||||
#define DescribeVirtualKeyCode(x) DescribeVirtualKeyCode(alloca(32), x)
|
||||
#define DescribeWhence(x) DescribeWhence(alloca(12), x)
|
||||
#define DescribeWhichPrio(x) DescribeWhichPrio(alloca(12), x)
|
||||
|
||||
|
|
216
libc/intrin/describevirtualkeycode.c
Normal file
216
libc/intrin/describevirtualkeycode.c
Normal file
|
@ -0,0 +1,216 @@
|
|||
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
|
||||
│vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi│
|
||||
╞══════════════════════════════════════════════════════════════════════════════╡
|
||||
│ Copyright 2023 Justine Alexandra Roberts Tunney │
|
||||
│ │
|
||||
│ Permission to use, copy, modify, and/or distribute this software for │
|
||||
│ any purpose with or without fee is hereby granted, provided that the │
|
||||
│ above copyright notice and this permission notice appear in all copies. │
|
||||
│ │
|
||||
│ THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL │
|
||||
│ WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED │
|
||||
│ WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE │
|
||||
│ AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL │
|
||||
│ DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR │
|
||||
│ PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER │
|
||||
│ TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR │
|
||||
│ PERFORMANCE OF THIS SOFTWARE. │
|
||||
╚─────────────────────────────────────────────────────────────────────────────*/
|
||||
#include "libc/intrin/kprintf.h"
|
||||
#include "libc/macros.internal.h"
|
||||
#include "libc/nt/enum/vk.h"
|
||||
|
||||
// clang-format off
|
||||
static const struct VirtualKeyCodeName {
|
||||
uint32_t code;
|
||||
const char *name;
|
||||
} kVirtualKeyCodeNames[] = {
|
||||
{kNtVkLbutton, "kNtVkLbutton"},
|
||||
{kNtVkRbutton, "kNtVkRbutton"},
|
||||
{kNtVkCancel, "kNtVkCancel"},
|
||||
{kNtVkMbutton, "kNtVkMbutton"},
|
||||
{kNtVkXbutton1, "kNtVkXbutton1"},
|
||||
{kNtVkXbutton2, "kNtVkXbutton2"},
|
||||
{kNtVkBack, "kNtVkBack"},
|
||||
{kNtVkTab, "kNtVkTab"},
|
||||
{kNtVkClear, "kNtVkClear"},
|
||||
{kNtVkReturn, "kNtVkReturn"},
|
||||
{kNtVkShift, "kNtVkShift"},
|
||||
{kNtVkControl, "kNtVkControl"},
|
||||
{kNtVkMenu, "kNtVkMenu"},
|
||||
{kNtVkPause, "kNtVkPause"},
|
||||
{kNtVkCapital, "kNtVkCapital"},
|
||||
{kNtVkKana, "kNtVkKana"},
|
||||
{kNtVkHangul, "kNtVkHangul"},
|
||||
{kNtVkJunja, "kNtVkJunja"},
|
||||
{kNtVkFinal, "kNtVkFinal"},
|
||||
{kNtVkHanja, "kNtVkHanja"},
|
||||
{kNtVkKanji, "kNtVkKanji"},
|
||||
{kNtVkEscape, "kNtVkEscape"},
|
||||
{kNtVkConvert, "kNtVkConvert"},
|
||||
{kNtVkNonconvert, "kNtVkNonconvert"},
|
||||
{kNtVkAccept, "kNtVkAccept"},
|
||||
{kNtVkModechange, "kNtVkModechange"},
|
||||
{kNtVkSpace, "kNtVkSpace"},
|
||||
{kNtVkPrior, "kNtVkPrior"},
|
||||
{kNtVkNext, "kNtVkNext"},
|
||||
{kNtVkEnd, "kNtVkEnd"},
|
||||
{kNtVkHome, "kNtVkHome"},
|
||||
{kNtVkLeft, "kNtVkLeft"},
|
||||
{kNtVkUp, "kNtVkUp"},
|
||||
{kNtVkRight, "kNtVkRight"},
|
||||
{kNtVkDown, "kNtVkDown"},
|
||||
{kNtVkSelect, "kNtVkSelect"},
|
||||
{kNtVkPrint, "kNtVkPrint"},
|
||||
{kNtVkExecute, "kNtVkExecute"},
|
||||
{kNtVkSnapshot, "kNtVkSnapshot"},
|
||||
{kNtVkInsert, "kNtVkInsert"},
|
||||
{kNtVkDelete, "kNtVkDelete"},
|
||||
{kNtVkHelp, "kNtVkHelp"},
|
||||
{kNtVkLwin, "kNtVkLwin"},
|
||||
{kNtVkRwin, "kNtVkRwin"},
|
||||
{kNtVkApps, "kNtVkApps"},
|
||||
{kNtVkSleep, "kNtVkSleep"},
|
||||
{kNtVkNumpad0, "kNtVkNumpad0"},
|
||||
{kNtVkNumpad1, "kNtVkNumpad1"},
|
||||
{kNtVkNumpad2, "kNtVkNumpad2"},
|
||||
{kNtVkNumpad3, "kNtVkNumpad3"},
|
||||
{kNtVkNumpad4, "kNtVkNumpad4"},
|
||||
{kNtVkNumpad5, "kNtVkNumpad5"},
|
||||
{kNtVkNumpad6, "kNtVkNumpad6"},
|
||||
{kNtVkNumpad7, "kNtVkNumpad7"},
|
||||
{kNtVkNumpad8, "kNtVkNumpad8"},
|
||||
{kNtVkNumpad9, "kNtVkNumpad9"},
|
||||
{kNtVkMultiply, "kNtVkMultiply"},
|
||||
{kNtVkAdd, "kNtVkAdd"},
|
||||
{kNtVkSeparator, "kNtVkSeparator"},
|
||||
{kNtVkSubtract, "kNtVkSubtract"},
|
||||
{kNtVkDecimal, "kNtVkDecimal"},
|
||||
{kNtVkDivide, "kNtVkDivide"},
|
||||
{kNtVkF1, "kNtVkF1"},
|
||||
{kNtVkF2, "kNtVkF2"},
|
||||
{kNtVkF3, "kNtVkF3"},
|
||||
{kNtVkF4, "kNtVkF4"},
|
||||
{kNtVkF5, "kNtVkF5"},
|
||||
{kNtVkF6, "kNtVkF6"},
|
||||
{kNtVkF7, "kNtVkF7"},
|
||||
{kNtVkF8, "kNtVkF8"},
|
||||
{kNtVkF9, "kNtVkF9"},
|
||||
{kNtVkF10, "kNtVkF10"},
|
||||
{kNtVkF11, "kNtVkF11"},
|
||||
{kNtVkF12, "kNtVkF12"},
|
||||
{kNtVkF13, "kNtVkF13"},
|
||||
{kNtVkF14, "kNtVkF14"},
|
||||
{kNtVkF15, "kNtVkF15"},
|
||||
{kNtVkF16, "kNtVkF16"},
|
||||
{kNtVkF17, "kNtVkF17"},
|
||||
{kNtVkF18, "kNtVkF18"},
|
||||
{kNtVkF19, "kNtVkF19"},
|
||||
{kNtVkF20, "kNtVkF20"},
|
||||
{kNtVkF21, "kNtVkF21"},
|
||||
{kNtVkF22, "kNtVkF22"},
|
||||
{kNtVkF23, "kNtVkF23"},
|
||||
{kNtVkF24, "kNtVkF24"},
|
||||
{kNtVkNumlock, "kNtVkNumlock"},
|
||||
{kNtVkScroll, "kNtVkScroll"},
|
||||
{kNtVkLshift, "kNtVkLshift"},
|
||||
{kNtVkRshift, "kNtVkRshift"},
|
||||
{kNtVkLcontrol, "kNtVkLcontrol"},
|
||||
{kNtVkRcontrol, "kNtVkRcontrol"},
|
||||
{kNtVkLmenu, "kNtVkLmenu"},
|
||||
{kNtVkRmenu, "kNtVkRmenu"},
|
||||
{kNtVkBrowserBack, "kNtVkBrowserBack"},
|
||||
{kNtVkBrowserForward, "kNtVkBrowserForward"},
|
||||
{kNtVkBrowserRefresh, "kNtVkBrowserRefresh"},
|
||||
{kNtVkBrowserStop, "kNtVkBrowserStop"},
|
||||
{kNtVkBrowserSearch, "kNtVkBrowserSearch"},
|
||||
{kNtVkBrowserFavorites, "kNtVkBrowserFavorites"},
|
||||
{kNtVkBrowserHome, "kNtVkBrowserHome"},
|
||||
{kNtVkVolumeMute, "kNtVkVolumeMute"},
|
||||
{kNtVkVolumeDown, "kNtVkVolumeDown"},
|
||||
{kNtVkVolumeUp, "kNtVkVolumeUp"},
|
||||
{kNtVkMediaNextTrack, "kNtVkMediaNextTrack"},
|
||||
{kNtVkMediaPrevTrack, "kNtVkMediaPrevTrack"},
|
||||
{kNtVkMediaStop, "kNtVkMediaStop"},
|
||||
{kNtVkMediaPlayPause, "kNtVkMediaPlayPause"},
|
||||
{kNtVkLaunchMail, "kNtVkLaunchMail"},
|
||||
{kNtVkLaunchMediaSelect, "kNtVkLaunchMediaSelect"},
|
||||
{kNtVkLaunchApp1, "kNtVkLaunchApp1"},
|
||||
{kNtVkLaunchApp2, "kNtVkLaunchApp2"},
|
||||
{kNtVkOem_1, "kNtVkOem_1"},
|
||||
{kNtVkOemPlus, "kNtVkOemPlus"},
|
||||
{kNtVkOemComma, "kNtVkOemComma"},
|
||||
{kNtVkOemMinus, "kNtVkOemMinus"},
|
||||
{kNtVkOemPeriod, "kNtVkOemPeriod"},
|
||||
{kNtVkOem_2, "kNtVkOem_2"},
|
||||
{kNtVkOem_3, "kNtVkOem_3"},
|
||||
{kNtVkGamepadA, "kNtVkGamepadA"},
|
||||
{kNtVkGamepadB, "kNtVkGamepadB"},
|
||||
{kNtVkGamepadX, "kNtVkGamepadX"},
|
||||
{kNtVkGamepadY, "kNtVkGamepadY"},
|
||||
{kNtVkGamepadRightShoulder, "kNtVkGamepadRightShoulder"},
|
||||
{kNtVkGamepadLeftShoulder, "kNtVkGamepadLeftShoulder"},
|
||||
{kNtVkGamepadLeftTrigger, "kNtVkGamepadLeftTrigger"},
|
||||
{kNtVkGamepadRightTrigger, "kNtVkGamepadRightTrigger"},
|
||||
{kNtVkGamepadDpadUp, "kNtVkGamepadDpadUp"},
|
||||
{kNtVkGamepadDpadDown, "kNtVkGamepadDpadDown"},
|
||||
{kNtVkGamepadDpadLeft, "kNtVkGamepadDpadLeft"},
|
||||
{kNtVkGamepadDpadRight, "kNtVkGamepadDpadRight"},
|
||||
{kNtVkGamepadMenu, "kNtVkGamepadMenu"},
|
||||
{kNtVkGamepadView, "kNtVkGamepadView"},
|
||||
{kNtVkGamepadLeftThumbstickButton, "kNtVkGamepadLeftThumbstickButton"},
|
||||
{kNtVkGamepadRightThumbstickButton, "kNtVkGamepadRightThumbstickButton"},
|
||||
{kNtVkGamepadLeftThumbstickUp, "kNtVkGamepadLeftThumbstickUp"},
|
||||
{kNtVkGamepadLeftThumbstickDown, "kNtVkGamepadLeftThumbstickDown"},
|
||||
{kNtVkGamepadLeftThumbstickRight, "kNtVkGamepadLeftThumbstickRight"},
|
||||
{kNtVkGamepadLeftThumbstickLeft, "kNtVkGamepadLeftThumbstickLeft"},
|
||||
{kNtVkGamepadRightThumbstickUp, "kNtVkGamepadRightThumbstickUp"},
|
||||
{kNtVkGamepadRightThumbstickDown, "kNtVkGamepadRightThumbstickDown"},
|
||||
{kNtVkGamepadRightThumbstickRight, "kNtVkGamepadRightThumbstickRight"},
|
||||
{kNtVkGamepadRightThumbstickLeft, "kNtVkGamepadRightThumbstickLeft"},
|
||||
{kNtVkOem_4, "kNtVkOem_4"},
|
||||
{kNtVkOem_5, "kNtVkOem_5"},
|
||||
{kNtVkOem_6, "kNtVkOem_6"},
|
||||
{kNtVkOem_7, "kNtVkOem_7"},
|
||||
{kNtVkOem_8, "kNtVkOem_8"},
|
||||
{kNtVkOemAx, "kNtVkOemAx"},
|
||||
{kNtVkOem_102, "kNtVkOem_102"},
|
||||
{kNtVkIcoHelp, "kNtVkIcoHelp"},
|
||||
{kNtVkIco_00, "kNtVkIco_00"},
|
||||
{kNtVkProcesskey, "kNtVkProcesskey"},
|
||||
{kNtVkIcoClear, "kNtVkIcoClear"},
|
||||
{kNtVkPacket, "kNtVkPacket"},
|
||||
{kNtVkOemReset, "kNtVkOemReset"},
|
||||
{kNtVkOemJump, "kNtVkOemJump"},
|
||||
{kNtVkOemPa1, "kNtVkOemPa1"},
|
||||
{kNtVkOemPa2, "kNtVkOemPa2"},
|
||||
{kNtVkOemPa3, "kNtVkOemPa3"},
|
||||
{kNtVkOemWsctrl, "kNtVkOemWsctrl"},
|
||||
{kNtVkOemCusel, "kNtVkOemCusel"},
|
||||
{kNtVkOemAttn, "kNtVkOemAttn"},
|
||||
{kNtVkOemFinish, "kNtVkOemFinish"},
|
||||
{kNtVkOemCopy, "kNtVkOemCopy"},
|
||||
{kNtVkOemAuto, "kNtVkOemAuto"},
|
||||
{kNtVkOemEnlw, "kNtVkOemEnlw"},
|
||||
{kNtVkOemBacktab, "kNtVkOemBacktab"},
|
||||
{kNtVkAttn, "kNtVkAttn"},
|
||||
{kNtVkCrsel, "kNtVkCrsel"},
|
||||
{kNtVkExsel, "kNtVkExsel"},
|
||||
{kNtVkEreof, "kNtVkEreof"},
|
||||
{kNtVkPlay, "kNtVkPlay"},
|
||||
{kNtVkZoom, "kNtVkZoom"},
|
||||
{kNtVkNoname, "kNtVkNoname"},
|
||||
{kNtVkPa1, "kNtVkPa1"},
|
||||
{kNtVkOemClear, "kNtVkOemClear"},
|
||||
};
|
||||
// clang-format on
|
||||
|
||||
const char *(DescribeVirtualKeyCode)(char buf[32], uint32_t x) {
|
||||
for (int i = 0; i < ARRAYLEN(kVirtualKeyCodeNames); ++i) {
|
||||
if (x == kVirtualKeyCodeNames[i].code) {
|
||||
return kVirtualKeyCodeNames[i].name;
|
||||
}
|
||||
}
|
||||
ksnprintf(buf, 32, "%#x[%#lc]", x, x);
|
||||
return buf;
|
||||
}
|
Loading…
Reference in a new issue