drivers/wifi: Remove unnecessary data structure copy
[coreboot2.git] / payloads / libpayload / curses / PDCurses / win32 / pdckbd.c
bloba23ec956f5c0562e7839cc626e3dbe15bd54b93d
1 /* Public Domain Curses */
3 #include "pdcwin.h"
5 RCSID("$Id: pdckbd.c,v 1.115 2008/07/20 20:12:04 wmcbrine Exp $")
7 /*man-start**************************************************************
9 Name: pdckbd
11 Synopsis:
12 unsigned long PDC_get_input_fd(void);
14 Description:
15 PDC_get_input_fd() returns the file descriptor that PDCurses
16 reads its input from. It can be used for select().
18 Portability X/Open BSD SYS V
19 PDC_get_input_fd - - -
21 **man-end****************************************************************/
23 unsigned long pdc_key_modifiers = 0L;
25 /* These variables are used to store information about the next
26 Input Event. */
28 static INPUT_RECORD save_ip;
29 static MOUSE_STATUS old_mouse_status;
30 static DWORD event_count = 0;
31 static SHORT left_key;
32 static int key_count = 0;
33 static int save_press = 0;
35 #define KEV save_ip.Event.KeyEvent
36 #define MEV save_ip.Event.MouseEvent
38 /************************************************************************
39 * Table for key code translation of function keys in keypad mode *
40 * These values are for strict IBM keyboard compatibles only *
41 ************************************************************************/
43 typedef struct
45 unsigned short normal;
46 unsigned short shift;
47 unsigned short control;
48 unsigned short alt;
49 unsigned short extended;
50 } KPTAB;
52 static KPTAB kptab[] =
54 {0, 0, 0, 0, 0 }, /* 0 */
55 {0, 0, 0, 0, 0 }, /* 1 VK_LBUTTON */
56 {0, 0, 0, 0, 0 }, /* 2 VK_RBUTTON */
57 {0, 0, 0, 0, 0 }, /* 3 VK_CANCEL */
58 {0, 0, 0, 0, 0 }, /* 4 VK_MBUTTON */
59 {0, 0, 0, 0, 0 }, /* 5 */
60 {0, 0, 0, 0, 0 }, /* 6 */
61 {0, 0, 0, 0, 0 }, /* 7 */
62 {0x08, 0x08, 0x7F, ALT_BKSP, 0 }, /* 8 VK_BACK */
63 {0x09, KEY_BTAB, CTL_TAB, ALT_TAB, 999 }, /* 9 VK_TAB */
64 {0, 0, 0, 0, 0 }, /* 10 */
65 {0, 0, 0, 0, 0 }, /* 11 */
66 {KEY_B2, 0x35, CTL_PAD5, ALT_PAD5, 0 }, /* 12 VK_CLEAR */
67 {0x0D, 0x0D, CTL_ENTER, ALT_ENTER, 1 }, /* 13 VK_RETURN */
68 {0, 0, 0, 0, 0 }, /* 14 */
69 {0, 0, 0, 0, 0 }, /* 15 */
70 {0, 0, 0, 0, 0 }, /* 16 VK_SHIFT HANDLED SEPARATELY */
71 {0, 0, 0, 0, 0 }, /* 17 VK_CONTROL HANDLED SEPARATELY */
72 {0, 0, 0, 0, 0 }, /* 18 VK_MENU HANDLED SEPARATELY */
73 {0, 0, 0, 0, 0 }, /* 19 VK_PAUSE */
74 {0, 0, 0, 0, 0 }, /* 20 VK_CAPITAL HANDLED SEPARATELY */
75 {0, 0, 0, 0, 0 }, /* 21 VK_HANGUL */
76 {0, 0, 0, 0, 0 }, /* 22 */
77 {0, 0, 0, 0, 0 }, /* 23 VK_JUNJA */
78 {0, 0, 0, 0, 0 }, /* 24 VK_FINAL */
79 {0, 0, 0, 0, 0 }, /* 25 VK_HANJA */
80 {0, 0, 0, 0, 0 }, /* 26 */
81 {0x1B, 0x1B, 0x1B, ALT_ESC, 0 }, /* 27 VK_ESCAPE */
82 {0, 0, 0, 0, 0 }, /* 28 VK_CONVERT */
83 {0, 0, 0, 0, 0 }, /* 29 VK_NONCONVERT */
84 {0, 0, 0, 0, 0 }, /* 30 VK_ACCEPT */
85 {0, 0, 0, 0, 0 }, /* 31 VK_MODECHANGE */
86 {0x20, 0x20, 0x20, 0x20, 0 }, /* 32 VK_SPACE */
87 {KEY_A3, 0x39, CTL_PAD9, ALT_PAD9, 3 }, /* 33 VK_PRIOR */
88 {KEY_C3, 0x33, CTL_PAD3, ALT_PAD3, 4 }, /* 34 VK_NEXT */
89 {KEY_C1, 0x31, CTL_PAD1, ALT_PAD1, 5 }, /* 35 VK_END */
90 {KEY_A1, 0x37, CTL_PAD7, ALT_PAD7, 6 }, /* 36 VK_HOME */
91 {KEY_B1, 0x34, CTL_PAD4, ALT_PAD4, 7 }, /* 37 VK_LEFT */
92 {KEY_A2, 0x38, CTL_PAD8, ALT_PAD8, 8 }, /* 38 VK_UP */
93 {KEY_B3, 0x36, CTL_PAD6, ALT_PAD6, 9 }, /* 39 VK_RIGHT */
94 {KEY_C2, 0x32, CTL_PAD2, ALT_PAD2, 10 }, /* 40 VK_DOWN */
95 {0, 0, 0, 0, 0 }, /* 41 VK_SELECT */
96 {0, 0, 0, 0, 0 }, /* 42 VK_PRINT */
97 {0, 0, 0, 0, 0 }, /* 43 VK_EXECUTE */
98 {0, 0, 0, 0, 0 }, /* 44 VK_SNAPSHOT*/
99 {PAD0, 0x30, CTL_PAD0, ALT_PAD0, 11 }, /* 45 VK_INSERT */
100 {PADSTOP, 0x2E, CTL_PADSTOP, ALT_PADSTOP,12 }, /* 46 VK_DELETE */
101 {0, 0, 0, 0, 0 }, /* 47 VK_HELP */
102 {0x30, 0x29, 0, ALT_0, 0 }, /* 48 */
103 {0x31, 0x21, 0, ALT_1, 0 }, /* 49 */
104 {0x32, 0x40, 0, ALT_2, 0 }, /* 50 */
105 {0x33, 0x23, 0, ALT_3, 0 }, /* 51 */
106 {0x34, 0x24, 0, ALT_4, 0 }, /* 52 */
107 {0x35, 0x25, 0, ALT_5, 0 }, /* 53 */
108 {0x36, 0x5E, 0, ALT_6, 0 }, /* 54 */
109 {0x37, 0x26, 0, ALT_7, 0 }, /* 55 */
110 {0x38, 0x2A, 0, ALT_8, 0 }, /* 56 */
111 {0x39, 0x28, 0, ALT_9, 0 }, /* 57 */
112 {0, 0, 0, 0, 0 }, /* 58 */
113 {0, 0, 0, 0, 0 }, /* 59 */
114 {0, 0, 0, 0, 0 }, /* 60 */
115 {0, 0, 0, 0, 0 }, /* 61 */
116 {0, 0, 0, 0, 0 }, /* 62 */
117 {0, 0, 0, 0, 0 }, /* 63 */
118 {0, 0, 0, 0, 0 }, /* 64 */
119 {0x61, 0x41, 0x01, ALT_A, 0 }, /* 65 */
120 {0x62, 0x42, 0x02, ALT_B, 0 }, /* 66 */
121 {0x63, 0x43, 0x03, ALT_C, 0 }, /* 67 */
122 {0x64, 0x44, 0x04, ALT_D, 0 }, /* 68 */
123 {0x65, 0x45, 0x05, ALT_E, 0 }, /* 69 */
124 {0x66, 0x46, 0x06, ALT_F, 0 }, /* 70 */
125 {0x67, 0x47, 0x07, ALT_G, 0 }, /* 71 */
126 {0x68, 0x48, 0x08, ALT_H, 0 }, /* 72 */
127 {0x69, 0x49, 0x09, ALT_I, 0 }, /* 73 */
128 {0x6A, 0x4A, 0x0A, ALT_J, 0 }, /* 74 */
129 {0x6B, 0x4B, 0x0B, ALT_K, 0 }, /* 75 */
130 {0x6C, 0x4C, 0x0C, ALT_L, 0 }, /* 76 */
131 {0x6D, 0x4D, 0x0D, ALT_M, 0 }, /* 77 */
132 {0x6E, 0x4E, 0x0E, ALT_N, 0 }, /* 78 */
133 {0x6F, 0x4F, 0x0F, ALT_O, 0 }, /* 79 */
134 {0x70, 0x50, 0x10, ALT_P, 0 }, /* 80 */
135 {0x71, 0x51, 0x11, ALT_Q, 0 }, /* 81 */
136 {0x72, 0x52, 0x12, ALT_R, 0 }, /* 82 */
137 {0x73, 0x53, 0x13, ALT_S, 0 }, /* 83 */
138 {0x74, 0x54, 0x14, ALT_T, 0 }, /* 84 */
139 {0x75, 0x55, 0x15, ALT_U, 0 }, /* 85 */
140 {0x76, 0x56, 0x16, ALT_V, 0 }, /* 86 */
141 {0x77, 0x57, 0x17, ALT_W, 0 }, /* 87 */
142 {0x78, 0x58, 0x18, ALT_X, 0 }, /* 88 */
143 {0x79, 0x59, 0x19, ALT_Y, 0 }, /* 89 */
144 {0x7A, 0x5A, 0x1A, ALT_Z, 0 }, /* 90 */
145 {0, 0, 0, 0, 0 }, /* 91 VK_LWIN */
146 {0, 0, 0, 0, 0 }, /* 92 VK_RWIN */
147 {0, 0, 0, 0, 0 }, /* 93 VK_APPS */
148 {0, 0, 0, 0, 0 }, /* 94 */
149 {0, 0, 0, 0, 0 }, /* 95 */
150 {0x30, 0, CTL_PAD0, ALT_PAD0, 0 }, /* 96 VK_NUMPAD0 */
151 {0x31, 0, CTL_PAD1, ALT_PAD1, 0 }, /* 97 VK_NUMPAD1 */
152 {0x32, 0, CTL_PAD2, ALT_PAD2, 0 }, /* 98 VK_NUMPAD2 */
153 {0x33, 0, CTL_PAD3, ALT_PAD3, 0 }, /* 99 VK_NUMPAD3 */
154 {0x34, 0, CTL_PAD4, ALT_PAD4, 0 }, /* 100 VK_NUMPAD4 */
155 {0x35, 0, CTL_PAD5, ALT_PAD5, 0 }, /* 101 VK_NUMPAD5 */
156 {0x36, 0, CTL_PAD6, ALT_PAD6, 0 }, /* 102 VK_NUMPAD6 */
157 {0x37, 0, CTL_PAD7, ALT_PAD7, 0 }, /* 103 VK_NUMPAD7 */
158 {0x38, 0, CTL_PAD8, ALT_PAD8, 0 }, /* 104 VK_NUMPAD8 */
159 {0x39, 0, CTL_PAD9, ALT_PAD9, 0 }, /* 105 VK_NUMPAD9 */
160 {PADSTAR, SHF_PADSTAR,CTL_PADSTAR, ALT_PADSTAR,999 }, /* 106 VK_MULTIPLY*/
161 {PADPLUS, SHF_PADPLUS,CTL_PADPLUS, ALT_PADPLUS,999 }, /* 107 VK_ADD */
162 {0, 0, 0, 0, 0 }, /* 108 VK_SEPARATOR */
163 {PADMINUS, SHF_PADMINUS,CTL_PADMINUS,ALT_PADMINUS,999}, /* 109 VK_SUBTRACT*/
164 {0x2E, 0, CTL_PADSTOP, ALT_PADSTOP,0 }, /* 110 VK_DECIMAL */
165 {PADSLASH, SHF_PADSLASH,CTL_PADSLASH,ALT_PADSLASH,2 }, /* 111 VK_DIVIDE */
166 {KEY_F(1), KEY_F(13), KEY_F(25), KEY_F(37), 0 }, /* 112 VK_F1 */
167 {KEY_F(2), KEY_F(14), KEY_F(26), KEY_F(38), 0 }, /* 113 VK_F2 */
168 {KEY_F(3), KEY_F(15), KEY_F(27), KEY_F(39), 0 }, /* 114 VK_F3 */
169 {KEY_F(4), KEY_F(16), KEY_F(28), KEY_F(40), 0 }, /* 115 VK_F4 */
170 {KEY_F(5), KEY_F(17), KEY_F(29), KEY_F(41), 0 }, /* 116 VK_F5 */
171 {KEY_F(6), KEY_F(18), KEY_F(30), KEY_F(42), 0 }, /* 117 VK_F6 */
172 {KEY_F(7), KEY_F(19), KEY_F(31), KEY_F(43), 0 }, /* 118 VK_F7 */
173 {KEY_F(8), KEY_F(20), KEY_F(32), KEY_F(44), 0 }, /* 119 VK_F8 */
174 {KEY_F(9), KEY_F(21), KEY_F(33), KEY_F(45), 0 }, /* 120 VK_F9 */
175 {KEY_F(10), KEY_F(22), KEY_F(34), KEY_F(46), 0 }, /* 121 VK_F10 */
176 {KEY_F(11), KEY_F(23), KEY_F(35), KEY_F(47), 0 }, /* 122 VK_F11 */
177 {KEY_F(12), KEY_F(24), KEY_F(36), KEY_F(48), 0 }, /* 123 VK_F12 */
179 /* 124 through 218 */
181 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
182 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
183 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
184 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
185 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
186 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
187 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
188 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
189 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
190 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
191 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
192 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
193 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
194 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
195 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
196 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
197 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
198 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
199 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
200 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
201 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
202 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
203 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
204 {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0},
206 {0x5B, 0x7B, 0x1B, ALT_LBRACKET,0 }, /* 219 */
207 {0x5C, 0x7C, 0x1C, ALT_BSLASH, 0 }, /* 220 */
208 {0x5D, 0x7D, 0x1D, ALT_RBRACKET,0 }, /* 221 */
209 {0, 0, 0x27, ALT_FQUOTE, 0 }, /* 222 */
210 {0, 0, 0, 0, 0 }, /* 223 */
211 {0, 0, 0, 0, 0 }, /* 224 */
212 {0, 0, 0, 0, 0 } /* 225 */
215 static KPTAB ext_kptab[] =
217 {0, 0, 0, 0, }, /* MUST BE EMPTY */
218 {PADENTER, SHF_PADENTER, CTL_PADENTER, ALT_PADENTER}, /* 13 */
219 {PADSLASH, SHF_PADSLASH, CTL_PADSLASH, ALT_PADSLASH}, /* 111 */
220 {KEY_PPAGE, KEY_SPREVIOUS, CTL_PGUP, ALT_PGUP }, /* 33 */
221 {KEY_NPAGE, KEY_SNEXT, CTL_PGDN, ALT_PGDN }, /* 34 */
222 {KEY_END, KEY_SEND, CTL_END, ALT_END }, /* 35 */
223 {KEY_HOME, KEY_SHOME, CTL_HOME, ALT_HOME }, /* 36 */
224 {KEY_LEFT, KEY_SLEFT, CTL_LEFT, ALT_LEFT }, /* 37 */
225 {KEY_UP, KEY_SUP, CTL_UP, ALT_UP }, /* 38 */
226 {KEY_RIGHT, KEY_SRIGHT, CTL_RIGHT, ALT_RIGHT }, /* 39 */
227 {KEY_DOWN, KEY_SDOWN, CTL_DOWN, ALT_DOWN }, /* 40 */
228 {KEY_IC, KEY_SIC, CTL_INS, ALT_INS }, /* 45 */
229 {KEY_DC, KEY_SDC, CTL_DEL, ALT_DEL }, /* 46 */
230 {PADSLASH, SHF_PADSLASH, CTL_PADSLASH, ALT_PADSLASH}, /* 191 */
233 /* End of kptab[] */
235 unsigned long PDC_get_input_fd(void)
237 PDC_LOG(("PDC_get_input_fd() - called\n"));
239 return 0L;
242 void PDC_set_keyboard_binary(bool on)
244 PDC_LOG(("PDC_set_keyboard_binary() - called\n"));
247 /* check if a key or mouse event is waiting */
249 bool PDC_check_key(void)
251 if (key_count > 0)
252 return TRUE;
254 GetNumberOfConsoleInputEvents(pdc_con_in, &event_count);
256 return (event_count != 0);
259 /* _get_key_count returns 0 if save_ip doesn't contain an event which
260 should be passed back to the user. This function filters "useless"
261 events.
263 The function returns the number of keys waiting. This may be > 1
264 if the repetition of real keys pressed so far are > 1.
266 Returns 0 on NUMLOCK, CAPSLOCK, SCROLLLOCK.
268 Returns 1 for SHIFT, ALT, CTRL only if no other key has been pressed
269 in between, and SP->return_key_modifiers is set; these are returned
270 on keyup.
272 Normal keys are returned on keydown only. The number of repetitions
273 are returned. Dead keys (diacritics) are omitted. See below for a
274 description.
277 static int _get_key_count(void)
279 int num_keys = 0, vk;
281 PDC_LOG(("_get_key_count() - called\n"));
283 vk = KEV.wVirtualKeyCode;
285 if (KEV.bKeyDown)
287 /* key down */
289 save_press = 0;
291 if (vk == VK_CAPITAL || vk == VK_NUMLOCK || vk == VK_SCROLL)
293 /* throw away these modifiers */
295 else if (vk == VK_SHIFT || vk == VK_CONTROL || vk == VK_MENU)
297 /* These keys are returned on keyup only. */
299 save_press = vk;
300 switch (vk)
302 case VK_SHIFT:
303 left_key = GetKeyState(VK_LSHIFT);
304 break;
305 case VK_CONTROL:
306 left_key = GetKeyState(VK_LCONTROL);
307 break;
308 case VK_MENU:
309 left_key = GetKeyState(VK_LMENU);
312 else
314 /* Check for diacritics. These are dead keys. Some locales
315 have modified characters like umlaut-a, which is an "a"
316 with two dots on it. In some locales you have to press a
317 special key (the dead key) immediately followed by the
318 "a" to get a composed umlaut-a. The special key may have
319 a normal meaning with different modifiers. */
321 if (KEV.uChar.UnicodeChar || !(MapVirtualKey(vk, 2) & 0x80000000))
322 num_keys = KEV.wRepeatCount;
325 else
327 /* key up */
329 /* Only modifier keys or the results of ALT-numpad entry are
330 returned on keyup */
332 if ((vk == VK_MENU && KEV.uChar.UnicodeChar) ||
333 ((vk == VK_SHIFT || vk == VK_CONTROL || vk == VK_MENU) &&
334 vk == save_press))
336 save_press = 0;
337 num_keys = 1;
341 PDC_LOG(("_get_key_count() - returning: num_keys %d\n", num_keys));
343 return num_keys;
346 /* _process_key_event returns -1 if the key in save_ip should be
347 ignored. Otherwise it returns the keycode which should be returned
348 by PDC_get_key(). save_ip must be a key event.
350 CTRL-ALT support has been disabled, when is it emitted plainly? */
352 static int _process_key_event(void)
354 int key = (unsigned short)KEV.uChar.UnicodeChar;
355 WORD vk = KEV.wVirtualKeyCode;
356 DWORD state = KEV.dwControlKeyState;
358 int idx;
359 BOOL enhanced;
361 SP->key_code = TRUE;
363 /* Save the key modifiers if required. Do this first to allow to
364 detect e.g. a pressed CTRL key after a hit of NUMLOCK. */
366 if (SP->save_key_modifiers)
368 if (state & (LEFT_ALT_PRESSED|RIGHT_ALT_PRESSED))
369 pdc_key_modifiers |= PDC_KEY_MODIFIER_ALT;
371 if (state & SHIFT_PRESSED)
372 pdc_key_modifiers |= PDC_KEY_MODIFIER_SHIFT;
374 if (state & (LEFT_CTRL_PRESSED|RIGHT_CTRL_PRESSED))
375 pdc_key_modifiers |= PDC_KEY_MODIFIER_CONTROL;
377 if (state & NUMLOCK_ON)
378 pdc_key_modifiers |= PDC_KEY_MODIFIER_NUMLOCK;
381 /* Handle modifier keys hit by themselves */
383 switch (vk)
385 case VK_SHIFT: /* shift */
386 if (!SP->return_key_modifiers)
387 return -1;
389 return (left_key & 0x8000) ? KEY_SHIFT_L : KEY_SHIFT_R;
391 case VK_CONTROL: /* control */
392 if (!SP->return_key_modifiers)
393 return -1;
395 return (left_key & 0x8000) ? KEY_CONTROL_L : KEY_CONTROL_R;
397 case VK_MENU: /* alt */
398 if (!key)
400 if (!SP->return_key_modifiers)
401 return -1;
403 return (left_key & 0x8000) ? KEY_ALT_L : KEY_ALT_R;
407 /* The system may emit Ascii or Unicode characters depending on
408 whether ReadConsoleInputA or ReadConsoleInputW is used.
410 Normally, if key != 0 then the system did the translation
411 successfully. But this is not true for LEFT_ALT (different to
412 RIGHT_ALT). In case of LEFT_ALT we can get key != 0. So
413 check for this first. */
415 if (key && ( !(state & LEFT_ALT_PRESSED) ||
416 (state & RIGHT_ALT_PRESSED) ))
418 /* This code should catch all keys returning a printable
419 character. Characters above 0x7F should be returned as
420 positive codes. But if'ndef NUMKEYPAD we have to return
421 extended keycodes for keypad codes. */
423 #ifndef NUMKEYPAD
424 if (kptab[vk].extended == 0)
425 #endif
427 SP->key_code = FALSE;
428 return key;
432 /* This case happens if a functional key has been entered. */
434 if ((state & ENHANCED_KEY) && (kptab[vk].extended != 999))
436 enhanced = TRUE;
437 idx = kptab[vk].extended;
439 else
441 enhanced = FALSE;
442 idx = vk;
445 if (state & SHIFT_PRESSED)
446 key = enhanced ? ext_kptab[idx].shift : kptab[idx].shift;
448 else if (state & (LEFT_CTRL_PRESSED|RIGHT_CTRL_PRESSED))
449 key = enhanced ? ext_kptab[idx].control : kptab[idx].control;
451 else if (state & (LEFT_ALT_PRESSED|RIGHT_ALT_PRESSED))
452 key = enhanced ? ext_kptab[idx].alt : kptab[idx].alt;
454 else
455 key = enhanced ? ext_kptab[idx].normal : kptab[idx].normal;
457 if (key < KEY_CODE_YES)
458 SP->key_code = FALSE;
460 return key;
463 static int _process_mouse_event(void)
465 static const DWORD button_mask[] = {1, 4, 2};
466 short action, shift_flags = 0;
467 int i;
469 save_press = 0;
470 SP->key_code = TRUE;
472 memset(&pdc_mouse_status, 0, sizeof(MOUSE_STATUS));
474 /* Handle scroll wheel */
476 if (MEV.dwEventFlags == 4)
478 pdc_mouse_status.changes = (MEV.dwButtonState & 0xFF000000) ?
479 PDC_MOUSE_WHEEL_DOWN : PDC_MOUSE_WHEEL_UP;
481 pdc_mouse_status.x = -1;
482 pdc_mouse_status.y = -1;
484 memset(&old_mouse_status, 0, sizeof(old_mouse_status));
486 return KEY_MOUSE;
489 action = (MEV.dwEventFlags == 2) ? BUTTON_DOUBLE_CLICKED :
490 ((MEV.dwEventFlags == 1) ? BUTTON_MOVED : BUTTON_PRESSED);
492 for (i = 0; i < 3; i++)
493 pdc_mouse_status.button[i] =
494 (MEV.dwButtonState & button_mask[i]) ? action : 0;
496 if (action == BUTTON_PRESSED && MEV.dwButtonState & 7 && SP->mouse_wait)
498 /* Check for a click -- a PRESS followed immediately by a release */
500 if (!event_count)
502 napms(SP->mouse_wait);
504 GetNumberOfConsoleInputEvents(pdc_con_in, &event_count);
507 if (event_count)
509 INPUT_RECORD ip;
510 DWORD count;
511 bool have_click = FALSE;
513 PeekConsoleInput(pdc_con_in, &ip, 1, &count);
515 for (i = 0; i < 3; i++)
517 if (pdc_mouse_status.button[i] == BUTTON_PRESSED &&
518 !(ip.Event.MouseEvent.dwButtonState & button_mask[i]))
520 pdc_mouse_status.button[i] = BUTTON_CLICKED;
521 have_click = TRUE;
525 /* If a click was found, throw out the event */
527 if (have_click)
528 ReadConsoleInput(pdc_con_in, &ip, 1, &count);
532 pdc_mouse_status.x = MEV.dwMousePosition.X;
533 pdc_mouse_status.y = MEV.dwMousePosition.Y;
535 pdc_mouse_status.changes = 0;
537 for (i = 0; i < 3; i++)
539 if (old_mouse_status.button[i] != pdc_mouse_status.button[i])
540 pdc_mouse_status.changes |= (1 << i);
542 if (pdc_mouse_status.button[i] == BUTTON_MOVED)
544 /* Discard non-moved "moves" */
546 if (pdc_mouse_status.x == old_mouse_status.x &&
547 pdc_mouse_status.y == old_mouse_status.y)
548 return -1;
550 /* Motion events always flag the button as changed */
552 pdc_mouse_status.changes |= (1 << i);
553 pdc_mouse_status.changes |= PDC_MOUSE_MOVED;
554 break;
558 old_mouse_status = pdc_mouse_status;
560 /* Treat click events as release events for comparison purposes */
562 for (i = 0; i < 3; i++)
564 if (old_mouse_status.button[i] == BUTTON_CLICKED ||
565 old_mouse_status.button[i] == BUTTON_DOUBLE_CLICKED)
566 old_mouse_status.button[i] = BUTTON_RELEASED;
569 /* Check for SHIFT/CONTROL/ALT */
571 if (MEV.dwControlKeyState & (LEFT_ALT_PRESSED|RIGHT_ALT_PRESSED))
572 shift_flags |= BUTTON_ALT;
574 if (MEV.dwControlKeyState & (LEFT_CTRL_PRESSED|RIGHT_CTRL_PRESSED))
575 shift_flags |= BUTTON_CONTROL;
577 if (MEV.dwControlKeyState & SHIFT_PRESSED)
578 shift_flags |= BUTTON_SHIFT;
580 if (shift_flags)
582 for (i = 0; i < 3; i++)
584 if (pdc_mouse_status.changes & (1 << i))
585 pdc_mouse_status.button[i] |= shift_flags;
589 return KEY_MOUSE;
592 /* return the next available key or mouse event */
594 int PDC_get_key(void)
596 pdc_key_modifiers = 0L;
598 if (!key_count)
600 DWORD count;
602 ReadConsoleInput(pdc_con_in, &save_ip, 1, &count);
603 event_count--;
605 if (save_ip.EventType == MOUSE_EVENT)
606 key_count = 1;
607 else if (save_ip.EventType == KEY_EVENT)
608 key_count = _get_key_count();
611 if (key_count)
613 key_count--;
615 switch (save_ip.EventType)
617 case KEY_EVENT:
618 return _process_key_event();
620 case MOUSE_EVENT:
621 return _process_mouse_event();
625 return -1;
628 /* discard any pending keyboard or mouse input -- this is the core
629 routine for flushinp() */
631 void PDC_flushinp(void)
633 PDC_LOG(("PDC_flushinp() - called\n"));
635 FlushConsoleInputBuffer(pdc_con_in);
638 int PDC_mouse_set(void)
640 /* If turning on mouse input: Set ENABLE_MOUSE_INPUT, and clear
641 all other flags, including the extended flags;
642 If turning off the mouse: Set QuickEdit Mode to the status it
643 had on startup, and clear all other flags */
645 SetConsoleMode(pdc_con_in, SP->_trap_mbe ?
646 (ENABLE_MOUSE_INPUT|0x0080) : (pdc_quick_edit|0x0080));
648 memset(&old_mouse_status, 0, sizeof(old_mouse_status));
650 return OK;
653 int PDC_modifiers_set(void)
655 return OK;