1+ #ifdef RB3E_XBOX
2+ #include <xtl.h>
3+ #include "rb3/Data.h"
4+ #include "ports.h"
5+
6+ // Reimplementation of DC3's TranslateVK
7+ // This function translates the system XInput VirtualKey value into Harmonix's keycode values
8+ int TranslateVK (DWORD virtualKey , char shift )
9+ {
10+ // ASCII range
11+ // Honestly not sure why this range is even mapped, at these ranges the Unicode translation should be handling it
12+ if (virtualKey >= 0x41 && virtualKey <= 0x5a ) {
13+ if (!shift ) {
14+ return virtualKey ;
15+ } else {
16+ return tolower (virtualKey );
17+ }
18+ }
19+
20+ // Function key range
21+ if (virtualKey >= VK_F1 && virtualKey <= VK_F12 ) {
22+ return virtualKey + 0x121 ;
23+ }
24+
25+ // Other keycode mappings
26+ switch (virtualKey ) {
27+ case VK_HOME :
28+ return 0x138 ;
29+ case VK_CAPITAL :
30+ return 0x122 ;
31+ case VK_BACK :
32+ return 0x08 ;
33+ case VK_TAB :
34+ return 0x09 ;
35+ case VK_RETURN :
36+ return 0x0a ;
37+ case VK_PAUSE :
38+ return 0x12d ;
39+ case VK_ESCAPE :
40+ return 0x12e ;
41+ case VK_PRIOR :
42+ return 0x13a ;
43+ case VK_NEXT :
44+ return 0x13b ;
45+ case VK_END :
46+ return 0x139 ;
47+ case VK_PRINT :
48+ return 0x12c ;
49+ case VK_LEFT :
50+ return 0x140 ;
51+ case VK_UP :
52+ return 0x142 ;
53+ case VK_RIGHT :
54+ return 0x141 ;
55+ case VK_DOWN :
56+ return 0x143 ;
57+ case VK_INSERT :
58+ return 0x136 ;
59+ case VK_DELETE :
60+ return 0x137 ;
61+ case VK_NUMLOCK :
62+ return 0x123 ;
63+ case VK_SCROLL :
64+ return 0x124 ;
65+ }
66+
67+ return virtualKey ;
68+ }
69+
70+
71+ // Reimplementation of KeyboardPoll from DC3
72+ void KeyboardPoll () {
73+ XINPUT_KEYSTROKE keystroke ;
74+ DWORD keystrokeResult ;
75+ static DataNode msgNodes [6 ] = {0 };
76+ static DataArray keyMsg = {0 };
77+ static DataNode retNode ;
78+ Symbol uiSym ;
79+ Symbol keySym ;
80+ char unicodeChar [4 ];
81+ int keyCode ;
82+
83+ keystrokeResult = XInputGetKeystroke (XUSER_INDEX_ANY , 2 , & keystroke );
84+ if (keystrokeResult == ERROR_SUCCESS && (keystroke .Flags & XINPUT_KEYSTROKE_KEYUP ) == 0 ) {
85+ WideCharToMultiByte (0 , 0 , & keystroke .Unicode , 1 , unicodeChar , 2 , 0x0 , 0x0 );
86+ if (unicodeChar [0 ] == '\0' || unicodeChar [0 ] < ' ' || unicodeChar [0 ] > '~' ) {
87+ keyCode = TranslateVK (keystroke .VirtualKey , (keystroke .Flags & XINPUT_KEYSTROKE_SHIFT ) > 0 );
88+ } else {
89+ keyCode = (int )unicodeChar [0 ];
90+ }
91+
92+ keyMsg .mNodes = (DataNodes * )& msgNodes ;
93+ keyMsg .mNodeCount = 6 ;
94+ keyMsg .mRefCount = 1 ;
95+ keyMsg .mFile = * (Symbol * )PORT_NULLSYMBOL ;
96+
97+ SymbolConstruct (& uiSym , "ui" );
98+ SymbolConstruct (& keySym , "key" );
99+
100+ // Construct a command array to do this:
101+ // {ui key $key $shift $ctrl $alt}
102+
103+ // ui object
104+ msgNodes [0 ].type = SYMBOL ;
105+ msgNodes [0 ].value .string = uiSym .sym ;
106+
107+ // key handler
108+ msgNodes [1 ].type = SYMBOL ;
109+ msgNodes [1 ].value .string = keySym .sym ;
110+
111+ // key
112+ msgNodes [2 ].type = INT_VALUE ;
113+ msgNodes [2 ].value .intVal = keyCode ;
114+
115+ // shift
116+ msgNodes [3 ].type = INT_VALUE ;
117+ msgNodes [3 ].value .intVal = (keystroke .Flags & XINPUT_KEYSTROKE_SHIFT ) > 0 ;
118+
119+ // ctrl
120+ msgNodes [4 ].type = INT_VALUE ;
121+ msgNodes [4 ].value .intVal = (keystroke .Flags & XINPUT_KEYSTROKE_CTRL ) > 0 ;
122+
123+ // alt
124+ msgNodes [5 ].type = INT_VALUE ;
125+ msgNodes [5 ].value .intVal = (keystroke .Flags & XINPUT_KEYSTROKE_ALT ) > 0 ;
126+
127+ DataArrayExecute (& retNode , & keyMsg );
128+
129+ }
130+ }
131+ #endif
0 commit comments