static void reset_keys(void) { int i; for(i = 0; i < 256; i++) { if (modifiers_state[i]) { if (i & 0x80) kbd_put_keycode(0xe0); kbd_put_keycode(i | 0x80); modifiers_state[i] = 0; } } }
static void reset_keys(void) { int i; for(i = 0; i < 256; i++) { if (modifiers_state[i]) { if (i & SCANCODE_GREY) kbd_put_keycode(SCANCODE_EMUL0); kbd_put_keycode(i | SCANCODE_UP); modifiers_state[i] = 0; } } }
static void sdl_process_key(SDL_KeyboardEvent *ev) { int keycode, v; if (ev->keysym.sym == SDLK_PAUSE) { /* specific case */ v = 0; if (ev->type == SDL_KEYUP) v |= SCANCODE_UP; kbd_put_keycode(0xe1); kbd_put_keycode(0x1d | v); kbd_put_keycode(0x45 | v); return; } if (kbd_layout) { // LOGV("Found kbd layout using generic for %d\n",ev->keysym.sym); keycode = sdl_keyevent_to_keycode_generic(ev); } else { // LOGV("Found no kbd layout for %d\n",ev->keysym.sym); keycode = sdl_keyevent_to_keycode(ev); } switch(keycode) { case 0x00: /* sent when leaving window: reset the modifiers state */ reset_keys(); return; case 0x2a: /* Left Shift */ case 0x36: /* Right Shift */ case 0x1d: /* Left CTRL */ case 0x9d: /* Right CTRL */ case 0x38: /* Left ALT */ case 0xb8: /* Right ALT */ if (ev->type == SDL_KEYUP) modifiers_state[keycode] = 0; else modifiers_state[keycode] = 1; break; #define QEMU_SDL_VERSION ((SDL_MAJOR_VERSION << 8) + SDL_MINOR_VERSION) #if QEMU_SDL_VERSION < 0x102 || QEMU_SDL_VERSION == 0x102 && SDL_PATCHLEVEL < 14 /* SDL versions before 1.2.14 don't support key up for caps/num lock. */ case 0x45: /* num lock */ case 0x3a: /* caps lock */ /* SDL does not send the key up event, so we generate it */ kbd_put_keycode(keycode); kbd_put_keycode(keycode | SCANCODE_UP); return; #endif } /* now send the key code */ if (keycode & SCANCODE_GREY) kbd_put_keycode(SCANCODE_EMUL0); if (ev->type == SDL_KEYUP) kbd_put_keycode(keycode | SCANCODE_UP); else kbd_put_keycode(keycode & SCANCODE_KEYCODEMASK); }
void user_event_keycode(int kcode) { #if 0 /* TODO */ kbd_put_keycode(kcode); #endif }
static void sdl_process_key(SDL_KeyboardEvent *ev) { int keycode, v; if (ev->keysym.sym == SDLK_PAUSE) { /* specific case */ v = 0; if (ev->type == SDL_KEYUP) v |= 0x80; kbd_put_keycode(0xe1); kbd_put_keycode(0x1d | v); kbd_put_keycode(0x45 | v); return; } if (kbd_layout) { keycode = sdl_keyevent_to_keycode_generic(ev); } else { keycode = sdl_keyevent_to_keycode(ev); } switch(keycode) { case 0x00: /* sent when leaving window: reset the modifiers state */ reset_keys(); return; case 0x2a: /* Left Shift */ case 0x36: /* Right Shift */ case 0x1d: /* Left CTRL */ case 0x9d: /* Right CTRL */ case 0x38: /* Left ALT */ case 0xb8: /* Right ALT */ if (ev->type == SDL_KEYUP) modifiers_state[keycode] = 0; else modifiers_state[keycode] = 1; break; case 0x45: /* num lock */ case 0x3a: /* caps lock */ /* SDL does not send the key up event, so we generate it */ kbd_put_keycode(keycode); kbd_put_keycode(keycode | 0x80); return; } /* now send the key code */ if (keycode & 0x80) kbd_put_keycode(0xe0); if (ev->type == SDL_KEYUP) kbd_put_keycode(keycode | 0x80); else kbd_put_keycode(keycode & 0x7f); }
static void curses_refresh(DisplayChangeListener *dcl) { int chr, nextchr, keysym, keycode, keycode_alt; if (invalidate) { clear(); refresh(); curses_calc_pad(); vga_hw_invalidate(); invalidate = 0; } vga_hw_text_update(screen); nextchr = ERR; while (1) { /* while there are any pending key strokes to process */ if (nextchr == ERR) chr = getch(); else { chr = nextchr; nextchr = ERR; } if (chr == ERR) break; #ifdef KEY_RESIZE /* this shouldn't occur when we use a custom SIGWINCH handler */ if (chr == KEY_RESIZE) { clear(); refresh(); curses_calc_pad(); curses_update(dcl, 0, 0, width, height); continue; } #endif keycode = curses2keycode[chr]; keycode_alt = 0; /* alt key */ if (keycode == 1) { nextchr = getch(); if (nextchr != ERR) { chr = nextchr; keycode_alt = ALT; keycode = curses2keycode[nextchr]; nextchr = ERR; if (keycode != -1) { keycode |= ALT; /* process keys reserved for qemu */ if (keycode >= QEMU_KEY_CONSOLE0 && keycode < QEMU_KEY_CONSOLE0 + 9) { erase(); wnoutrefresh(stdscr); console_select(keycode - QEMU_KEY_CONSOLE0); invalidate = 1; continue; } } } } if (kbd_layout) { keysym = -1; if (chr < CURSES_KEYS) keysym = curses2keysym[chr]; if (keysym == -1) { if (chr < ' ') { keysym = chr + '@'; if (keysym >= 'A' && keysym <= 'Z') keysym += 'a' - 'A'; keysym |= KEYSYM_CNTRL; } else keysym = chr; } keycode = keysym2scancode(kbd_layout, keysym & KEYSYM_MASK); if (keycode == 0) continue; keycode |= (keysym & ~KEYSYM_MASK) >> 16; keycode |= keycode_alt; } if (keycode == -1) continue; if (is_graphic_console()) { /* since terminals don't know about key press and release * events, we need to emit both for each key received */ if (keycode & SHIFT) kbd_put_keycode(SHIFT_CODE); if (keycode & CNTRL) kbd_put_keycode(CNTRL_CODE); if (keycode & ALT) kbd_put_keycode(ALT_CODE); if (keycode & ALTGR) { kbd_put_keycode(SCANCODE_EMUL0); kbd_put_keycode(ALT_CODE); } if (keycode & GREY) kbd_put_keycode(GREY_CODE); kbd_put_keycode(keycode & KEY_MASK); if (keycode & GREY) kbd_put_keycode(GREY_CODE); kbd_put_keycode((keycode & KEY_MASK) | KEY_RELEASE); if (keycode & ALTGR) { kbd_put_keycode(SCANCODE_EMUL0); kbd_put_keycode(ALT_CODE | KEY_RELEASE); } if (keycode & ALT) kbd_put_keycode(ALT_CODE | KEY_RELEASE); if (keycode & CNTRL) kbd_put_keycode(CNTRL_CODE | KEY_RELEASE); if (keycode & SHIFT) kbd_put_keycode(SHIFT_CODE | KEY_RELEASE); } else { keysym = curses2qemu[chr]; if (keysym == -1) keysym = chr; kbd_put_keysym(keysym); } } }
static void xenfb_kbd_handler(void *opaque) { #define KBD_NUM_BATCH 64 union xenkbd_in_event buf[KBD_NUM_BATCH]; int n, i; XenFBState *xs = opaque; DisplayState *s = xs->ds; static int buttons; static int x, y; n = kbdfront_receive(xs->kbd_dev, buf, KBD_NUM_BATCH); for (i = 0; i < n; i++) { switch (buf[i].type) { case XENKBD_TYPE_MOTION: fprintf(stderr, "FB backend sent us relative mouse motion event!\n"); break; case XENKBD_TYPE_POS: { int new_x = buf[i].pos.abs_x; int new_y = buf[i].pos.abs_y; if (new_x >= s->width) new_x = s->width - 1; if (new_y >= s->height) new_y = s->height - 1; if (kbd_mouse_is_absolute()) { kbd_mouse_event( new_x * 0x7FFF / (s->width - 1), new_y * 0x7FFF / (s->height - 1), buf[i].pos.rel_z, buttons); } else { kbd_mouse_event( new_x - x, new_y - y, buf[i].pos.rel_z, buttons); } x = new_x; y = new_y; break; } case XENKBD_TYPE_KEY: { int keycode = buf[i].key.keycode; int button = 0; if (keycode == BTN_LEFT) button = MOUSE_EVENT_LBUTTON; else if (keycode == BTN_RIGHT) button = MOUSE_EVENT_RBUTTON; else if (keycode == BTN_MIDDLE) button = MOUSE_EVENT_MBUTTON; if (button) { if (buf[i].key.pressed) buttons |= button; else buttons &= ~button; if (kbd_mouse_is_absolute()) kbd_mouse_event( x * 0x7FFF / (s->width - 1), y * 0x7FFF / (s->height - 1), 0, buttons); else kbd_mouse_event(0, 0, 0, buttons); } else { int scancode = linux2scancode[keycode]; if (!scancode) { fprintf(stderr, "Can't convert keycode %x to scancode\n", keycode); break; } if (scancode & 0x80) { kbd_put_keycode(0xe0); scancode &= 0x7f; } if (!buf[i].key.pressed) scancode |= 0x80; kbd_put_keycode(scancode); } break; } } } }
static void curses_refresh(DisplayState *ds) { int chr, nextchr, keysym, keycode; if (invalidate) { clear(); refresh(); curses_calc_pad(); ds->surface->width = FONT_WIDTH * width; ds->surface->height = FONT_HEIGHT * height; vga_hw_invalidate(); invalidate = 0; } vga_hw_text_update(screen); nextchr = ERR; while (1) { /* while there are any pending key strokes to process */ if (nextchr == ERR) chr = getch(); else { chr = nextchr; nextchr = ERR; } if (chr == ERR) break; #ifdef KEY_RESIZE /* this shouldn't occur when we use a custom SIGWINCH handler */ if (chr == KEY_RESIZE) { clear(); refresh(); curses_calc_pad(); curses_update(ds, 0, 0, width, height); ds->surface->width = FONT_WIDTH * width; ds->surface->height = FONT_HEIGHT * height; continue; } #endif keycode = curses2keycode[chr]; if (keycode == -1) continue; /* alt key */ if (keycode == 1) { nextchr = getch(); if (nextchr != ERR) { keycode = curses2keycode[nextchr]; nextchr = ERR; if (keycode == -1) continue; keycode |= ALT; /* process keys reserved for qemu */ if (keycode >= QEMU_KEY_CONSOLE0 && keycode < QEMU_KEY_CONSOLE0 + 9) { erase(); wnoutrefresh(stdscr); console_select(keycode - QEMU_KEY_CONSOLE0); invalidate = 1; continue; } } } if (kbd_layout && !(keycode & GREY)) { keysym = keycode2keysym[keycode & KEY_MASK]; if (keysym == -1) keysym = chr; keycode &= ~KEY_MASK; keycode |= keysym2scancode(kbd_layout, keysym); } if (is_graphic_console()) { /* since terminals don't know about key press and release * events, we need to emit both for each key received */ if (keycode & SHIFT) kbd_put_keycode(SHIFT_CODE); if (keycode & CNTRL) kbd_put_keycode(CNTRL_CODE); if (keycode & ALT) kbd_put_keycode(ALT_CODE); if (keycode & GREY) kbd_put_keycode(GREY_CODE); kbd_put_keycode(keycode & KEY_MASK); if (keycode & GREY) kbd_put_keycode(GREY_CODE); kbd_put_keycode((keycode & KEY_MASK) | KEY_RELEASE); if (keycode & ALT) kbd_put_keycode(ALT_CODE | KEY_RELEASE); if (keycode & CNTRL) kbd_put_keycode(CNTRL_CODE | KEY_RELEASE); if (keycode & SHIFT) kbd_put_keycode(SHIFT_CODE | KEY_RELEASE); } else { keysym = curses2keysym[chr]; if (keysym == -1) keysym = chr; kbd_put_keysym(keysym); } } }