static void *manymouse_thread(void* data) { fs_log("[MANYMOUSE] Thread running\n"); int k = g_fs_ml_input_device_count; g_first_manymouse_index = k; int mouse_count = ManyMouse_Init(); if (mouse_count < 0) { fs_log("[MANYMOUSE] Initialization failed (%d)\n", mouse_count); } else if (mouse_count == 0) { fs_log("MANYMOUSE: no mice found\n"); // no mice found, so we just quit using the library } for (int i = 0; i < mouse_count; i++) { const char *device = ManyMouse_DeviceName(i); const char *driver = ManyMouse_DriverName(); char *name; if (device[0] == 0 || g_ascii_strcasecmp(device, "mouse") == 0) { name = g_strdup("Mouse: Unnamed Mouse"); } else { name = g_strdup_printf("Mouse: %s", device); } // fs_ml_input_unique_device_name either returns name, or frees it // and return another name, so name must be malloced and owned by // caller name = fs_ml_input_unique_device_name(name); fs_log("MANYMOUSE: Adding %s (%s)\n", name, driver); g_fs_ml_input_devices[k].type = FS_ML_MOUSE; g_fs_ml_input_devices[k].index = k; g_fs_ml_input_devices[k].name = name; g_fs_ml_input_devices[k].alias = g_strdup_printf("MOUSE #%d", i + 2); k += 1; } // when done like this, I believe no memory barrier is needed when the // other thread polls g_manymouse_last_index g_manymouse_last_index = k; if (mouse_count < 0) { // ManyMouse library was not initialized return NULL; } ManyMouseEvent event; fs_ml_event *new_event; while (!fs_ml_is_quitting()) { // printf("..\n"); while (ManyMouse_PollEvent(&event)) { // printf(" -- event type %d -- \n", event.type); if (event.type == MANYMOUSE_EVENT_RELMOTION) { // printf("MANYMOUSE_EVENT_RELMOTION\n"); new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEMOTION; new_event->motion.device = g_first_manymouse_index + \ event.device; if (event.item == 0) { new_event->motion.xrel = event.value; new_event->motion.yrel = 0; } else if (event.item == 1) { new_event->motion.xrel = 0; new_event->motion.yrel = event.value; } new_event->motion.x = FS_ML_NO_ABSOLUTE_MOUSE_POS; new_event->motion.y = FS_ML_NO_ABSOLUTE_MOUSE_POS; fs_ml_post_event(new_event); // ManyMouseEventType type; // unsigned int device; // unsigned int item; // int value; // int minval; // int maxval; } else if (event.type == MANYMOUSE_EVENT_BUTTON) { db_log(input, "MANYMOUSE: EVENT_BUTTON " "device %d item %d value %d\n", event.device, event.item, event.value); new_event = fs_ml_alloc_event(); new_event->type = event.value ? FS_ML_MOUSEBUTTONDOWN : FS_ML_MOUSEBUTTONUP; new_event->button.state = event.value != 0; new_event->button.device = g_first_manymouse_index + \ event.device; if (event.item == 0) { new_event->button.button = FS_ML_BUTTON_LEFT; } else if (event.item == 1) { new_event->button.button = FS_ML_BUTTON_RIGHT; } else if (event.item == 2) { new_event->button.button = FS_ML_BUTTON_MIDDLE; } else { new_event->button.button = 0; } fs_ml_post_event(new_event); } else if (event.type == MANYMOUSE_EVENT_ABSMOTION) { // printf("MANYMOUSE_EVENT_ABSMOTION\n"); } else if (event.type == MANYMOUSE_EVENT_SCROLL) { db_log(input, "MANYMOUSE: EVENT_SCROLL " "device %d item %d value %d\n", event.device, event.item, event.value); new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONDOWN; new_event->button.state = 1; new_event->button.device = g_first_manymouse_index + \ event.device; new_event->button.button = 0; if (event.item == 0) { if (event.value == 1) { new_event->button.button = FS_ML_BUTTON_WHEELUP; } else { new_event->button.button = FS_ML_BUTTON_WHEELDOWN; } } fs_ml_post_event(new_event); } } fs_ml_usleep(1000); } ManyMouse_Quit(); return NULL; }
static int event_loop() { int result = 0; SDL_Event event; while (SDL_PollEvent(&event)) { switch(event.type) { case SDL_QUIT: fs_log("intercepted SDL_QUIT\n"); fs_ml_quit(); continue; #ifdef USE_SDL2 case SDL_WINDOWEVENT: // printf("SDL_WINDOWEVENT...\n"); if (event.window.event == SDL_WINDOWEVENT_RESIZED) { on_resize(event.window.data1, event.window.data2); } else if (event.window.event == SDL_WINDOWEVENT_CLOSE) { event.type = SDL_QUIT; SDL_PushEvent(&event); } continue; #else case SDL_VIDEORESIZE: on_resize(event.resize.w, event.resize.h); continue; case SDL_ACTIVEEVENT: //fs_log("got active event %d %d %d %d\n", event.active.state, // SDL_APPMOUSEFOCUS, SDL_APPINPUTFOCUS, SDL_APPACTIVE); if ((event.active.state & SDL_APPINPUTFOCUS)) { if (event.active.gain) { fs_log("got keyboard focus\n"); // just got keyboard focus -- clearing modifier states fs_ml_clear_keyboard_modifier_state(); if (g_fs_ml_had_input_grab) { fs_log("- had input grab, re-acquiring\n"); fs_ml_grab_input(1, 1); g_fs_ml_had_input_grab = 0; } if (g_fs_ml_was_fullscreen) { if (!g_fs_emu_video_fullscreen) { fs_log("- was in fullsreen mode before (switching)\n"); fs_ml_toggle_fullscreen(); } g_fs_ml_was_fullscreen = 0; } } else { fs_log("lost keyboard focus\n"); if (fs_ml_has_input_grab()) { fs_log("- releasing input grab\n"); fs_ml_grab_input(0, 1); g_fs_ml_had_input_grab = 1; } else { fs_log("- did not have input grab\n"); //g_fs_ml_had_input_grab = 0; } } } continue; #endif case SDL_KEYDOWN: case SDL_KEYUP: if (g_debug_input) { fs_log("SDL key sym %d mod %d scancode %d state %d\n", event.key.keysym.sym, event.key.keysym.mod, event.key.keysym.scancode, event.key.state); } if (event.key.keysym.sym == 0 && event.key.keysym.scancode == 0) { // ignore "ghost key" seen on OS X which without this // specific check will cause the A key to be mysteriously // pressed. if (g_debug_input) { fs_log("- ignored key with keysym 0 and scancode 0\n"); } continue; } /* if (event.key.keysym.sym == SDLK_F12) { g_f12_state = event.key.state ? FS_ML_KEY_MOD_F12 : 0; printf("-- g_f12_state is %d\n", g_f12_state); } else if (event.key.keysym.sym == SDLK_F11) { g_f11_state = event.key.state ? FS_ML_KEY_MOD_F11 : 0; } */ const Uint8* key_state; int num_keys; #ifdef USE_SDL2 key_state = SDL_GetKeyboardState(&num_keys); g_f11_state = key_state[SDL_SCANCODE_F11] ? FS_ML_KEY_MOD_F11 : 0; g_f12_state = key_state[SDL_SCANCODE_F12] ? FS_ML_KEY_MOD_F12 : 0; // printf("%d %d\n", g_f11_state, g_f12_state); #else key_state = SDL_GetKeyState(&num_keys); g_f11_state = key_state[SDLK_F11] ? FS_ML_KEY_MOD_F11 : 0; g_f12_state = key_state[SDLK_F12] ? FS_ML_KEY_MOD_F12 : 0; #endif int key = -1; #ifdef USE_SDL2 if (event.key.keysym.scancode <= LAST_SDL2_SCANCODE) { key = g_sdl2_keys[event.key.keysym.scancode]; } #else if (0) { } #endif #if defined(MACOSX) #ifdef USE_SDL2 #else else if (event.key.keysym.sym == SDLK_LSHIFT) { key = SDLK_LSHIFT; } else if (event.key.keysym.sym == SDLK_LCTRL) { key = SDLK_LCTRL; } else if (event.key.keysym.sym == SDLK_LALT) { key = SDLK_LALT; } else if (event.key.keysym.sym == SDLK_LMETA) { key = SDLK_LSUPER; } else if (event.key.keysym.sym == SDLK_RMETA) { key = SDLK_RSUPER; } else if (event.key.keysym.sym == SDLK_RALT) { key = SDLK_RALT; } else if (event.key.keysym.sym == SDLK_RCTRL) { key = SDLK_RCTRL; } else if (event.key.keysym.sym == SDLK_RSHIFT) { key = SDLK_RSHIFT; } else if (event.key.keysym.sym == SDLK_CAPSLOCK) { key = SDLK_CAPSLOCK; } #endif #elif defined(WINDOWS) #else else if (event.key.keysym.sym == SDLK_MODE) { key = SDLK_RALT; } #endif else { key = fs_ml_scancode_to_key(event.key.keysym.scancode); } #ifdef USE_SDL2 if (0) { // the below trick does not currently work for SDL2, as // there is no mapping yet for translated keys } #else if (g_f12_state || g_f11_state) { // leave translated key code in keysym } #endif else if (key >= 0) { if (g_debug_input) { fs_log("- key code set to %d (was %d) based on " "scancode %d\n", key, event.key.keysym.sym, event.key.keysym.scancode); } event.key.keysym.sym = key; } int mod = event.key.keysym.mod; if (mod & KMOD_LSHIFT || mod & KMOD_RSHIFT) { event.key.keysym.mod |= KMOD_SHIFT; } if (mod & KMOD_LALT || mod & KMOD_RALT) { //mod & ~(KMOD_LALT | KMOD_RALT); event.key.keysym.mod |= KMOD_ALT; } if (mod & KMOD_LCTRL || mod & KMOD_RCTRL) { event.key.keysym.mod |= KMOD_CTRL; } if (mod & KMOD_LMETA || mod & KMOD_RMETA) { event.key.keysym.mod |= KMOD_META; } // filter out other modidifers event.key.keysym.mod &= (KMOD_SHIFT | KMOD_ALT | KMOD_CTRL | KMOD_META); // add F11/F12 state event.key.keysym.mod |= g_f11_state | g_f12_state; //printf("%d %d %d %d\n", event.key.keysym.mod, // KMOD_ALT, KMOD_LALT, KMOD_RALT); break; //case SDL_MOUSEBUTTONDOWN: // printf("--- mousebutton down ---\n"); } fs_ml_event *new_event = NULL; #if !defined(USE_SDL2) fs_ml_event *new_event_2 = NULL; #endif if (event.type == SDL_KEYDOWN) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_KEYDOWN; new_event->key.keysym.sym = event.key.keysym.sym; new_event->key.keysym.mod = event.key.keysym.mod; #ifdef USE_SDL2 // SDL2 sends its own text input events #else if (event.key.keysym.unicode && event.key.keysym.unicode < 128) { // FIXME: only supporting ASCII for now.. new_event_2 = fs_ml_alloc_event(); new_event_2->type = FS_ML_TEXTINPUT; new_event_2->text.text[0] = event.key.keysym.unicode; new_event_2->text.text[1] = '\0'; } #endif new_event->key.state = event.key.state; } else if (event.type == SDL_KEYUP) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_KEYUP; new_event->key.keysym.sym = event.key.keysym.sym; new_event->key.keysym.mod = event.key.keysym.mod; new_event->key.state = event.key.state; } else if (event.type == SDL_JOYBUTTONDOWN) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYBUTTONDOWN; new_event->jbutton.which = g_fs_ml_first_joystick_index + \ event.jbutton.which; new_event->jbutton.button = event.jbutton.button; new_event->jbutton.state = event.jbutton.state; } else if (event.type == SDL_JOYBUTTONUP) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYBUTTONUP; new_event->jbutton.which = g_fs_ml_first_joystick_index + \ event.jbutton.which; new_event->jbutton.button = event.jbutton.button; new_event->jbutton.state = event.jbutton.state; } else if (event.type == SDL_JOYAXISMOTION) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYAXISMOTION; new_event->jaxis.which = g_fs_ml_first_joystick_index + \ event.jaxis.which; new_event->jaxis.axis = event.jaxis.axis; new_event->jaxis.value = event.jaxis.value; } else if (event.type == SDL_JOYHATMOTION) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYHATMOTION; new_event->jhat.which = g_fs_ml_first_joystick_index + \ event.jhat.which; new_event->jhat.hat = event.jhat.hat; new_event->jhat.value = event.jhat.value; } else if (event.type == SDL_MOUSEMOTION) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEMOTION; new_event->motion.device = g_fs_ml_first_mouse_index; new_event->motion.xrel = event.motion.xrel; new_event->motion.yrel = event.motion.yrel; /* Absolute window coordinates */ new_event->motion.x = event.motion.x; new_event->motion.y = event.motion.y; //printf("ISREL %d\n", SDL_GetRelativeMouseMode()); if (g_debug_input) { fs_log("SDL mouse event x: %4d y: %4d xrel: %4d yrel: %4d\n", event.motion.x, event.motion.y, event.motion.xrel, event.motion.yrel); } } else if (event.type == SDL_MOUSEBUTTONDOWN) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONDOWN; new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.button = event.button.button; #ifdef MACOSX if (new_event->button.button == 1) { int mod = SDL_GetModState(); if (mod & KMOD_ALT) { new_event->button.button = 2; } else if (mod & KMOD_CTRL) { new_event->button.button = 3; } } #endif new_event->button.state = event.button.state; } else if (event.type == SDL_MOUSEBUTTONUP) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONUP; new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.button = event.button.button; #ifdef MACOSX if (new_event->button.button == 1) { int mod = SDL_GetModState(); if (mod & KMOD_ALT) { new_event->button.button = 2; } else if (mod & KMOD_CTRL) { new_event->button.button = 3; } } #endif new_event->button.state = event.button.state; } #ifdef USE_SDL2 else if (event.type == SDL_MOUSEWHEEL) { /* if (event.wheel.which == SDL_TOUCH_MOUSEID) { } */ if (event.wheel.y) { if (g_debug_input) { fs_log("SDL mouse event y-scroll: %4d\n", event.wheel.y); } new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONDOWN; if (event.wheel.y > 0) { new_event->button.button = FS_ML_BUTTON_WHEELUP; } else { new_event->button.button = FS_ML_BUTTON_WHEELDOWN; } new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.state = 1; } } else if (event.type == SDL_TEXTINPUT) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_TEXTINPUT; memcpy(&(new_event->text.text), &(event.text.text), MIN(TEXTINPUTEVENT_TEXT_SIZE, SDL_TEXTINPUTEVENT_TEXT_SIZE)); new_event->text.text[TEXTINPUTEVENT_TEXT_SIZE - 1] = 0; } #endif if (new_event) { fs_ml_post_event(new_event); } #if !defined(USE_SDL2) if (new_event_2) { fs_ml_post_event(new_event_2); } #endif } return result; }
int fs_ml_event_loop(void) { // printf("fs_ml_event_loop\n"); int result = 0; SDL_Event event; while (SDL_PollEvent(&event)) { switch(event.type) { case SDL_QUIT: fs_log("Received SDL_QUIT\n"); fs_ml_quit(); #ifdef FSE_DRIVERS printf("returning 1 from fs_ml_event_loop\n"); result = 1; #endif continue; case SDL_WINDOWEVENT: if (event.window.event == SDL_WINDOWEVENT_RESIZED) { on_resize(event.window.data1, event.window.data2); } else if (event.window.event == SDL_WINDOWEVENT_CLOSE) { event.type = SDL_QUIT; SDL_PushEvent(&event); } else if (event.window.event == SDL_WINDOWEVENT_FOCUS_GAINED) { if (g_grab_input_on_activate) { fs_log("Window focus gained - grabbing input\n"); g_grab_input_on_activate = false; fs_ml_set_input_grab(true); #ifdef MACOSX } else if (fs_ml_input_grab()) { /* Input grab could be "lost" due to Cmd+Tab */ fs_log("[INPUT] Forcing re-grab of input on macOS\n"); fs_ml_set_input_grab(false); fs_ml_set_input_grab(true); #endif } } continue; case SDL_KEYDOWN: case SDL_KEYUP: if (g_fs_log_input) { fs_log("SDL key sym %d mod %d scancode %d state %d repeat %d\n", event.key.keysym.sym, event.key.keysym.mod, event.key.keysym.scancode, event.key.state, event.key.repeat); } if (event.key.repeat) { continue; } if (event.key.keysym.sym == 0 && event.key.keysym.scancode == 0) { /* ignore "ghost key" seen on OS X which without this * specific check will cause the A key to be mysteriously * pressed. */ if (g_fs_log_input) { fs_log("- ignored key with keysym 0 and scancode 0\n"); } continue; } /* if (event.key.keysym.sym == SDLK_F12) { g_f12_state = event.key.state ? FS_ML_KEY_MOD_F12 : 0; printf("-- g_f12_state is %d\n", g_f12_state); } else if (event.key.keysym.sym == SDLK_F11) { g_f11_state = event.key.state ? FS_ML_KEY_MOD_F11 : 0; } */ const Uint8* key_state; int num_keys; key_state = SDL_GetKeyboardState(&num_keys); g_f11_state = key_state[SDL_SCANCODE_F11] ? FS_ML_KEY_MOD_F11 : 0; g_f12_state = key_state[SDL_SCANCODE_F12] ? FS_ML_KEY_MOD_F12 : 0; int key = -1; if (event.key.keysym.scancode <= LAST_SDL2_SCANCODE) { key = g_sdl2_keys[event.key.keysym.scancode]; } #if defined(MACOSX) #elif defined(WINDOWS) #else else if (event.key.keysym.sym == SDLK_MODE) { key = SDLK_RALT; } #endif else { key = fs_ml_scancode_to_key(event.key.keysym.scancode); } #ifdef USE_SDL2 if (0) { // the below trick does not currently work for SDL2, as // there is no mapping yet for translated keys } #else if (g_f12_state || g_f11_state) { // leave translated key code in keysym } #endif else if (key >= 0) { if (g_fs_log_input) { fs_log("- key code set to %d (was %d) based on " "scancode %d\n", key, event.key.keysym.sym, event.key.keysym.scancode); } event.key.keysym.sym = key; } int mod = event.key.keysym.mod; if (mod & KMOD_LSHIFT || mod & KMOD_RSHIFT) event.key.keysym.mod |= KMOD_SHIFT; #if 0 if (mod & KMOD_LALT || mod & KMOD_RALT) event.key.keysym.mod |= KMOD_ALT; #endif if (mod & KMOD_LCTRL || mod & KMOD_RCTRL) event.key.keysym.mod |= KMOD_CTRL; #if 0 if (mod & KMOD_LMETA || mod & KMOD_RMETA) event.key.keysym.mod |= KMOD_META; #endif /* Filter out other modidifers */ event.key.keysym.mod &= KMOD_SHIFT | KMOD_ALT | KMOD_CTRL | KMOD_META; /* Add F11/F12 modifier state */ event.key.keysym.mod |= g_f11_state | g_f12_state; //printf("%d %d %d %d\n", event.key.keysym.mod, // KMOD_ALT, KMOD_LALT, KMOD_RALT); break; //case SDL_MOUSEBUTTONDOWN: // printf("--- mousebutton down ---\n"); } fs_ml_event *new_event = NULL; if (event.type == SDL_KEYDOWN) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_KEYDOWN; new_event->key.keysym.sym = event.key.keysym.sym; new_event->key.keysym.mod = event.key.keysym.mod; new_event->key.state = event.key.state; } else if (event.type == SDL_KEYUP) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_KEYUP; new_event->key.keysym.sym = event.key.keysym.sym; new_event->key.keysym.mod = event.key.keysym.mod; new_event->key.state = event.key.state; } else if (event.type == SDL_JOYBUTTONDOWN) { if (g_fs_log_input) { fs_log("SDL_JOYBUTTONDOWN which %d button %d state %d\n", event.jbutton.which, event.jbutton.button, event.jbutton.state); } new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYBUTTONDOWN; new_event->jbutton.which = \ g_fs_ml_sdl_joystick_index_map[event.jbutton.which]; new_event->jbutton.button = event.jbutton.button; new_event->jbutton.state = event.jbutton.state; } else if (event.type == SDL_JOYBUTTONUP) { if (g_fs_log_input) { fs_log("SDL_JOYBUTTONUP which %d button %d state %d\n", event.jbutton.which, event.jbutton.button, event.jbutton.state); } new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYBUTTONUP; new_event->jbutton.which = \ g_fs_ml_sdl_joystick_index_map[event.jbutton.which]; new_event->jbutton.button = event.jbutton.button; new_event->jbutton.state = event.jbutton.state; } else if (event.type == SDL_JOYAXISMOTION) { /* Not logging axis motion, too much noise */ new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYAXISMOTION; new_event->jaxis.which = \ g_fs_ml_sdl_joystick_index_map[event.jaxis.which]; new_event->jaxis.axis = event.jaxis.axis; new_event->jaxis.value = event.jaxis.value; } else if (event.type == SDL_JOYHATMOTION) { if (g_fs_log_input) { fs_log("SDL_JOYHATMOTION which %d hat %d value %d\n", event.jhat.which, event.jhat.hat, event.jhat.value); } new_event = fs_ml_alloc_event(); new_event->type = FS_ML_JOYHATMOTION; new_event->jhat.which = \ g_fs_ml_sdl_joystick_index_map[event.jhat.which]; new_event->jhat.hat = event.jhat.hat; new_event->jhat.value = event.jhat.value; } else if (event.type == SDL_MOUSEMOTION) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEMOTION; new_event->motion.device = g_fs_ml_first_mouse_index; new_event->motion.xrel = event.motion.xrel; new_event->motion.yrel = event.motion.yrel; /* Absolute window coordinates */ new_event->motion.x = event.motion.x; new_event->motion.y = event.motion.y; //printf("ISREL %d\n", SDL_GetRelativeMouseMode()); if (g_fs_log_input) { fs_log("SDL mouse event x: %4d y: %4d xrel: %4d yrel: %4d\n", event.motion.x, event.motion.y, event.motion.xrel, event.motion.yrel); } } else if (event.type == SDL_MOUSEBUTTONDOWN) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONDOWN; new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.button = event.button.button; #ifdef MACOSX if (new_event->button.button == 1) { int mod = SDL_GetModState(); if (mod & KMOD_ALT) { new_event->button.button = 2; } else if (mod & KMOD_CTRL) { new_event->button.button = 3; } } #endif new_event->button.state = event.button.state; } else if (event.type == SDL_MOUSEBUTTONUP) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONUP; new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.button = event.button.button; #ifdef MACOSX if (new_event->button.button == 1) { int mod = SDL_GetModState(); if (mod & KMOD_ALT) { new_event->button.button = 2; } else if (mod & KMOD_CTRL) { new_event->button.button = 3; } } #endif new_event->button.state = event.button.state; } else if (event.type == SDL_MOUSEWHEEL) { /* if (event.wheel.which == SDL_TOUCH_MOUSEID) { } */ if (event.wheel.y) { if (g_fs_log_input) { fs_log("SDL mouse event y-scroll: %4d\n", event.wheel.y); } new_event = fs_ml_alloc_event(); new_event->type = FS_ML_MOUSEBUTTONDOWN; if (event.wheel.y > 0) { new_event->button.button = FS_ML_BUTTON_WHEELUP; } else { new_event->button.button = FS_ML_BUTTON_WHEELDOWN; } new_event->button.device = g_fs_ml_first_mouse_index; new_event->button.state = 1; } } else if (event.type == SDL_TEXTINPUT) { new_event = fs_ml_alloc_event(); new_event->type = FS_ML_TEXTINPUT; memcpy(&(new_event->text.text), &(event.text.text), MIN(TEXTINPUTEVENT_TEXT_SIZE, SDL_TEXTINPUTEVENT_TEXT_SIZE)); new_event->text.text[TEXTINPUTEVENT_TEXT_SIZE - 1] = 0; } if (new_event) { fs_ml_post_event(new_event); } } return result; }
static int event_loop() { int result = 0; SDL_Event event; while (SDL_PollEvent(&event)) { switch(event.type) { case SDL_QUIT: fs_log("intercepted SDL_QUIT\n"); fs_ml_quit(); continue; case SDL_VIDEORESIZE: on_resize(event.resize.w, event.resize.h); continue; case SDL_ACTIVEEVENT: //fs_log("got active event %d %d %d %d\n", event.active.state, // SDL_APPMOUSEFOCUS, SDL_APPINPUTFOCUS, SDL_APPACTIVE); if ((event.active.state & SDL_APPINPUTFOCUS)) { if (event.active.gain) { fs_log("got keyboard focus\n"); // just got keyboard focus -- clearing modifier states fs_ml_clear_keyboard_modifier_state(); if (g_fs_ml_had_input_grab) { fs_log("- had input grab, re-acquiring\n"); fs_ml_grab_input(1, 1); g_fs_ml_had_input_grab = 0; } if (g_fs_ml_was_fullscreen) { if (!g_fs_emu_video_fullscreen) { fs_log("- was in fullsreen mode before (switching)\n"); fs_ml_toggle_fullscreen(); } g_fs_ml_was_fullscreen = 0; } } else { fs_log("lost keyboard focus\n"); if (fs_ml_has_input_grab()) { fs_log("- releasing input grab\n"); fs_ml_grab_input(0, 1); g_fs_ml_had_input_grab = 1; } else { fs_log("- did not have input grab\n"); //g_fs_ml_had_input_grab = 0; } } } continue; case SDL_KEYDOWN: case SDL_KEYUP: if (g_debug_keys) { fs_log("SDL key sym %d mod %d scancode %d state %d\n", event.key.keysym.sym, event.key.keysym.mod, event.key.keysym.scancode, event.key.state); } int key = -1; if (0) { } #ifdef MACOSX else if (event.key.keysym.sym == SDLK_LSHIFT) { key = SDLK_LSHIFT; } else if (event.key.keysym.sym == SDLK_LCTRL) { key = SDLK_LCTRL; } else if (event.key.keysym.sym == SDLK_LALT) { key = SDLK_LALT; } else if (event.key.keysym.sym == SDLK_LMETA) { key = SDLK_LSUPER; } else if (event.key.keysym.sym == SDLK_RMETA) { key = SDLK_RSUPER; } else if (event.key.keysym.sym == SDLK_RALT) { key = SDLK_RALT; } else if (event.key.keysym.sym == SDLK_RCTRL) { key = SDLK_RCTRL; } else if (event.key.keysym.sym == SDLK_RSHIFT) { key = SDLK_RSHIFT; } else if (event.key.keysym.sym == SDLK_CAPSLOCK) { key = SDLK_CAPSLOCK; } #endif else { key = fs_ml_scancode_to_key(event.key.keysym.scancode); } if (key >= 0) { event.key.keysym.sym = key; } int mod = event.key.keysym.mod; if (mod & KMOD_LSHIFT || mod & KMOD_RSHIFT) { event.key.keysym.mod |= KMOD_SHIFT; } if (mod & KMOD_LALT || mod & KMOD_RALT) { //mod & ~(KMOD_LALT | KMOD_RALT); event.key.keysym.mod |= KMOD_ALT; } if (mod & KMOD_LCTRL || mod & KMOD_RCTRL) { event.key.keysym.mod |= KMOD_CTRL; } if (mod & KMOD_LMETA || mod & KMOD_RMETA) { event.key.keysym.mod |= KMOD_META; } // filter out other modidifers event.key.keysym.mod &= (KMOD_SHIFT | KMOD_ALT | KMOD_CTRL | KMOD_META); //printf("%d %d %d %d\n", event.key.keysym.mod, // KMOD_ALT, KMOD_LALT, KMOD_RALT); break; //case SDL_MOUSEBUTTONDOWN: // printf("--- mousebutton down ---\n"); } fs_ml_event *new_event = fs_ml_alloc_event(); *new_event = event; fs_ml_post_event(new_event); } return result; }
static void process_keyboard_input(LPRAWINPUT raw_input) { //LPRAWKEYBOARD raw_keyboard = &(raw_input->data.keyboard); //int vkey = raw_keyboard->VKey; //int vkey = raw_keyboard->VKey; //int flags = raw_keyboard->Flags; // int vkey = raw_input->data.keyboard.VKey; int flags = raw_input->data.keyboard.Flags; int make_code = raw_input->data.keyboard.MakeCode; if (g_fs_log_input) { fs_log("vkey...: %d (0x%x) make %d extra %d flags %d E0 %d E1 %d\n", vkey, vkey, raw_input->data.keyboard.MakeCode, raw_input->data.keyboard.ExtraInformation, flags, (flags & RI_KEY_E0) != 0, (flags & RI_KEY_E1) != 0); } #ifdef USE_MAKECODES vkey = make_code; if (flags & RI_KEY_E0) { vkey += NUM_VKEYS; } else if (flags & RI_KEY_E1) { vkey += 2 * NUM_VKEYS; } #else /* Special cases */ if (make_code == 54) { /* For some reason, flags is not set properly for right shift */ vkey = VK_SHIFT + E0; } else if (flags & RI_KEY_E0) { vkey += NUM_VKEYS; } else if (flags & RI_KEY_E1) { vkey += 2 * NUM_VKEYS; } #endif int update_mod = 0; int state = ((flags & RI_KEY_BREAK) == 0); switch (vkey) { case 42: g_mod_lshift = state; //mod_shift = g_mod_lshift || g_mod_rshift; update_mod = 1; break; case 54: g_mod_rshift = state; //mod_shift = g_mod_lshift || g_mod_rshift; update_mod = 1; break; case 29: g_mod_lctrl = state; //mod_ctrl = g_mod_lctrl || g_mod_rctrl; update_mod = 1; break; case E0 + 29: g_mod_rctrl = state; //mod_ctrl = g_mod_lctrl || g_mod_rctrl; update_mod = 1; break; case 56: g_mod_lalt = state; //mod_alt = g_mod_lalt || g_mod_ralt; update_mod = 1; break; case E0 + 56: g_mod_ralt = state; update_mod = 1; break; case 87: g_mod_f11 = state; update_mod = 1; break; case 88: g_mod_f12 = state; update_mod = 1; break; } static unsigned char keyboard_state[256] = {}; //GetKeyboardState(keyboard_state); if (update_mod) { if (g_mod_lshift || g_mod_rshift) { g_mod = g_mod | KMOD_SHIFT; keyboard_state[VK_SHIFT] = 0x80; } else { g_mod = g_mod & ~KMOD_SHIFT; keyboard_state[VK_SHIFT] = 0x0; } if (g_mod_lctrl || g_mod_rctrl) { g_mod = g_mod | KMOD_CTRL; keyboard_state[VK_CONTROL] = 0x80; } else { g_mod = g_mod & ~KMOD_CTRL; keyboard_state[VK_CONTROL] = 0x0; } if (g_mod_lalt || g_mod_ralt) { g_mod = g_mod | KMOD_ALT; keyboard_state[VK_MENU] = 0x80; } else { g_mod = g_mod & ~KMOD_ALT; keyboard_state[VK_MENU] = 0x0; } if (g_mod_f11) { g_mod = g_mod | FS_ML_KEY_MOD_F11; } else { g_mod = g_mod & ~FS_ML_KEY_MOD_F11; } if (g_mod_f12) { g_mod = g_mod | FS_ML_KEY_MOD_F12; } else { g_mod = g_mod & ~FS_ML_KEY_MOD_F12; } } int key_code = g_key_mapping[vkey]; WORD character = 0; if (!g_is_modifier_key[key_code]) { ToAsciiEx(raw_input->data.keyboard.VKey, raw_input->data.keyboard.MakeCode, keyboard_state, &character, 0, g_keyboard_layout); //printf("%d %d => %d\n", raw_input->data.keyboard.VKey, // raw_input->data.keyboard.MakeCode, character); if (character > 128) { character = 0; } if (state == 1) { fs_ml_event *event = fs_ml_alloc_event(); event->type = FS_ML_TEXTINPUT; event->text.text[0] = character; event->text.text[1] = '\0'; fs_ml_post_event(event); } } if (state == 0) { // key is up if (vkey <= MAX_VKEY && g_key_state[vkey]) { g_key_state[vkey] = 0; fs_ml_event *event = fs_ml_alloc_event(); event->type = FS_ML_KEYUP; event->key.keysym.sym = key_code; event->key.keysym.mod = g_mod; //event->key.keysym.unicode = character; event->key.state = 0; fs_ml_post_event(event); } } else { // key is down if (vkey <= MAX_VKEY && !g_key_state[vkey]) { //fs_log("down\n"); g_key_state[vkey] = 1; fs_ml_event *event = fs_ml_alloc_event(); event->type = FS_ML_KEYDOWN; event->key.keysym.sym = key_code; event->key.keysym.mod = g_mod; //event->key.keysym.unicode = character; event->key.state = 1; //fs_log("code: %d\n", event->key.code); fs_ml_post_event(event); } } }