diff --git a/settings.c b/settings.c index 57988210ad..ddd4832e4a 100644 --- a/settings.c +++ b/settings.c @@ -22,9 +22,12 @@ #include #include "hqflt/filters.h" #include "config.h" +#include struct settings g_settings; +static void read_keybinds(config_file_t *conf); + static void set_defaults(void) { const char *def_video = NULL; @@ -251,8 +254,113 @@ void parse_config(void) free(tmp_str); } + read_keybinds(conf); // TODO: Keybinds. config_file_free(conf); } + +struct bind_map +{ + const char *key; + int snes_key; +}; + +static const struct bind_map bind_maps[2][12] = { + { + { "input_player1_a", SNES_DEVICE_ID_JOYPAD_A }, + { "input_player1_b", SNES_DEVICE_ID_JOYPAD_B }, + { "input_player1_y", SNES_DEVICE_ID_JOYPAD_Y }, + { "input_player1_x", SNES_DEVICE_ID_JOYPAD_X }, + { "input_player1_start", SNES_DEVICE_ID_JOYPAD_START }, + { "input_player1_select", SNES_DEVICE_ID_JOYPAD_SELECT }, + { "input_player1_l", SNES_DEVICE_ID_JOYPAD_L }, + { "input_player1_r", SNES_DEVICE_ID_JOYPAD_R }, + { "input_player1_left", SNES_DEVICE_ID_JOYPAD_LEFT }, + { "input_player1_right", SNES_DEVICE_ID_JOYPAD_RIGHT }, + { "input_player1_up", SNES_DEVICE_ID_JOYPAD_UP }, + { "input_player1_down", SNES_DEVICE_ID_JOYPAD_DOWN }, + }, + { + { "input_player2_a", SNES_DEVICE_ID_JOYPAD_A }, + { "input_player2_b", SNES_DEVICE_ID_JOYPAD_B }, + { "input_player2_y", SNES_DEVICE_ID_JOYPAD_Y }, + { "input_player2_x", SNES_DEVICE_ID_JOYPAD_X }, + { "input_player2_start", SNES_DEVICE_ID_JOYPAD_START }, + { "input_player2_select", SNES_DEVICE_ID_JOYPAD_SELECT }, + { "input_player2_l", SNES_DEVICE_ID_JOYPAD_L }, + { "input_player2_r", SNES_DEVICE_ID_JOYPAD_R }, + { "input_player2_left", SNES_DEVICE_ID_JOYPAD_LEFT }, + { "input_player2_right", SNES_DEVICE_ID_JOYPAD_RIGHT }, + { "input_player2_up", SNES_DEVICE_ID_JOYPAD_UP }, + { "input_player2_down", SNES_DEVICE_ID_JOYPAD_DOWN }, + } +}; + +struct glfw_map +{ + const char *str; + int key; +}; + +// Edit: Not portable to different input systems atm. Might move this map into the driver itself or something. +static const struct glfw_map glfw_map[] = { + { "left", GLFW_KEY_LEFT }, + { "right", GLFW_KEY_RIGHT }, + { "up", GLFW_KEY_UP }, + { "down", GLFW_KEY_DOWN }, + { "enter", GLFW_KEY_ENTER }, + { "rshift", GLFW_KEY_RSHIFT }, + { "space", GLFW_KEY_SPACE } +}; + +static struct snes_keybind *find_snes_bind(unsigned port, int id) +{ + struct snes_keybind *binds = g_settings.input.binds[port]; + + for (int i = 0; binds[i].id != -1; i++) + { + if (id == binds[i].id) + return &binds[i]; + } + return NULL; +} + +static int find_glfw_bind(const char *str) +{ + for (int i = 0; i < sizeof(glfw_map)/sizeof(struct glfw_map); i++) + { + if (strcasecmp(glfw_map[i].str, str) == 0) + return glfw_map[i].key; + } + return -1; +} + +void read_keybinds(config_file_t *conf) +{ + char *tmp_str; + int glfw_key; + + for (int j = 0; j < 1; j++) + { + for (int i = 0; i < sizeof(bind_maps[j])/sizeof(struct bind_map); i++) + { + if (config_get_string(conf, bind_maps[j][i].key, &tmp_str)) + { + // If the bind is a normal key-press ... + if (strlen(tmp_str) == 1 && isalpha(*tmp_str)) + glfw_key = toupper(*tmp_str); + else // Check if we have a special mapping for it. + glfw_key = find_glfw_bind(tmp_str); + + struct snes_keybind *bind = find_snes_bind(0, bind_maps[j][i].snes_key); + + if (bind && glfw_key >= 0) + bind->key = glfw_key; + + free(tmp_str); + } + } + } +} diff --git a/ssnes.cfg b/ssnes.cfg index e8bcc5e2f7..46fa9ecd82 100644 --- a/ssnes.cfg +++ b/ssnes.cfg @@ -27,3 +27,68 @@ ### Input # input_axis_threshold = + +input_player1_a = t +input_player1_b = y +input_player1_y = +input_player1_x = +input_player1_start = +input_player1_select = +input_player1_l = +input_player1_r = +input_player1_left = +input_player1_right = +input_player1_up = +input_player1_down = + +input_player1_a_btn = +input_player1_b_btn = +input_player1_y_btn = +input_player1_x_btn = +input_player1_start_btn = +input_player1_select_btn = +input_player1_l_btn = +input_player1_r_btn = +input_player1_left_btn = +input_player1_right_btn = +input_player1_up_btn = +input_player1_down_btn = +input_player1_left_axis = +input_player1_right_axis = +input_player1_up_axis = +input_player1_down_axis = + +input_player2_a = +input_player2_b = +input_player2_y = +input_player2_x = +input_player2_start = +input_player2_select = +input_player2_l = +input_player2_r = +input_player2_left = +input_player2_right = +input_player2_up = +input_player2_down = + +input_player2_a_btn = +input_player2_b_btn = +input_player2_y_btn = +input_player2_x_btn = +input_player2_start_btn = +input_player2_select_btn = +input_player2_l_btn = +input_player2_r_btn = +input_player2_left_btn = +input_player2_right_btn = +input_player2_up_btn = +input_player2_down_btn = +input_player2_left_axis = +input_player2_right_axis = +input_player2_up_axis = +input_player2_down_axis = + +input_toggle_fast_forward = +input_toggle_fullscreen = +input_save_state = +input_load_state =