From f31de1c66a21ad09e4fac8730c31d16240135894 Mon Sep 17 00:00:00 2001 From: Lukas Krickl Date: Mon, 2 Mar 2026 05:00:47 +0100 Subject: [PATCH] input: reworked input to make the platform do less work. Inputs are now polled based on action entries and the platform simply has to accept a call of the core code for each action. Actions now contain a generic scan code and device id to allow the backend to decide which device to poll. The device id is opaque. The platform may decide what it means. --- src/i_input.c | 77 +++++------------------ src/i_input.h | 30 +++++---- src/p_platform.h | 10 +++ src/p_r_sdl/p_window.c | 137 +++++++++++++++++++++++++++++------------ 4 files changed, 140 insertions(+), 114 deletions(-) diff --git a/src/i_input.c b/src/i_input.c index d50cc48..a8c16ce 100644 --- a/src/i_input.c +++ b/src/i_input.c @@ -1,58 +1,38 @@ #include "i_input.h" -/* TODO: change api so that this calls the platform backend - * with specific actions that are expected */ - struct i_input_map i_input_map; void i_input_init(void) { + p_input_init(); p_input_set_default_map(); /* TODO read key map from config file */ } -struct i_input_map_ent* i_input_find_ent(u16 scan_code, lrts_bool mod_shift, - lrts_bool mod_alt, lrts_bool mod_ctrl, lrts_bool mod_super) { - u32 i = 0; - struct i_input_map_ent *ent = LRTS_NULL; - for (i = 0; i < I_INPUT_ACTION_LEN; i++) { - ent = &i_input_map.inputs[i]; - - if (ent->scan_code == scan_code - && ent->mod_shift == mod_shift - && ent->mod_alt == mod_alt - && ent->mod_ctrl == mod_ctrl - && ent->mod_super == mod_super) { - return ent; - } - } - - return LRTS_NULL; -} - -void i_input_set(u16 scan_code, lrts_bool mod_shift, lrts_bool mod_alt, lrts_bool mod_ctrl, lrts_bool mod_super) { - struct i_input_map_ent *ent = i_input_find_ent(scan_code, mod_shift, mod_alt, mod_ctrl, mod_super); - if (ent == LRTS_NULL) { - return; - } - ent->held = 1; +void i_input_map_init_default(enum i_input_actions action, + u16 scan_code, + u16 device_id, + lrts_bool mod_shift, + lrts_bool mod_alt, + lrts_bool mod_ctrl, + lrts_bool mod_super) { + struct i_input_map_ent *e = &i_input_map.inputs[action]; + e->scan_code = scan_code; + e->device_id = device_id; + e->mod_shift = mod_shift; + e->mod_alt = mod_alt; + e->mod_ctrl = mod_ctrl; + e->mod_super = mod_super; } -void i_input_unset(u16 scan_code, lrts_bool mod_shift, lrts_bool mod_alt, lrts_bool mod_ctrl, lrts_bool mod_super) { - struct i_input_map_ent *ent = i_input_find_ent(scan_code, mod_shift, mod_alt, mod_ctrl, mod_super); - if (ent == LRTS_NULL) { - return; - } - ent->held = 0; -} void i_input_update(void) { u32 i = 0; /* move all pressed events over one position */ for (i = 0; i < I_INPUT_ACTION_LEN; i++) { i_input_map.inputs[i].pressed <<= 1; - i_input_map.inputs[i].pressed |= i_input_map.inputs[i].held; + i_input_map.inputs[i].pressed |= p_input_poll_action(&i_input_map.inputs[i]); } } @@ -61,31 +41,6 @@ void i_input_cursor_set(i32 x, i32 y) { i_input_map.cursor_y = y; } -void i_input_cursor_click_set(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_CLICK].held = 1; -} - -void i_input_cursor_drag_set(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_DRAG].held = 1; -} - -void i_input_cursor_action_set(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_ACTION].held = 1; -} - -void i_input_cursor_click_unset(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_CLICK].held = 0; -} - -void i_input_cursor_drag_unset(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_DRAG].held = 0; -} - -void i_input_cursor_action_unset(void) { - i_input_map.inputs[I_INPUT_ACTION_CURSOR_ACTION].held = 0; -} - - lrts_bool i_input_just_pressed(enum i_input_actions action) { LRTS_UNUSED(action); return LRTS_FALSE; diff --git a/src/i_input.h b/src/i_input.h index 3669ddd..90d68b9 100644 --- a/src/i_input.h +++ b/src/i_input.h @@ -30,6 +30,10 @@ enum i_input_actions { /* input entry */ struct i_input_map_ent { + /* can be used by the platform module to poll + * a specfici device */ + u16 device_id; + /* this is a platform specific button * code to this input action */ @@ -46,7 +50,6 @@ struct i_input_map_ent { * the most recent state is in the rightmost bit */ u16 pressed; - u16 held; }; /* map of all input actions to scanscodes */ @@ -70,11 +73,9 @@ void i_input_init(void); * to pass events as inputs to the engine * should be called by p_poll_events */ -void i_input_set(u16 scan_code, lrts_bool mod_shift, lrts_bool mod_alt, lrts_bool mod_ctrl, lrts_bool mod_super); +void i_input_set(u16 scan_code, lrts_bool mod_shift, lrts_bool mod_alt, + lrts_bool mod_ctrl, lrts_bool mod_super, lrts_bool key_state); -/* unsets held state - */ -void i_input_unset(u16 scan_code, lrts_bool mod_shift, lrts_bool mod_alt, lrts_bool mod_ctrl, lrts_bool mod_super); /* updates input history by shifting pressed bitfield over by 1 and oring it with the held state */ void i_input_update(void); @@ -84,14 +85,6 @@ void i_input_update(void); */ void i_input_cursor_set(i32 x, i32 y); -void i_input_cursor_click_set(void); -void i_input_cursor_drag_set(void); -void i_input_cursor_action_set(void); - -void i_input_cursor_click_unset(void); -void i_input_cursor_drag_unset(void); -void i_input_cursor_action_unset(void); - /* returns true if this action was just performed this frame */ lrts_bool i_input_just_pressed(enum i_input_actions action); @@ -107,4 +100,15 @@ lrts_bool i_input_double_press(enum i_input_actions action); */ void i_input_poll(void); + +/* inits the default for a keybind */ +void i_input_map_init_default(enum i_input_actions action, + u16 scan_code, + u16 device_id, + lrts_bool mod_shift, + lrts_bool mod_alt, + lrts_bool mod_ctrl, + lrts_bool mod_super); + + #endif diff --git a/src/p_platform.h b/src/p_platform.h index 2817e0f..4495d9d 100644 --- a/src/p_platform.h +++ b/src/p_platform.h @@ -1,6 +1,8 @@ #ifndef P_PLATFORM_H__ #define P_PLATFORM_H__ +#include "i_input.h" + /** * This module contains init code for platforms */ @@ -75,4 +77,12 @@ int p_poll_events(); */ void p_input_set_default_map(); +/** + * Inits input platform + */ +void p_input_init(void); + +/* polls a single key action. returns current buttin state */ +lrts_bool p_input_poll_action(struct i_input_map_ent *ent); + #endif diff --git a/src/p_r_sdl/p_window.c b/src/p_r_sdl/p_window.c index ecc1d2b..27e0ab9 100644 --- a/src/p_r_sdl/p_window.c +++ b/src/p_r_sdl/p_window.c @@ -5,11 +5,101 @@ SDL_Window *p_main_window; SDL_Surface *r_target; -void p_input_set_default_map() { - i_input_map.inputs[I_INPUT_ACTION_CAMERA_UP].scan_code = SDL_SCANCODE_UP; - i_input_map.inputs[I_INPUT_ACTION_CAMERA_DOWN].scan_code = SDL_SCANCODE_DOWN; - i_input_map.inputs[I_INPUT_ACTION_CAMERA_LEFT].scan_code = SDL_SCANCODE_LEFT; - i_input_map.inputs[I_INPUT_ACTION_CAMERA_RIGHT].scan_code = SDL_SCANCODE_RIGHT; +const bool *key_map; +SDL_MouseButtonFlags mouse_state; + +enum p_input_devices { + P_INPUT_DEV_MOUSE, + P_INPUT_DEV_KEYBOARD +}; + +void p_input_init(void) { + key_map = SDL_GetKeyboardState(LRTS_NULL); +} + +void p_input_set_default_map(void) { + i_input_map_init_default(I_INPUT_ACTION_CAMERA_UP, + SDL_SCANCODE_UP, + P_INPUT_DEV_KEYBOARD, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + i_input_map_init_default(I_INPUT_ACTION_CAMERA_DOWN, + SDL_SCANCODE_DOWN, + P_INPUT_DEV_KEYBOARD, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + i_input_map_init_default(I_INPUT_ACTION_CAMERA_LEFT, + SDL_SCANCODE_LEFT, + P_INPUT_DEV_KEYBOARD, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + i_input_map_init_default(I_INPUT_ACTION_CAMERA_RIGHT, + SDL_SCANCODE_RIGHT, + P_INPUT_DEV_KEYBOARD, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + + i_input_map_init_default(I_INPUT_ACTION_CURSOR_CLICK, + SDL_BUTTON_LMASK, + P_INPUT_DEV_MOUSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + + i_input_map_init_default(I_INPUT_ACTION_CURSOR_ACTION, + SDL_BUTTON_RMASK, + P_INPUT_DEV_MOUSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); + + i_input_map_init_default(I_INPUT_ACTION_CURSOR_DRAG, + SDL_BUTTON_MMASK, + P_INPUT_DEV_MOUSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE, + LRTS_FALSE); +} + +lrts_bool p_input_poll_action(struct i_input_map_ent *ent) { + lrts_bool mod_shift, mod_alt, mod_ctrl, mod_super, pressed; + if (ent == LRTS_NULL) { + return LRTS_FALSE; + } + + mod_shift = key_map[SDL_SCANCODE_LSHIFT] | key_map[SDL_SCANCODE_RSHIFT]; + mod_alt = key_map[SDL_SCANCODE_LALT] | key_map[SDL_SCANCODE_RALT]; + mod_ctrl = key_map[SDL_SCANCODE_LCTRL] | key_map[SDL_SCANCODE_RCTRL]; + mod_super = key_map[SDL_SCANCODE_LGUI] | key_map[SDL_SCANCODE_RGUI]; + + if (ent->device_id == P_INPUT_DEV_KEYBOARD) { + pressed = key_map[ent->scan_code]; + } else if (ent->device_id == P_INPUT_DEV_MOUSE) { + pressed = (mouse_state & ent->scan_code) != 0; + } else { + pressed = LRTS_FALSE; + } + + + if (ent->mod_shift == mod_shift + && ent->mod_alt == mod_alt + && ent->mod_ctrl == mod_ctrl + && ent->mod_super == mod_super) { + return pressed; + } + + return LRTS_FALSE; } int p_poll_events() { @@ -21,45 +111,12 @@ int p_poll_events() { case SDL_EVENT_QUIT: lrts_cfg()->exit = LRTS_TRUE; break; - case SDL_EVENT_KEY_DOWN: - i_input_set(e.key.scancode, - (e.key.mod & (SDL_KMOD_LSHIFT | SDL_KMOD_RSHIFT)) != 0, - (e.key.mod & (SDL_KMOD_LALT | SDL_KMOD_RALT)) != 0, - (e.key.mod & (SDL_KMOD_LCTRL | SDL_KMOD_RCTRL)) != 0, - (e.key.mod & (SDL_KMOD_LGUI | SDL_KMOD_RGUI)) != 0 - ); - break; - case SDL_EVENT_KEY_UP: - i_input_unset(e.key.scancode, - (e.key.mod & (SDL_KMOD_LSHIFT | SDL_KMOD_RSHIFT)) != 0, - (e.key.mod & (SDL_KMOD_LALT | SDL_KMOD_RALT)) != 0, - (e.key.mod & (SDL_KMOD_LCTRL | SDL_KMOD_RCTRL)) != 0, - (e.key.mod & (SDL_KMOD_LGUI | SDL_KMOD_RGUI)) != 0 - ); - break; - case SDL_EVENT_MOUSE_BUTTON_DOWN: - if (e.button.button == SDL_BUTTON_LEFT) { - i_input_cursor_click_set(); - } else if (e.button.button == SDL_BUTTON_MIDDLE) { - i_input_cursor_drag_set(); - } else if (e.button.button == SDL_BUTTON_RIGHT) { - i_input_cursor_action_set(); - } - break; - case SDL_EVENT_MOUSE_BUTTON_UP: - if (e.button.button == SDL_BUTTON_LEFT) { - i_input_cursor_click_unset(); - } else if (e.button.button == SDL_BUTTON_MIDDLE) { - i_input_cursor_drag_unset(); - } else if (e.button.button == SDL_BUTTON_RIGHT) { - i_input_cursor_action_unset(); - } - break; } } + - SDL_GetMouseState(&x, &y); + mouse_state = SDL_GetMouseState(&x, &y); i_input_cursor_set(x, y); return 0; -- 2.30.2