Allow to exit the options menu without saving changes made (#484)

* Allow exiting options menu without saving

* Change "Back" button text to "Cancel" to be more explicit

* clang format

* fix load_game

* use proper existing defines for options default values

* fix buttons' array sizes

---------

Co-authored-by: MathisMartin31 <mathis.martin31@gmail.com>
This commit is contained in:
Geralt
2026-05-19 18:10:49 -07:00
committed by GitHub
co-authored by MathisMartin31
parent 9b85329669
commit 69403f059f
3 changed files with 120 additions and 132 deletions
Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.1 KiB

After

Width:  |  Height:  |  Size: 2.1 KiB

+109 -121
View File
@@ -19,15 +19,14 @@
#include <tonc_math.h> #include <tonc_math.h>
#include <tonc_memdef.h> #include <tonc_memdef.h>
// Button indices enum OptionButtonRows
enum OptionButtons
{ {
GAME_SPEED_BTN_IDX, GAME_SPEED_ROW_IDX,
HIGH_CONTRAST_BTN_IDX, HIGH_CONTRAST_ROW_IDX,
MUSIC_VOLUME_BTN_IDX, MUSIC_VOLUME_ROW_IDX,
SOUND_VOLUME_BTN_IDX, SOUND_VOLUME_ROW_IDX,
BACK_BTN_IDX, SAVE_BACK_ROW_IDX,
NB_OPTIONS_BUTTONS NB_OPTIONS_ROWS
}; };
enum OptionSpeedButtons enum OptionSpeedButtons
{ {
@@ -38,22 +37,26 @@ enum OptionSpeedButtons
// Color palette indices // Color palette indices
#define MENU_BUTTON_MAIN_COLOR_PAL_IDX 1 #define MENU_BUTTON_MAIN_COLOR_PAL_IDX 1
#define BACK_BUTTON_MAIN_COLOR_PAL_IDX 3 #define SAVE_BUTTON_MAIN_COLOR_PAL_IDX 3
#define SPEED_DOWN_BUTTON_OUTLINE_COLOR_PAL_IDX 4 #define BACK_BUTTON_MAIN_COLOR_PAL_IDX 4
#define SPEED_BUTTON_OUTLINE_COLOR_PAL_IDX 5 #define SPEED_DOWN_BUTTON_OUTLINE_COLOR_PAL_IDX 5
#define SPEED_UP_BUTTON_OUTLINE_COLOR_PAL_IDX 6 #define SPEED_BUTTON_OUTLINE_COLOR_PAL_IDX 6
#define CONTRAST_BUTTON_OUTLINE_COLOR_PAL_IDX 7 #define SPEED_UP_BUTTON_OUTLINE_COLOR_PAL_IDX 7
#define MUSIC_BUTTON_OUTLINE_COLOR_PAL_IDX 8 #define CONTRAST_BUTTON_OUTLINE_COLOR_PAL_IDX 8
#define SOUND_BUTTON_OUTLINE_COLOR_PAL_IDX 9 #define MUSIC_BUTTON_OUTLINE_COLOR_PAL_IDX 9
#define BACK_BUTTON_OUTLINE_COLOR_PAL_IDX 10 #define SOUND_BUTTON_OUTLINE_COLOR_PAL_IDX 10
#define SAVE_BUTTON_OUTLINE_COLOR_PAL_IDX 11
#define BACK_BUTTON_OUTLINE_COLOR_PAL_IDX 12
// Define selection grid for the menu buttons // Define selection grid for the menu buttons
static void game_speed_down_on_pressed(void); static void game_speed_down_on_pressed(void);
static void game_speed_up_on_pressed(void); static void game_speed_up_on_pressed(void);
static void high_contrast_on_pressed(void); static void high_contrast_on_pressed(void);
static void save_on_pressed(void);
static void back_on_pressed(void); static void back_on_pressed(void);
static int options_menu_return_row_size(void); static int options_menu_return_upper_rows_size(void);
static int options_menu_return_bottom_row_size(void);
static void options_menu_row_on_key_transit(SelectionGrid* selection_grid, Selection* selection); static void options_menu_row_on_key_transit(SelectionGrid* selection_grid, Selection* selection);
static bool game_speed_row_on_selection_changed( static bool game_speed_row_on_selection_changed(
SelectionGrid* selection_grid, SelectionGrid* selection_grid,
@@ -83,49 +86,52 @@ static bool regular_button_row_on_selection_changed(
// clang-format off // clang-format off
static SelectionGridRow options_menu_selection_rows[] = { static SelectionGridRow options_menu_selection_rows[] = {
{ {
GAME_SPEED_BTN_IDX, GAME_SPEED_ROW_IDX,
options_menu_return_row_size, options_menu_return_upper_rows_size,
game_speed_row_on_selection_changed, game_speed_row_on_selection_changed,
NULL, NULL,
{.wrap = true} // The wrapping is used to allow button activation with Left/Right arrows by {.wrap = true} // The wrapping is used to allow button activation with Left/Right arrows by
// putting logic into the `game_speed_row_on_selection_changed` function // putting logic into the `game_speed_row_on_selection_changed` function
}, },
{ {
HIGH_CONTRAST_BTN_IDX, HIGH_CONTRAST_ROW_IDX,
options_menu_return_row_size, options_menu_return_upper_rows_size,
regular_button_row_on_selection_changed, regular_button_row_on_selection_changed,
options_menu_row_on_key_transit, options_menu_row_on_key_transit,
{.wrap = false} {.wrap = false}
}, },
{ {
MUSIC_VOLUME_BTN_IDX, MUSIC_VOLUME_ROW_IDX,
options_menu_return_row_size, options_menu_return_upper_rows_size,
music_volume_row_on_selection_changed, music_volume_row_on_selection_changed,
NULL, NULL,
{.wrap = true} // Same trick as Game Speed button {.wrap = true} // Same trick as Game Speed button
}, },
{ {
SOUND_VOLUME_BTN_IDX, SOUND_VOLUME_ROW_IDX,
options_menu_return_row_size, options_menu_return_upper_rows_size,
sound_volume_row_on_selection_changed, sound_volume_row_on_selection_changed,
NULL, NULL,
{.wrap = true} // Same trick as Game Speed button {.wrap = true} // Same trick as Game Speed button
}, },
{ {
BACK_BTN_IDX, SAVE_BACK_ROW_IDX,
options_menu_return_row_size, options_menu_return_bottom_row_size,
regular_button_row_on_selection_changed, regular_button_row_on_selection_changed,
options_menu_row_on_key_transit, options_menu_row_on_key_transit,
{.wrap = false} {.wrap = false}
} }
}; };
static Button options_menu_buttons[] = { static Button options_menu_buttons[NB_OPTIONS_ROWS][2] = {
{SPEED_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}, {{SPEED_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}},
{CONTRAST_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, high_contrast_on_pressed, NULL}, {{CONTRAST_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, high_contrast_on_pressed, NULL}},
{MUSIC_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}, {{MUSIC_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}},
{SOUND_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}, {{SOUND_BUTTON_OUTLINE_COLOR_PAL_IDX, MENU_BUTTON_MAIN_COLOR_PAL_IDX, NULL, NULL}},
{BACK_BUTTON_OUTLINE_COLOR_PAL_IDX, BACK_BUTTON_MAIN_COLOR_PAL_IDX, back_on_pressed, NULL} {
{SAVE_BUTTON_OUTLINE_COLOR_PAL_IDX, SAVE_BUTTON_MAIN_COLOR_PAL_IDX, save_on_pressed, NULL},
{BACK_BUTTON_OUTLINE_COLOR_PAL_IDX, BACK_BUTTON_MAIN_COLOR_PAL_IDX, back_on_pressed, NULL},
}
}; };
static Button game_speed_buttons[] = { static Button game_speed_buttons[] = {
@@ -138,7 +144,7 @@ const Selection OPTIONS_MENU_INIT_SEL = {0, 0};
static SelectionGrid options_menu_selection_grid = { static SelectionGrid options_menu_selection_grid = {
options_menu_selection_rows, options_menu_selection_rows,
NB_OPTIONS_BUTTONS, NB_OPTIONS_ROWS,
OPTIONS_MENU_INIT_SEL OPTIONS_MENU_INIT_SEL
}; };
@@ -146,28 +152,28 @@ static SelectionGrid options_menu_selection_grid = {
// clang-format off // clang-format off
// Values in tiles // Values in tiles
static const Rect OPTIONS_SPEED_DOWN_ACTIVE_BTN_SRC_RECT = { 3, 20, 3, 21}; static const Rect OPTIONS_SPEED_DOWN_ACTIVE_BTN_SRC_RECT = { 0, 20, 0, 21};
static const Rect OPTIONS_SPEED_DOWN_DISABLED_BTN_SRC_RECT = { 9, 22, 9, 23}; static const Rect OPTIONS_SPEED_DOWN_DISABLED_BTN_SRC_RECT = { 6, 22, 6, 23};
static const BG_POINT OPTIONS_SPEED_DOWN_BTN_DEST_POS = {11, 3}; static const BG_POINT OPTIONS_SPEED_DOWN_BTN_DEST_POS = {11, 3};
static const Rect OPTIONS_SPEED_UP_ACTIVE_BTN_SRC_RECT = {10, 20, 10, 21}; static const Rect OPTIONS_SPEED_UP_ACTIVE_BTN_SRC_RECT = { 7, 20, 7, 21};
static const Rect OPTIONS_SPEED_UP_DISABLED_BTN_SRC_RECT = {10, 22, 10, 23}; static const Rect OPTIONS_SPEED_UP_DISABLED_BTN_SRC_RECT = { 7, 22, 7, 23};
static const BG_POINT OPTIONS_SPEED_UP_BTN_DEST_POS = {18, 3}; static const BG_POINT OPTIONS_SPEED_UP_BTN_DEST_POS = {18, 3};
static const Rect OPTIONS_SPEED_VALUES[GAME_SPEED_MAX] = { { 6, 20, 7, 21}, static const Rect OPTIONS_SPEED_VALUES[GAME_SPEED_MAX] = { { 3, 20, 4, 21},
{ 3, 22, 4, 23}, { 0, 22, 1, 23},
{ 5, 22, 6, 23}, { 2, 22, 3, 23},
{ 7, 22, 8, 23} }; { 4, 22, 5, 23} };
static const BG_POINT OPTIONS_SPEED_VALUE_DEST_POS = {14, 3}; static const BG_POINT OPTIONS_SPEED_VALUE_DEST_POS = {14, 3};
static const Rect OPTIONS_CONTRAST_VALUE_YES_SRC_RECT = { 4, 24, 7, 25}; static const Rect OPTIONS_CONTRAST_VALUE_YES_SRC_RECT = { 1, 24, 4, 25};
static const Rect OPTIONS_CONTRAST_VALUE_NO_SRC_RECT = { 9, 24, 12, 25}; static const Rect OPTIONS_CONTRAST_VALUE_NO_SRC_RECT = { 6, 24, 9, 25};
static const BG_POINT OPTIONS_CONTRAST_VALUE_DEST_POS = {13, 7}; static const BG_POINT OPTIONS_CONTRAST_VALUE_DEST_POS = {13, 7};
static const Rect OPTIONS_MUSIC_SLIDER_FULL_SRC = {12, 20, 12, 20}; static const Rect OPTIONS_MUSIC_SLIDER_FULL_SRC = { 9, 20, 9, 20};
static const Rect OPTIONS_MUSIC_SLIDER_MID_SRC = {13, 20, 13, 20}; static const Rect OPTIONS_MUSIC_SLIDER_MID_SRC = {10, 20, 10, 20};
static const Rect OPTIONS_MUSIC_SLIDER_EMPTY_SRC = {14, 20, 14, 20}; static const Rect OPTIONS_MUSIC_SLIDER_EMPTY_SRC = {11, 20, 11, 20};
static const Rect OPTIONS_SOUND_SLIDER_FULL_SRC = {12, 22, 12, 22}; static const Rect OPTIONS_SOUND_SLIDER_FULL_SRC = { 9, 22, 9, 22};
static const Rect OPTIONS_SOUND_SLIDER_MID_SRC = {13, 22, 13, 22}; static const Rect OPTIONS_SOUND_SLIDER_MID_SRC = {10, 22, 10, 22};
static const Rect OPTIONS_SOUND_SLIDER_EMPTY_SRC = {14, 22, 14, 22}; static const Rect OPTIONS_SOUND_SLIDER_EMPTY_SRC = {11, 22, 11, 22};
static const BG_POINT OPTIONS_MUSIC_SLIDER_START_POS = { 5, 11}; static const BG_POINT OPTIONS_MUSIC_SLIDER_START_POS = { 5, 11};
static const BG_POINT OPTIONS_SOUND_SLIDER_START_POS = { 5, 14}; static const BG_POINT OPTIONS_SOUND_SLIDER_START_POS = { 5, 14};
static const BG_POINT OPTIONS_MUSIC_SLIDER_END_POS = {24, 11}; static const BG_POINT OPTIONS_MUSIC_SLIDER_END_POS = {24, 11};
@@ -184,16 +190,13 @@ static const BG_POINT OPTIONS_MUSIC_VOLUME_TEXT_POS = { 56, 80};
static const BG_POINT OPTIONS_MUSIC_VALUE_TEXT_POS = {160, 80}; static const BG_POINT OPTIONS_MUSIC_VALUE_TEXT_POS = {160, 80};
static const BG_POINT OPTIONS_SOUND_VOLUME_TEXT_POS = { 56, 104}; static const BG_POINT OPTIONS_SOUND_VOLUME_TEXT_POS = { 56, 104};
static const BG_POINT OPTIONS_SOUND_VALUE_TEXT_POS = {160, 104}; static const BG_POINT OPTIONS_SOUND_VALUE_TEXT_POS = {160, 104};
static const BG_POINT OPTIONS_BACK_SAVE_TEXT_POS = { 72, 136}; static const BG_POINT OPTIONS_BACK_SAVE_TEXT_POS = { 64, 136};
// clang-format on // clang-format on
#define GAME_SPEED_ARROW_HIGHLIGHT_DURATION 10 #define GAME_SPEED_ARROW_HIGHLIGHT_DURATION 10
enum OptionSpeedButtons game_speed_arrow_highlight_button = GAME_SPEED_UP_BTN_IDX; enum OptionSpeedButtons game_speed_arrow_highlight_button = GAME_SPEED_UP_BTN_IDX;
static s32 game_speed_arrow_highlight_start = UNDEFINED; static s32 game_speed_arrow_highlight_start = UNDEFINED;
static bool any_value_changed = false;
static bool back_btn_is_save_state = false;
static void disable_all_game_speed_outlines_except_self(enum OptionSpeedButtons highlighted_btn) static void disable_all_game_speed_outlines_except_self(enum OptionSpeedButtons highlighted_btn)
{ {
for (int i = 0; i < NB_GAME_SPEED_BUTTONS; i++) for (int i = 0; i < NB_GAME_SPEED_BUTTONS; i++)
@@ -202,14 +205,19 @@ static void disable_all_game_speed_outlines_except_self(enum OptionSpeedButtons
} }
} }
static void disable_all_outlines_except_self(enum OptionButtons highlighted_btn) static void disable_all_outlines_except_self(Selection sel_btn)
{ {
// These two get disabled no matter what here // These two get disabled no matter what here
disable_all_game_speed_outlines_except_self(NB_GAME_SPEED_BUTTONS); disable_all_game_speed_outlines_except_self(NB_GAME_SPEED_BUTTONS);
for (int i = 0; i < NB_OPTIONS_BUTTONS; i++) for (int j = 0; j < NB_OPTIONS_ROWS; j++)
{ {
button_set_highlight(&options_menu_buttons[i], i == highlighted_btn); int nb_buttons_in_row = (j == SAVE_BACK_ROW_IDX) ? options_menu_return_bottom_row_size()
: options_menu_return_upper_rows_size();
for (int i = 0; i < nb_buttons_in_row; i++)
{
button_set_highlight(&options_menu_buttons[j][i], i == sel_btn.x && j == sel_btn.y);
}
} }
} }
@@ -244,8 +252,6 @@ static void update_game_speed_button_graphics()
OPTIONS_SPEED_VALUES[g_game_vars.game_speed - 1], OPTIONS_SPEED_VALUES[g_game_vars.game_speed - 1],
OPTIONS_SPEED_VALUE_DEST_POS OPTIONS_SPEED_VALUE_DEST_POS
); );
any_value_changed = true;
} }
static void update_high_contrast_button_graphics() static void update_high_contrast_button_graphics()
@@ -258,11 +264,9 @@ static void update_high_contrast_button_graphics()
{ {
main_bg_se_copy_rect(OPTIONS_CONTRAST_VALUE_NO_SRC_RECT, OPTIONS_CONTRAST_VALUE_DEST_POS); main_bg_se_copy_rect(OPTIONS_CONTRAST_VALUE_NO_SRC_RECT, OPTIONS_CONTRAST_VALUE_DEST_POS);
} }
any_value_changed = true;
} }
static void update_volume_slider_graphics(enum OptionButtons slider_idx) static void update_volume_slider_graphics(enum OptionButtonRows sel_row)
{ {
u8 slider_value; u8 slider_value;
BG_POINT slider_segment_dest; BG_POINT slider_segment_dest;
@@ -272,9 +276,9 @@ static void update_volume_slider_graphics(enum OptionButtons slider_idx)
Rect slider_segment_empty; Rect slider_segment_empty;
BG_POINT slider_text_pos; BG_POINT slider_text_pos;
switch (slider_idx) switch (sel_row)
{ {
case MUSIC_VOLUME_BTN_IDX: case MUSIC_VOLUME_ROW_IDX:
slider_value = g_game_vars.music_volume; slider_value = g_game_vars.music_volume;
slider_segment_dest = OPTIONS_MUSIC_SLIDER_START_POS; slider_segment_dest = OPTIONS_MUSIC_SLIDER_START_POS;
slider_segment_length = OPTIONS_MUSIC_SLIDER_SEGMENT_LENGTH; slider_segment_length = OPTIONS_MUSIC_SLIDER_SEGMENT_LENGTH;
@@ -283,7 +287,7 @@ static void update_volume_slider_graphics(enum OptionButtons slider_idx)
slider_segment_empty = OPTIONS_MUSIC_SLIDER_EMPTY_SRC; slider_segment_empty = OPTIONS_MUSIC_SLIDER_EMPTY_SRC;
slider_text_pos = OPTIONS_MUSIC_VALUE_TEXT_POS; slider_text_pos = OPTIONS_MUSIC_VALUE_TEXT_POS;
break; break;
case SOUND_VOLUME_BTN_IDX: case SOUND_VOLUME_ROW_IDX:
slider_value = g_game_vars.sound_volume; slider_value = g_game_vars.sound_volume;
slider_segment_dest = OPTIONS_SOUND_SLIDER_START_POS; slider_segment_dest = OPTIONS_SOUND_SLIDER_START_POS;
slider_segment_length = OPTIONS_SOUND_SLIDER_SEGMENT_LENGTH; slider_segment_length = OPTIONS_SOUND_SLIDER_SEGMENT_LENGTH;
@@ -338,20 +342,6 @@ static void update_volume_slider_graphics(enum OptionButtons slider_idx)
TTE_WHITE_PB, TTE_WHITE_PB,
(slider_value * VOLUME_OPTION_INCREMENT) (slider_value * VOLUME_OPTION_INCREMENT)
); );
any_value_changed = true;
}
static void change_back_save_text(bool is_back)
{
char* btn_text = is_back ? " Back " : "Save Changes";
tte_printf(
"#{P:%d,%d; cx:0x%X000}%s",
OPTIONS_BACK_SAVE_TEXT_POS.x,
OPTIONS_BACK_SAVE_TEXT_POS.y,
TTE_WHITE_PB,
btn_text
);
} }
void game_options_menu_change_background(void) void game_options_menu_change_background(void)
@@ -387,7 +377,12 @@ void game_options_menu_change_background(void)
OPTIONS_SOUND_VOLUME_TEXT_POS.y, OPTIONS_SOUND_VOLUME_TEXT_POS.y,
TTE_WHITE_PB TTE_WHITE_PB
); );
change_back_save_text(true); tte_printf(
"#{P:%d,%d; cx:0x%X000}Save Cancel",
OPTIONS_BACK_SAVE_TEXT_POS.x,
OPTIONS_BACK_SAVE_TEXT_POS.y,
TTE_WHITE_PB
);
} }
void game_options_menu_on_init(void) void game_options_menu_on_init(void)
@@ -396,17 +391,13 @@ void game_options_menu_on_init(void)
// Select game speed button by default // Select game speed button by default
options_menu_selection_grid.selection = OPTIONS_MENU_INIT_SEL; options_menu_selection_grid.selection = OPTIONS_MENU_INIT_SEL;
disable_all_outlines_except_self(GAME_SPEED_BTN_IDX); disable_all_outlines_except_self(OPTIONS_MENU_INIT_SEL);
// Do an update on the first frame // Do an update on the first frame
update_game_speed_button_graphics(); update_game_speed_button_graphics();
update_high_contrast_button_graphics(); update_high_contrast_button_graphics();
update_volume_slider_graphics(MUSIC_VOLUME_BTN_IDX); update_volume_slider_graphics(MUSIC_VOLUME_ROW_IDX);
update_volume_slider_graphics(SOUND_VOLUME_BTN_IDX); update_volume_slider_graphics(SOUND_VOLUME_ROW_IDX);
// Prevent "Back" button to become "Save Changes" when we first load the data,
// the player hasn't technically changed anything so it would be confusing.
any_value_changed = false;
} }
void game_options_menu_on_update(void) void game_options_menu_on_update(void)
@@ -421,17 +412,6 @@ void game_options_menu_on_update(void)
game_speed_arrow_highlight_start = UNDEFINED; game_speed_arrow_highlight_start = UNDEFINED;
button_set_highlight(&game_speed_buttons[game_speed_arrow_highlight_button], false); button_set_highlight(&game_speed_buttons[game_speed_arrow_highlight_button], false);
} }
// Except on the first update where it is forced to display the loaded values
// instead of the default ones, if any value was changed, edit the last button
// text to read "Save Changes" instead of "Back"
if (any_value_changed && !back_btn_is_save_state)
{
change_back_save_text(false);
back_btn_is_save_state = true;
}
any_value_changed = false;
} }
void game_options_menu_on_exit(void) void game_options_menu_on_exit(void)
@@ -467,50 +447,58 @@ static void high_contrast_on_pressed(void)
} }
/** /**
* @brief Handles input for the Back/Save button. * @brief Handles input for the Save button.
*/ */
static void back_on_pressed(void) static void save_on_pressed(void)
{
if (back_btn_is_save_state)
{ {
save_options(); save_options();
change_back_save_text(true);
back_btn_is_save_state = false;
}
else
{
game_change_state(GAME_STATE_MAIN_MENU); game_change_state(GAME_STATE_MAIN_MENU);
} }
}
/** /**
* @brief Gives the width of options menu rows in selection grid. * @brief Handles input for the Back button.
*
* @returns Always 1, all rows contain only 1 button. Could have been a define
* but I had to make this a function so it could be given to the
* SelectionGrid constructor.
*/ */
static int options_menu_return_row_size(void) static void back_on_pressed(void)
{
load_options();
game_change_state(GAME_STATE_MAIN_MENU);
}
/**
* @brief Gives the width of upper options menu rows in selection grid.
*
* @returns 1
*/
static int options_menu_return_upper_rows_size(void)
{ {
return 1; return 1;
} }
/**
* @brief Gives the width of the Save and Back buttons' row.
*
* @returns 2
*/
static int options_menu_return_bottom_row_size(void)
{
return 2;
}
static void change_button_highlight( static void change_button_highlight(
int row_idx, int row_idx,
const Selection* prev_selection, const Selection* prev_selection,
const Selection* new_selection const Selection* new_selection
) )
{ {
if (prev_selection->y == row_idx && prev_selection->x >= 0 && if (prev_selection->y == row_idx)
prev_selection->x < NB_OPTIONS_BUTTONS)
{ {
button_set_highlight(&options_menu_buttons[row_idx], false); button_set_highlight(&options_menu_buttons[row_idx][prev_selection->x], false);
} }
if (new_selection->y == row_idx) if (new_selection->y == row_idx)
{ {
play_sfx(SFX_BUTTON, MM_BASE_PITCH_RATE, BUTTON_SFX_VOLUME); play_sfx(SFX_BUTTON, MM_BASE_PITCH_RATE, BUTTON_SFX_VOLUME);
button_set_highlight(&options_menu_buttons[row_idx], true); button_set_highlight(&options_menu_buttons[row_idx][new_selection->x], true);
} }
} }
@@ -555,7 +543,7 @@ static void options_menu_row_on_key_transit(SelectionGrid* selection_grid, Selec
{ {
if (key_hit(SELECT_CARD)) if (key_hit(SELECT_CARD))
{ {
button_press(&options_menu_buttons[selection->y]); button_press(&options_menu_buttons[selection->y][selection->x]);
} }
} }
@@ -591,7 +579,7 @@ static bool music_volume_row_on_selection_changed(
g_game_vars.music_volume++; g_game_vars.music_volume++;
} }
update_volume_slider_graphics(MUSIC_VOLUME_BTN_IDX); update_volume_slider_graphics(MUSIC_VOLUME_ROW_IDX);
mmSetModuleVolume(MM_MODULE_FULL_VOLUME * g_game_vars.music_volume / VOLUME_OPTION_MAX); mmSetModuleVolume(MM_MODULE_FULL_VOLUME * g_game_vars.music_volume / VOLUME_OPTION_MAX);
return true; return true;
@@ -618,7 +606,7 @@ static bool sound_volume_row_on_selection_changed(
g_game_vars.sound_volume++; g_game_vars.sound_volume++;
} }
update_volume_slider_graphics(SOUND_VOLUME_BTN_IDX); update_volume_slider_graphics(SOUND_VOLUME_ROW_IDX);
return true; return true;
} }
+8 -8
View File
@@ -155,10 +155,10 @@ static const SaveHeader SaveHeader_default = {
*/ */
static const SaveOptions SaveOptions_default = { static const SaveOptions SaveOptions_default = {
.tag_options = "- OPTIONS DATA -", .tag_options = "- OPTIONS DATA -",
.game_speed = 0, .game_speed = GAME_SPEED_MIN,
.high_contrast = false, .high_contrast = DEFAULT_HIGH_CONTRAST,
.music_volume = 0, .music_volume = VOLUME_OPTION_MAX,
.sound_volume = 0, .sound_volume = VOLUME_OPTION_MAX,
.padding = {UNDEFINED, UNDEFINED, UNDEFINED}, .padding = {UNDEFINED, UNDEFINED, UNDEFINED},
}; };
@@ -306,11 +306,11 @@ void save_options(void)
void load_options(void) void load_options(void)
{ {
SaveHeader header; SaveHeader header;
if (!get_save_header(&header) || !(header.valid_sections & SAVE_SECTION_FLAG_OPTIONS))
return;
SaveOptions options = SaveOptions_default; SaveOptions options = SaveOptions_default;
// If options data doesn't exist or is invalid, just don't read from
// SRAM and apply the default values
if (get_save_header(&header) && (header.valid_sections & SAVE_SECTION_FLAG_OPTIONS))
read_sram(OPTIONS_ADDRESS, (u8*)&options, sizeof(options)); read_sram(OPTIONS_ADDRESS, (u8*)&options, sizeof(options));
g_game_vars.game_speed = options.game_speed; g_game_vars.game_speed = options.game_speed;
@@ -362,11 +362,11 @@ void save_game(void)
void load_game(void) void load_game(void)
{ {
SaveHeader header; SaveHeader header;
if (!get_save_header(&header) || !(header.valid_sections & SAVE_SECTION_FLAG_GAME)) if (!get_save_header(&header) || !(header.valid_sections & SAVE_SECTION_FLAG_GAME))
return; return;
SaveGame game = SaveGame_default; SaveGame game = SaveGame_default;
read_sram(GAME_ADDRESS, (u8*)&game, sizeof(game)); read_sram(GAME_ADDRESS, (u8*)&game, sizeof(game));
g_game_vars.timer = game.timer; g_game_vars.timer = game.timer;