src/video/winrt/SDL_winrtkeyboard.cpp
author Sam Lantinga <slouken@libsdl.org>
Thu, 13 Mar 2014 00:40:08 -0700
changeset 8615 097646deaef2
parent 8600 092802455aed
child 8701 cb93e566a0c4
permissions -rw-r--r--
Fixed the copyright date on files contributed by David Ludwig
     1 /*
     2   Simple DirectMedia Layer
     3   Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
     4 
     5   This software is provided 'as-is', without any express or implied
     6   warranty.  In no event will the authors be held liable for any damages
     7   arising from the use of this software.
     8 
     9   Permission is granted to anyone to use this software for any purpose,
    10   including commercial applications, and to alter it and redistribute it
    11   freely, subject to the following restrictions:
    12 
    13   1. The origin of this software must not be misrepresented; you must not
    14      claim that you wrote the original software. If you use this software
    15      in a product, an acknowledgment in the product documentation would be
    16      appreciated but is not required.
    17   2. Altered source versions must be plainly marked as such, and must not be
    18      misrepresented as being the original software.
    19   3. This notice may not be removed or altered from any source distribution.
    20 */
    21 #include "../../SDL_internal.h"
    22 
    23 #if SDL_VIDEO_DRIVER_WINRT
    24 
    25 /* Standard C++11 includes */
    26 #include <unordered_map>
    27 
    28 
    29 /* Windows-specific includes */
    30 #include <Windows.h>
    31 #include <agile.h>
    32 
    33 
    34 /* SDL-specific includes */
    35 #include <SDL.h>
    36 #include "SDL_winrtevents_c.h"
    37 
    38 extern "C" {
    39 #include "../../events/scancodes_windows.h"
    40 #include "../../events/SDL_keyboard_c.h"
    41 }
    42 
    43 
    44 static SDL_Scancode WinRT_Official_Keycodes[] = {
    45     SDL_SCANCODE_UNKNOWN, // VirtualKey.None -- 0
    46     SDL_SCANCODE_UNKNOWN, // VirtualKey.LeftButton -- 1
    47     SDL_SCANCODE_UNKNOWN, // VirtualKey.RightButton -- 2
    48     SDL_SCANCODE_CANCEL, // VirtualKey.Cancel -- 3
    49     SDL_SCANCODE_UNKNOWN, // VirtualKey.MiddleButton -- 4
    50     SDL_SCANCODE_UNKNOWN, // VirtualKey.XButton1 -- 5
    51     SDL_SCANCODE_UNKNOWN, // VirtualKey.XButton2 -- 6
    52     SDL_SCANCODE_UNKNOWN, // -- 7
    53     SDL_SCANCODE_BACKSPACE, // VirtualKey.Back -- 8
    54     SDL_SCANCODE_TAB, // VirtualKey.Tab -- 9
    55     SDL_SCANCODE_UNKNOWN, // -- 10
    56     SDL_SCANCODE_UNKNOWN, // -- 11
    57     SDL_SCANCODE_CLEAR, // VirtualKey.Clear -- 12
    58     SDL_SCANCODE_RETURN, // VirtualKey.Enter -- 13
    59     SDL_SCANCODE_UNKNOWN, // -- 14
    60     SDL_SCANCODE_UNKNOWN, // -- 15
    61     SDL_SCANCODE_LSHIFT, // VirtualKey.Shift -- 16
    62     SDL_SCANCODE_LCTRL, // VirtualKey.Control -- 17
    63     SDL_SCANCODE_MENU, // VirtualKey.Menu -- 18
    64     SDL_SCANCODE_PAUSE, // VirtualKey.Pause -- 19
    65     SDL_SCANCODE_CAPSLOCK, // VirtualKey.CapitalLock -- 20
    66     SDL_SCANCODE_UNKNOWN, // VirtualKey.Kana or VirtualKey.Hangul -- 21
    67     SDL_SCANCODE_UNKNOWN, // -- 22
    68     SDL_SCANCODE_UNKNOWN, // VirtualKey.Junja -- 23
    69     SDL_SCANCODE_UNKNOWN, // VirtualKey.Final -- 24
    70     SDL_SCANCODE_UNKNOWN, // VirtualKey.Hanja or VirtualKey.Kanji -- 25
    71     SDL_SCANCODE_UNKNOWN, // -- 26
    72     SDL_SCANCODE_ESCAPE, // VirtualKey.Escape -- 27
    73     SDL_SCANCODE_UNKNOWN, // VirtualKey.Convert -- 28
    74     SDL_SCANCODE_UNKNOWN, // VirtualKey.NonConvert -- 29
    75     SDL_SCANCODE_UNKNOWN, // VirtualKey.Accept -- 30
    76     SDL_SCANCODE_UNKNOWN, // VirtualKey.ModeChange -- 31  (maybe SDL_SCANCODE_MODE ?)
    77     SDL_SCANCODE_SPACE, // VirtualKey.Space -- 32
    78     SDL_SCANCODE_PAGEUP, // VirtualKey.PageUp -- 33
    79     SDL_SCANCODE_PAGEDOWN, // VirtualKey.PageDown -- 34
    80     SDL_SCANCODE_END, // VirtualKey.End -- 35
    81     SDL_SCANCODE_HOME, // VirtualKey.Home -- 36
    82     SDL_SCANCODE_LEFT, // VirtualKey.Left -- 37
    83     SDL_SCANCODE_UP, // VirtualKey.Up -- 38
    84     SDL_SCANCODE_RIGHT, // VirtualKey.Right -- 39
    85     SDL_SCANCODE_DOWN, // VirtualKey.Down -- 40
    86     SDL_SCANCODE_SELECT, // VirtualKey.Select -- 41
    87     SDL_SCANCODE_UNKNOWN, // VirtualKey.Print -- 42  (maybe SDL_SCANCODE_PRINTSCREEN ?)
    88     SDL_SCANCODE_EXECUTE, // VirtualKey.Execute -- 43
    89     SDL_SCANCODE_UNKNOWN, // VirtualKey.Snapshot -- 44
    90     SDL_SCANCODE_INSERT, // VirtualKey.Insert -- 45
    91     SDL_SCANCODE_DELETE, // VirtualKey.Delete -- 46
    92     SDL_SCANCODE_HELP, // VirtualKey.Help -- 47
    93     SDL_SCANCODE_0, // VirtualKey.Number0 -- 48
    94     SDL_SCANCODE_1, // VirtualKey.Number1 -- 49
    95     SDL_SCANCODE_2, // VirtualKey.Number2 -- 50
    96     SDL_SCANCODE_3, // VirtualKey.Number3 -- 51
    97     SDL_SCANCODE_4, // VirtualKey.Number4 -- 52
    98     SDL_SCANCODE_5, // VirtualKey.Number5 -- 53
    99     SDL_SCANCODE_6, // VirtualKey.Number6 -- 54
   100     SDL_SCANCODE_7, // VirtualKey.Number7 -- 55
   101     SDL_SCANCODE_8, // VirtualKey.Number8 -- 56
   102     SDL_SCANCODE_9, // VirtualKey.Number9 -- 57
   103     SDL_SCANCODE_UNKNOWN, // -- 58
   104     SDL_SCANCODE_UNKNOWN, // -- 59
   105     SDL_SCANCODE_UNKNOWN, // -- 60
   106     SDL_SCANCODE_UNKNOWN, // -- 61
   107     SDL_SCANCODE_UNKNOWN, // -- 62
   108     SDL_SCANCODE_UNKNOWN, // -- 63
   109     SDL_SCANCODE_UNKNOWN, // -- 64
   110     SDL_SCANCODE_A, // VirtualKey.A -- 65
   111     SDL_SCANCODE_B, // VirtualKey.B -- 66
   112     SDL_SCANCODE_C, // VirtualKey.C -- 67
   113     SDL_SCANCODE_D, // VirtualKey.D -- 68
   114     SDL_SCANCODE_E, // VirtualKey.E -- 69
   115     SDL_SCANCODE_F, // VirtualKey.F -- 70
   116     SDL_SCANCODE_G, // VirtualKey.G -- 71
   117     SDL_SCANCODE_H, // VirtualKey.H -- 72
   118     SDL_SCANCODE_I, // VirtualKey.I -- 73
   119     SDL_SCANCODE_J, // VirtualKey.J -- 74
   120     SDL_SCANCODE_K, // VirtualKey.K -- 75
   121     SDL_SCANCODE_L, // VirtualKey.L -- 76
   122     SDL_SCANCODE_M, // VirtualKey.M -- 77
   123     SDL_SCANCODE_N, // VirtualKey.N -- 78
   124     SDL_SCANCODE_O, // VirtualKey.O -- 79
   125     SDL_SCANCODE_P, // VirtualKey.P -- 80
   126     SDL_SCANCODE_Q, // VirtualKey.Q -- 81
   127     SDL_SCANCODE_R, // VirtualKey.R -- 82
   128     SDL_SCANCODE_S, // VirtualKey.S -- 83
   129     SDL_SCANCODE_T, // VirtualKey.T -- 84
   130     SDL_SCANCODE_U, // VirtualKey.U -- 85
   131     SDL_SCANCODE_V, // VirtualKey.V -- 86
   132     SDL_SCANCODE_W, // VirtualKey.W -- 87
   133     SDL_SCANCODE_X, // VirtualKey.X -- 88
   134     SDL_SCANCODE_Y, // VirtualKey.Y -- 89
   135     SDL_SCANCODE_Z, // VirtualKey.Z -- 90
   136     SDL_SCANCODE_UNKNOWN, // VirtualKey.LeftWindows -- 91  (maybe SDL_SCANCODE_APPLICATION or SDL_SCANCODE_LGUI ?)
   137     SDL_SCANCODE_UNKNOWN, // VirtualKey.RightWindows -- 92  (maybe SDL_SCANCODE_APPLICATION or SDL_SCANCODE_RGUI ?)
   138     SDL_SCANCODE_APPLICATION, // VirtualKey.Application -- 93
   139     SDL_SCANCODE_UNKNOWN, // -- 94
   140     SDL_SCANCODE_SLEEP, // VirtualKey.Sleep -- 95
   141     SDL_SCANCODE_KP_0, // VirtualKey.NumberPad0 -- 96
   142     SDL_SCANCODE_KP_1, // VirtualKey.NumberPad1 -- 97
   143     SDL_SCANCODE_KP_2, // VirtualKey.NumberPad2 -- 98
   144     SDL_SCANCODE_KP_3, // VirtualKey.NumberPad3 -- 99
   145     SDL_SCANCODE_KP_4, // VirtualKey.NumberPad4 -- 100
   146     SDL_SCANCODE_KP_5, // VirtualKey.NumberPad5 -- 101
   147     SDL_SCANCODE_KP_6, // VirtualKey.NumberPad6 -- 102
   148     SDL_SCANCODE_KP_7, // VirtualKey.NumberPad7 -- 103
   149     SDL_SCANCODE_KP_8, // VirtualKey.NumberPad8 -- 104
   150     SDL_SCANCODE_KP_9, // VirtualKey.NumberPad9 -- 105
   151     SDL_SCANCODE_KP_MULTIPLY, // VirtualKey.Multiply -- 106
   152     SDL_SCANCODE_KP_PLUS, // VirtualKey.Add -- 107
   153     SDL_SCANCODE_UNKNOWN, // VirtualKey.Separator -- 108
   154     SDL_SCANCODE_KP_MINUS, // VirtualKey.Subtract -- 109
   155     SDL_SCANCODE_UNKNOWN, // VirtualKey.Decimal -- 110  (maybe SDL_SCANCODE_DECIMALSEPARATOR, SDL_SCANCODE_KP_DECIMAL, or SDL_SCANCODE_KP_PERIOD ?)
   156     SDL_SCANCODE_KP_DIVIDE, // VirtualKey.Divide -- 111
   157     SDL_SCANCODE_F1, // VirtualKey.F1 -- 112
   158     SDL_SCANCODE_F2, // VirtualKey.F2 -- 113
   159     SDL_SCANCODE_F3, // VirtualKey.F3 -- 114
   160     SDL_SCANCODE_F4, // VirtualKey.F4 -- 115
   161     SDL_SCANCODE_F5, // VirtualKey.F5 -- 116
   162     SDL_SCANCODE_F6, // VirtualKey.F6 -- 117
   163     SDL_SCANCODE_F7, // VirtualKey.F7 -- 118
   164     SDL_SCANCODE_F8, // VirtualKey.F8 -- 119
   165     SDL_SCANCODE_F9, // VirtualKey.F9 -- 120
   166     SDL_SCANCODE_F10, // VirtualKey.F10 -- 121
   167     SDL_SCANCODE_F11, // VirtualKey.F11 -- 122
   168     SDL_SCANCODE_F12, // VirtualKey.F12 -- 123
   169     SDL_SCANCODE_F13, // VirtualKey.F13 -- 124
   170     SDL_SCANCODE_F14, // VirtualKey.F14 -- 125
   171     SDL_SCANCODE_F15, // VirtualKey.F15 -- 126
   172     SDL_SCANCODE_F16, // VirtualKey.F16 -- 127
   173     SDL_SCANCODE_F17, // VirtualKey.F17 -- 128
   174     SDL_SCANCODE_F18, // VirtualKey.F18 -- 129
   175     SDL_SCANCODE_F19, // VirtualKey.F19 -- 130
   176     SDL_SCANCODE_F20, // VirtualKey.F20 -- 131
   177     SDL_SCANCODE_F21, // VirtualKey.F21 -- 132
   178     SDL_SCANCODE_F22, // VirtualKey.F22 -- 133
   179     SDL_SCANCODE_F23, // VirtualKey.F23 -- 134
   180     SDL_SCANCODE_F24, // VirtualKey.F24 -- 135
   181     SDL_SCANCODE_UNKNOWN, // -- 136
   182     SDL_SCANCODE_UNKNOWN, // -- 137
   183     SDL_SCANCODE_UNKNOWN, // -- 138
   184     SDL_SCANCODE_UNKNOWN, // -- 139
   185     SDL_SCANCODE_UNKNOWN, // -- 140
   186     SDL_SCANCODE_UNKNOWN, // -- 141
   187     SDL_SCANCODE_UNKNOWN, // -- 142
   188     SDL_SCANCODE_UNKNOWN, // -- 143
   189     SDL_SCANCODE_NUMLOCKCLEAR, // VirtualKey.NumberKeyLock -- 144
   190     SDL_SCANCODE_SCROLLLOCK, // VirtualKey.Scroll -- 145
   191     SDL_SCANCODE_UNKNOWN, // -- 146
   192     SDL_SCANCODE_UNKNOWN, // -- 147
   193     SDL_SCANCODE_UNKNOWN, // -- 148
   194     SDL_SCANCODE_UNKNOWN, // -- 149
   195     SDL_SCANCODE_UNKNOWN, // -- 150
   196     SDL_SCANCODE_UNKNOWN, // -- 151
   197     SDL_SCANCODE_UNKNOWN, // -- 152
   198     SDL_SCANCODE_UNKNOWN, // -- 153
   199     SDL_SCANCODE_UNKNOWN, // -- 154
   200     SDL_SCANCODE_UNKNOWN, // -- 155
   201     SDL_SCANCODE_UNKNOWN, // -- 156
   202     SDL_SCANCODE_UNKNOWN, // -- 157
   203     SDL_SCANCODE_UNKNOWN, // -- 158
   204     SDL_SCANCODE_UNKNOWN, // -- 159
   205     SDL_SCANCODE_LSHIFT, // VirtualKey.LeftShift -- 160
   206     SDL_SCANCODE_RSHIFT, // VirtualKey.RightShift -- 161
   207     SDL_SCANCODE_LCTRL, // VirtualKey.LeftControl -- 162
   208     SDL_SCANCODE_RCTRL, // VirtualKey.RightControl -- 163
   209     SDL_SCANCODE_MENU, // VirtualKey.LeftMenu -- 164
   210     SDL_SCANCODE_MENU, // VirtualKey.RightMenu -- 165
   211 };
   212 
   213 static std::unordered_map<int, SDL_Scancode> WinRT_Unofficial_Keycodes;
   214 
   215 static SDL_Scancode
   216 TranslateKeycode(int keycode)
   217 {
   218     if (WinRT_Unofficial_Keycodes.empty()) {
   219         /* Set up a table of undocumented (by Microsoft), WinRT-specific,
   220            key codes: */
   221         // TODO, WinRT: move content declarations of WinRT_Unofficial_Keycodes into a C++11 initializer list, when possible
   222         WinRT_Unofficial_Keycodes[220] = SDL_SCANCODE_GRAVE;
   223         WinRT_Unofficial_Keycodes[222] = SDL_SCANCODE_BACKSLASH;
   224     }
   225 
   226     /* Try to get a documented, WinRT, 'VirtualKey' first (as documented at
   227        http://msdn.microsoft.com/en-us/library/windows/apps/windows.system.virtualkey.aspx ).
   228        If that fails, fall back to a Win32 virtual key.
   229     */
   230     // TODO, WinRT: try filling out the WinRT keycode table as much as possible, using the Win32 table for interpretation hints
   231     //SDL_Log("WinRT TranslateKeycode, keycode=%d\n", (int)keycode);
   232     SDL_Scancode scancode = SDL_SCANCODE_UNKNOWN;
   233     if (keycode < SDL_arraysize(WinRT_Official_Keycodes)) {
   234         scancode = WinRT_Official_Keycodes[keycode];
   235     }
   236     if (scancode == SDL_SCANCODE_UNKNOWN) {
   237         if (WinRT_Unofficial_Keycodes.find(keycode) != WinRT_Unofficial_Keycodes.end()) {
   238             scancode = WinRT_Unofficial_Keycodes[keycode];
   239         }
   240     }
   241     if (scancode == SDL_SCANCODE_UNKNOWN) {
   242         if (keycode < SDL_arraysize(windows_scancode_table)) {
   243             scancode = windows_scancode_table[keycode];
   244         }
   245     }
   246     if (scancode == SDL_SCANCODE_UNKNOWN) {
   247         SDL_Log("WinRT TranslateKeycode, unknown keycode=%d\n", (int)keycode);
   248     }
   249     return scancode;
   250 }
   251 
   252 void
   253 WINRT_ProcessKeyDownEvent(Windows::UI::Core::KeyEventArgs ^args)
   254 {
   255     SDL_Scancode sdlScancode = TranslateKeycode((int)args->VirtualKey);
   256 #if 0
   257     SDL_Keycode keycode = SDL_GetKeyFromScancode(sdlScancode);
   258     SDL_Log("key down, handled=%s, ext?=%s, released?=%s, menu key down?=%s, repeat count=%d, native scan code=%d, was down?=%s, vkey=%d, sdl scan code=%d (%s), sdl key code=%d (%s)\n",
   259         (args->Handled ? "1" : "0"),
   260         (args->KeyStatus.IsExtendedKey ? "1" : "0"),
   261         (args->KeyStatus.IsKeyReleased ? "1" : "0"),
   262         (args->KeyStatus.IsMenuKeyDown ? "1" : "0"),
   263         args->KeyStatus.RepeatCount,
   264         args->KeyStatus.ScanCode,
   265         (args->KeyStatus.WasKeyDown ? "1" : "0"),
   266         args->VirtualKey,
   267         sdlScancode,
   268         SDL_GetScancodeName(sdlScancode),
   269         keycode,
   270         SDL_GetKeyName(keycode));
   271     //args->Handled = true;
   272     //VirtualKey vkey = args->VirtualKey;
   273 #endif
   274     SDL_SendKeyboardKey(SDL_PRESSED, sdlScancode);
   275 }
   276 
   277 void
   278 WINRT_ProcessKeyUpEvent(Windows::UI::Core::KeyEventArgs ^args)
   279 {
   280     SDL_Scancode sdlScancode = TranslateKeycode((int)args->VirtualKey);
   281 #if 0
   282     SDL_Keycode keycode = SDL_GetKeyFromScancode(sdlScancode);
   283     SDL_Log("key up, handled=%s, ext?=%s, released?=%s, menu key down?=%s, repeat count=%d, native scan code=%d, was down?=%s, vkey=%d, sdl scan code=%d (%s), sdl key code=%d (%s)\n",
   284         (args->Handled ? "1" : "0"),
   285         (args->KeyStatus.IsExtendedKey ? "1" : "0"),
   286         (args->KeyStatus.IsKeyReleased ? "1" : "0"),
   287         (args->KeyStatus.IsMenuKeyDown ? "1" : "0"),
   288         args->KeyStatus.RepeatCount,
   289         args->KeyStatus.ScanCode,
   290         (args->KeyStatus.WasKeyDown ? "1" : "0"),
   291         args->VirtualKey,
   292         sdlScancode,
   293         SDL_GetScancodeName(sdlScancode),
   294         keycode,
   295         SDL_GetKeyName(keycode));
   296     //args->Handled = true;
   297 #endif
   298     SDL_SendKeyboardKey(SDL_RELEASED, sdlScancode);
   299 }
   300 
   301 #endif // SDL_VIDEO_DRIVER_WINRT