mirror of
https://github.com/phoboslab/wipeout-rewrite
synced 2024-12-26 09:59:04 +01:00
Add button bindings to save data, add controls menu; close #6
This commit is contained in:
parent
0ded93de55
commit
b2e3ae80dd
5 changed files with 158 additions and 52 deletions
|
@ -4,9 +4,9 @@
|
|||
#include "utils.h"
|
||||
|
||||
static const char *button_names[] = {
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
[INPUT_KEY_A] = "A",
|
||||
[INPUT_KEY_B] = "B",
|
||||
|
|
|
@ -51,7 +51,7 @@ typedef enum {
|
|||
INPUT_KEY_LEFTBRACKET = 47,
|
||||
INPUT_KEY_RIGHTBRACKET = 48,
|
||||
INPUT_KEY_BACKSLASH = 49,
|
||||
INPUT_KEY_HASH = 50,
|
||||
INPUT_KEY_HASH = 50,
|
||||
INPUT_KEY_SEMICOLON = 51,
|
||||
INPUT_KEY_APOSTROPHE = 52,
|
||||
INPUT_KEY_TILDE = 53,
|
||||
|
@ -108,7 +108,7 @@ typedef enum {
|
|||
INPUT_KEY_LGUI = 103,
|
||||
INPUT_KEY_RCTRL = 104,
|
||||
INPUT_KEY_RSHIFT = 105,
|
||||
INPUT_KEY_RALT = 106,
|
||||
INPUT_KEY_RALT = 106,
|
||||
|
||||
INPUT_KEY_MAX = 107,
|
||||
|
||||
|
|
|
@ -404,8 +404,20 @@ save_t save = {
|
|||
|
||||
.has_rapier_class = true, // for testing; should be false in prod
|
||||
.has_bonus_circuts = true, // for testing; should be false in prod
|
||||
.highscores_name = {0,0,0,0},
|
||||
|
||||
.buttons = {
|
||||
[A_UP] = {INPUT_KEY_UP, INPUT_GAMEPAD_DPAD_UP},
|
||||
[A_DOWN] = {INPUT_KEY_DOWN, INPUT_GAMEPAD_DPAD_DOWN},
|
||||
[A_LEFT] = {INPUT_KEY_LEFT, INPUT_GAMEPAD_DPAD_LEFT},
|
||||
[A_RIGHT] = {INPUT_KEY_RIGHT, INPUT_GAMEPAD_DPAD_RIGHT},
|
||||
[A_BRAKE_LEFT] = {INPUT_KEY_C, INPUT_GAMEPAD_L_SHOULDER},
|
||||
[A_BRAKE_RIGHT] = {INPUT_KEY_V, INPUT_GAMEPAD_R_SHOULDER},
|
||||
[A_THRUST] = {INPUT_KEY_X, INPUT_GAMEPAD_A},
|
||||
[A_FIRE] = {INPUT_KEY_Z, INPUT_GAMEPAD_X},
|
||||
[A_CHANGE_VIEW] = {INPUT_KEY_A, INPUT_GAMEPAD_Y},
|
||||
},
|
||||
|
||||
.highscores_name = {0,0,0,0},
|
||||
.highscores = {
|
||||
[RACE_CLASS_VENOM] = {
|
||||
{
|
||||
|
@ -534,7 +546,7 @@ void game_init() {
|
|||
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_KEY_X, A_MENU_SELECT);
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_KEY_RETURN, A_MENU_START);
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_KEY_ESCAPE, A_MENU_START);
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_KEY_ESCAPE, A_MENU_QUIT);
|
||||
|
||||
// Gamepad
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_GAMEPAD_DPAD_UP, A_MENU_UP);
|
||||
|
@ -552,41 +564,17 @@ void game_init() {
|
|||
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_GAMEPAD_A, A_MENU_SELECT);
|
||||
input_bind(INPUT_LAYER_SYSTEM, INPUT_GAMEPAD_START, A_MENU_START);
|
||||
|
||||
|
||||
|
||||
|
||||
// User defined
|
||||
// TODO: these should be configurable and stored in the save struct
|
||||
// Keyboard
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_UP, A_UP);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_DOWN, A_DOWN);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_LEFT, A_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_RIGHT, A_RIGHT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_C, A_BRAKE_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_V, A_BRAKE_RIGHT);
|
||||
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_X, A_THRUST);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_Z, A_FIRE);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_KEY_A, A_CHANGE_VIEW);
|
||||
|
||||
// Gamepad
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_DPAD_UP, A_UP);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_DPAD_DOWN, A_DOWN);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_DPAD_LEFT, A_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_DPAD_RIGHT, A_RIGHT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_STICK_UP, A_UP);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_STICK_DOWN, A_DOWN);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_STICK_LEFT, A_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_STICK_RIGHT, A_RIGHT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_TRIGGER, A_BRAKE_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_R_TRIGGER, A_BRAKE_RIGHT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_L_SHOULDER, A_BRAKE_LEFT);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_R_SHOULDER, A_BRAKE_RIGHT);
|
||||
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_A, A_THRUST);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_X, A_FIRE);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_Y, A_CHANGE_VIEW);
|
||||
input_bind(INPUT_LAYER_USER, INPUT_GAMEPAD_SELECT, A_CHANGE_VIEW);
|
||||
// User defined, loaded from the save struct
|
||||
for (int action = 0; action < len(save.buttons); action++) {
|
||||
if (save.buttons[action][0] != INPUT_INVALID) {
|
||||
input_bind(INPUT_LAYER_USER, save.buttons[action][0], action);
|
||||
}
|
||||
if (save.buttons[action][1] != INPUT_INVALID) {
|
||||
input_bind(INPUT_LAYER_USER, save.buttons[action][1], action);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
game_set_scene(GAME_SCENE_INTRO);
|
||||
|
|
|
@ -20,15 +20,6 @@
|
|||
#define SAVE_DATA_MAGIC 0x64736f77
|
||||
|
||||
typedef enum {
|
||||
A_MENU_UP,
|
||||
A_MENU_DOWN,
|
||||
A_MENU_LEFT,
|
||||
A_MENU_RIGHT,
|
||||
A_MENU_BACK,
|
||||
A_MENU_SELECT,
|
||||
A_MENU_START,
|
||||
A_MENU_QUIT,
|
||||
|
||||
A_UP,
|
||||
A_DOWN,
|
||||
A_LEFT,
|
||||
|
@ -38,6 +29,16 @@ typedef enum {
|
|||
A_THRUST,
|
||||
A_FIRE,
|
||||
A_CHANGE_VIEW,
|
||||
NUM_GAME_ACTIONS,
|
||||
|
||||
A_MENU_UP,
|
||||
A_MENU_DOWN,
|
||||
A_MENU_LEFT,
|
||||
A_MENU_RIGHT,
|
||||
A_MENU_BACK,
|
||||
A_MENU_SELECT,
|
||||
A_MENU_START,
|
||||
A_MENU_QUIT,
|
||||
} action_t;
|
||||
|
||||
|
||||
|
@ -247,6 +248,9 @@ typedef struct {
|
|||
|
||||
uint32_t has_rapier_class;
|
||||
uint32_t has_bonus_circuts;
|
||||
|
||||
uint8_t buttons[NUM_GAME_ACTIONS][2];
|
||||
|
||||
char highscores_name[4];
|
||||
highscores_t highscores[NUM_RACE_CLASSES][NUM_CIRCUTS][NUM_HIGHSCORE_TABS];
|
||||
} save_t;
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
#include "../system.h"
|
||||
#include "../mem.h"
|
||||
#include "../platform.h"
|
||||
#include "../input.h"
|
||||
|
||||
#include "menu.h"
|
||||
#include "main_menu.h"
|
||||
|
@ -133,8 +134,121 @@ static void page_options_init(menu_t *menu) {
|
|||
// -----------------------------------------------------------------------------
|
||||
// Options Controls
|
||||
|
||||
static const char *button_names[NUM_GAME_ACTIONS][2] = {};
|
||||
static int control_current_action;
|
||||
static float await_input_deadline;
|
||||
|
||||
void button_capture(void *user, button_t button, int32_t ascii_char) {
|
||||
if (button == INPUT_INVALID) {
|
||||
return;
|
||||
}
|
||||
|
||||
menu_t *menu = (menu_t *)user;
|
||||
if (button == INPUT_KEY_ESCAPE) {
|
||||
input_capture(NULL, NULL);
|
||||
menu_pop(menu);
|
||||
return;
|
||||
}
|
||||
|
||||
int index = button < INPUT_KEY_MAX ? 0 : 1; // joypad or keyboard
|
||||
|
||||
// unbind this button if it's bound anywhere
|
||||
for (int i = 0; i < len(save.buttons); i++) {
|
||||
if (save.buttons[i][index] == button) {
|
||||
save.buttons[i][index] = INPUT_INVALID;
|
||||
}
|
||||
}
|
||||
input_capture(NULL, NULL);
|
||||
input_bind(INPUT_LAYER_USER, button, control_current_action);
|
||||
save.buttons[control_current_action][index] = button;
|
||||
save.is_dirty = true;
|
||||
menu_pop(menu);
|
||||
}
|
||||
|
||||
static void page_options_control_set_draw(menu_t *menu, int data) {
|
||||
float remaining = await_input_deadline - platform_now();
|
||||
|
||||
menu_page_t *page = &menu->pages[menu->index];
|
||||
char remaining_text[2] = { '0' + (uint8_t)clamp(remaining + 1, 0, 3), '\0'};
|
||||
vec2i_t pos = vec2i(page->items_pos.x, page->items_pos.y + 24);
|
||||
ui_draw_text_centered(remaining_text, ui_scaled_pos(page->items_anchor, pos), UI_SIZE_16, UI_COLOR_DEFAULT);
|
||||
|
||||
if (remaining <= 0) {
|
||||
input_capture(NULL, NULL);
|
||||
menu_pop(menu);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void page_options_controls_set_init(menu_t *menu, int data) {
|
||||
control_current_action = data;
|
||||
await_input_deadline = platform_now() + 3;
|
||||
|
||||
menu_page_t *page = menu_push(menu, "AWAITING INPUT", page_options_control_set_draw);
|
||||
input_capture(button_capture, menu);
|
||||
}
|
||||
|
||||
|
||||
static void page_options_control_draw(menu_t *menu, int data) {
|
||||
menu_page_t *page = &menu->pages[menu->index];
|
||||
|
||||
int left = page->items_pos.x + page->block_width - 100;
|
||||
int right = page->items_pos.x + page->block_width;
|
||||
int line_y = page->items_pos.y - 20;
|
||||
|
||||
vec2i_t left_head_pos = vec2i(left - ui_text_width("KEYBOARD", UI_SIZE_8), line_y);
|
||||
ui_draw_text("KEYBOARD", ui_scaled_pos(page->items_anchor, left_head_pos), UI_SIZE_8, UI_COLOR_DEFAULT);
|
||||
|
||||
vec2i_t right_head_pos = vec2i(right - ui_text_width("JOYSTICK", UI_SIZE_8), line_y);
|
||||
ui_draw_text("JOYSTICK", ui_scaled_pos(page->items_anchor, right_head_pos), UI_SIZE_8, UI_COLOR_DEFAULT);
|
||||
line_y += 20;
|
||||
|
||||
for (int action = 0; action < NUM_GAME_ACTIONS; action++) {
|
||||
rgba_t text_color = UI_COLOR_DEFAULT;
|
||||
if (action == data) {
|
||||
text_color = UI_COLOR_ACCENT;
|
||||
}
|
||||
|
||||
if (save.buttons[action][0] != INPUT_INVALID) {
|
||||
const char *name = input_button_to_name(save.buttons[action][0]);
|
||||
if (!name) {
|
||||
name = "UNKNWN";
|
||||
}
|
||||
vec2i_t pos = vec2i(left - ui_text_width(name, UI_SIZE_8), line_y);
|
||||
ui_draw_text(name, ui_scaled_pos(page->items_anchor, pos), UI_SIZE_8, text_color);
|
||||
}
|
||||
if (save.buttons[action][1] != INPUT_INVALID) {
|
||||
const char *name = input_button_to_name(save.buttons[action][1]);
|
||||
if (!name) {
|
||||
name = "UNKNWN";
|
||||
}
|
||||
vec2i_t pos = vec2i(right - ui_text_width(name, UI_SIZE_8), line_y);
|
||||
ui_draw_text(name, ui_scaled_pos(page->items_anchor, pos), UI_SIZE_8, text_color);
|
||||
}
|
||||
line_y += 12;
|
||||
}
|
||||
}
|
||||
|
||||
static void page_options_controls_init(menu_t *menu) {
|
||||
menu_page_t *page = menu_push(menu, "TODO", page_options_draw);
|
||||
menu_page_t *page = menu_push(menu, "CONTROLS", page_options_control_draw);
|
||||
flags_set(page->layout_flags, MENU_VERTICAL | MENU_FIXED);
|
||||
page->title_pos = vec2i(-160, -100);
|
||||
page->title_anchor = UI_POS_MIDDLE | UI_POS_CENTER;
|
||||
page->items_pos = vec2i(-160, -50);
|
||||
page->block_width = 320;
|
||||
page->items_anchor = UI_POS_MIDDLE | UI_POS_CENTER;
|
||||
|
||||
// const char *thrust_name = button_name(A_THRUST);
|
||||
// printf("thrust: %s\n", thrust_name);
|
||||
menu_page_add_button(page, A_UP, "UP", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_DOWN, "DOWN", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_LEFT, "LEFT", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_RIGHT, "RIGHT", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_BRAKE_LEFT, "BRAKE L", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_BRAKE_RIGHT, "BRAKE R", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_THRUST, "THRUST", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_FIRE, "FIRE", page_options_controls_set_init);
|
||||
menu_page_add_button(page, A_CHANGE_VIEW, "VIEW", page_options_controls_set_init);
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
@ -178,7 +292,7 @@ static void page_options_video_init(menu_t *menu) {
|
|||
flags_set(page->layout_flags, MENU_VERTICAL | MENU_FIXED);
|
||||
page->title_pos = vec2i(-160, -100);
|
||||
page->title_anchor = UI_POS_MIDDLE | UI_POS_CENTER;
|
||||
page->items_pos = vec2i(-160, -80);
|
||||
page->items_pos = vec2i(-160, -60);
|
||||
page->block_width = 320;
|
||||
page->items_anchor = UI_POS_MIDDLE | UI_POS_CENTER;
|
||||
|
||||
|
|
Loading…
Reference in a new issue