diff --git a/include/app/app.h b/include/app/app.h index 19d4087..b3190d1 100644 --- a/include/app/app.h +++ b/include/app/app.h @@ -152,7 +152,6 @@ enum menu_kind { MENU_VIDEO, MENU_AUDIO, MENU_BINDINGS, - MENU_MISC, MENU_MAX, }; @@ -202,6 +201,15 @@ struct settings { // Enable the emulation of the prefetch buffer bool prefetch_buffer; + // Start the last played game on startup, when no game is provided + bool start_last_played_game_on_startup; + + // Pause when the window is inactive + bool pause_when_window_inactive; + + // Pause when the game resets + bool pause_when_game_resets; + // Backup storage struct { bool autodetect; @@ -216,6 +224,9 @@ struct settings { } emulation; struct { + // Menubar mode (fixed above game or hover over game) + enum menubar_mode menubar_mode; + // Display mode enum display_mode display_mode; @@ -237,6 +248,9 @@ struct settings { // Pixel Scaling Filter (LCD Grid, xBRZ, etc.) enum pixel_scaling_filter_kind pixel_scaling_filter; + // Hide the cursor after a few seconds of inactivity + bool hide_cursor_when_mouse_inactive; + /* ** Debug */ @@ -265,23 +279,6 @@ struct settings { // Enable FIFO Channel bool enable_fifo_channels[2]; } audio; - - struct { - // Menubar mode (fixed above game or hover over game) - enum menubar_mode menubar_mode; - - // Start the last played game on startup, when no game is provided - bool start_last_played_game_on_startup; - - // Pause when the window is inactive - bool pause_when_window_inactive; - - // Pause when the game resets - bool pause_when_game_resets; - - // Hide the cursor after a few seconds of inactivity - bool hide_cursor_when_mouse_inactive; - } misc; }; struct app { diff --git a/source/app/config.c b/source/app/config.c index 79bda97..9211426 100644 --- a/source/app/config.c +++ b/source/app/config.c @@ -96,6 +96,18 @@ app_config_load( app->settings.emulation.prefetch_buffer = b; } + if (mjson_get_bool(data, data_len, "$.emulation.start_last_played_game_on_startup", &b)) { + app->settings.emulation.start_last_played_game_on_startup = b; + } + + if (mjson_get_bool(data, data_len, "$.emulation.pause_when_window_inactive", &b)) { + app->settings.emulation.pause_when_window_inactive = b; + } + + if (mjson_get_bool(data, data_len, "$.emulation.pause_when_game_resets", &b)) { + app->settings.emulation.pause_when_game_resets = b; + } + if (mjson_get_bool(data, data_len, "$.emulation.backup_storage.autodetect", &b)) { app->settings.emulation.backup_storage.autodetect = b; } @@ -118,6 +130,11 @@ app_config_load( int b; double d; + if (mjson_get_number(data, data_len, "$.video.menubar_mode", &d)) { + app->settings.video.menubar_mode = (int)d; + app->settings.video.menubar_mode = max(MENUBAR_MODE_MIN, min(app->settings.video.menubar_mode, MENUBAR_MODE_MAX)); + } + if (mjson_get_number(data, data_len, "$.video.display_mode", &d)) { app->settings.video.display_mode = (int)d; app->settings.video.display_mode = max(DISPLAY_MODE_MIN, min(app->settings.video.display_mode, DISPLAY_MODE_MAX)); @@ -151,6 +168,10 @@ app_config_load( app->settings.video.pixel_scaling_filter = (int)d; app->settings.video.pixel_scaling_filter = max(PIXEL_SCALING_FILTER_MIN, min(app->settings.video.pixel_scaling_filter, PIXEL_SCALING_FILTER_MAX)); } + + if (mjson_get_bool(data, data_len, "$.video.hide_cursor_when_mouse_inactive", &b)) { + app->settings.video.hide_cursor_when_mouse_inactive = b; + } } // Video @@ -168,33 +189,6 @@ app_config_load( } } - // Misc - { - int b; - double d; - - if (mjson_get_number(data, data_len, "$.misc.menubar_mode", &d)) { - app->settings.misc.menubar_mode = (int)d; - app->settings.misc.menubar_mode = max(MENUBAR_MODE_MIN, min(app->settings.misc.menubar_mode, MENUBAR_MODE_MAX)); - } - - if (mjson_get_bool(data, data_len, "$.misc.start_last_played_game_on_startup", &b)) { - app->settings.misc.start_last_played_game_on_startup = b; - } - - if (mjson_get_bool(data, data_len, "$.misc.pause_when_window_inactive", &b)) { - app->settings.misc.pause_when_window_inactive = b; - } - - if (mjson_get_bool(data, data_len, "$.misc.pause_when_game_resets", &b)) { - app->settings.misc.pause_when_game_resets = b; - } - - if (mjson_get_bool(data, data_len, "$.misc.hide_cursor_when_mouse_inactive", &b)) { - app->settings.misc.hide_cursor_when_mouse_inactive = b; - } - } - // Binds { char path[256]; @@ -317,6 +311,9 @@ app_config_save( "speed": %g, "alt_speed": %g, "prefetch_buffer": %B, + "start_last_played_game_on_startup": %B, + "pause_when_window_inactive": %B, + "pause_when_game_resets": %B, "backup_storage": { "autodetect": %B, "type": %d @@ -329,13 +326,15 @@ app_config_save( // Video "video": { + "menubar_mode": %d, "display_mode": %d, "display_size": %d, "aspect_ratio": %d, "vsync": %B, "texture_filter": %d, "pixel_color_filter": %d, - "pixel_scaling_filter": %d + "pixel_scaling_filter": %d, + "hide_cursor_when_mouse_inactive": %B }, // Audio @@ -343,15 +342,6 @@ app_config_save( "mute": %B, "level": %g }, - - // Misc - "misc": { - "menubar_mode": %d, - "start_last_played_game_on_startup": %B, - "pause_when_window_inactive": %B, - "pause_when_game_resets": %B, - "hide_cursor_when_mouse_inactive": %B - } }), app->settings.emulation.bios_path, app->file.recent_roms[0], @@ -369,10 +359,14 @@ app_config_save( app->settings.emulation.speed, app->settings.emulation.alt_speed, (int)app->settings.emulation.prefetch_buffer, + (int)app->settings.emulation.start_last_played_game_on_startup, + (int)app->settings.emulation.pause_when_window_inactive, + (int)app->settings.emulation.pause_when_game_resets, (int)app->settings.emulation.backup_storage.autodetect, (int)app->settings.emulation.backup_storage.type, (int)app->settings.emulation.gpio_device.autodetect, (int)app->settings.emulation.gpio_device.type, + (int)app->settings.video.menubar_mode, (int)app->settings.video.display_mode, (int)app->settings.video.display_size, (int)app->settings.video.aspect_ratio, @@ -380,13 +374,9 @@ app_config_save( (int)app->settings.video.texture_filter, (int)app->settings.video.pixel_color_filter, (int)app->settings.video.pixel_scaling_filter, + (int)app->settings.video.hide_cursor_when_mouse_inactive, (int)app->settings.audio.mute, - app->settings.audio.level, - (int)app->settings.misc.menubar_mode, - (int)app->settings.misc.start_last_played_game_on_startup, - (int)app->settings.misc.pause_when_window_inactive, - (int)app->settings.misc.pause_when_game_resets, - (int)app->settings.misc.hide_cursor_when_mouse_inactive + app->settings.audio.level ); if (!data) { diff --git a/source/app/emulator.c b/source/app/emulator.c index d8fc689..eb03769 100644 --- a/source/app/emulator.c +++ b/source/app/emulator.c @@ -712,7 +712,7 @@ app_emulator_configure_and_run( logln(HS_INFO, "Game successfully loaded."); - if (app->settings.misc.pause_when_game_resets) { + if (app->settings.emulation.pause_when_game_resets) { app_emulator_pause(app); } else { app_emulator_run(app); diff --git a/source/app/main.c b/source/app/main.c index bab945d..65a9abd 100644 --- a/source/app/main.c +++ b/source/app/main.c @@ -58,6 +58,9 @@ app_settings_default( settings->emulation.speed = 1.0; settings->emulation.alt_speed = -1.0; settings->emulation.prefetch_buffer = true; + settings->emulation.start_last_played_game_on_startup = false; + settings->emulation.pause_when_window_inactive = false; + settings->emulation.pause_when_game_resets = false; settings->emulation.backup_storage.autodetect = true; settings->emulation.backup_storage.type = BACKUP_NONE; settings->emulation.gpio_device.autodetect = true; @@ -66,6 +69,7 @@ app_settings_default( memset(settings->video.enable_bg_layers, true, sizeof(settings->video.enable_bg_layers)); memset(settings->audio.enable_psg_channels, true, sizeof(settings->audio.enable_psg_channels)); memset(settings->audio.enable_fifo_channels, true, sizeof(settings->audio.enable_fifo_channels)); + settings->video.menubar_mode = MENUBAR_MODE_FIXED_ABOVE_GAME; settings->video.display_mode = DISPLAY_MODE_WINDOWED; settings->video.display_size = 3; settings->video.aspect_ratio = ASPECT_RATIO_BORDERS; @@ -73,13 +77,9 @@ app_settings_default( settings->video.texture_filter = TEXTURE_FILTER_NEAREST; settings->video.pixel_color_filter = PIXEL_COLOR_FILTER_COLOR_CORRECTION; settings->video.pixel_scaling_filter = PIXEL_SCALING_FILTER_LCD_GRID; + settings->video.hide_cursor_when_mouse_inactive = true; settings->audio.mute = false; settings->audio.level = 1.0f; - settings->misc.menubar_mode = MENUBAR_MODE_FIXED_ABOVE_GAME; - settings->misc.start_last_played_game_on_startup = false; - settings->misc.pause_when_window_inactive = false; - settings->misc.pause_when_game_resets = false; - settings->misc.hide_cursor_when_mouse_inactive = true; } int @@ -146,7 +146,7 @@ main( if (app.args.rom_path) { app_emulator_configure_and_run(&app, app.args.rom_path, NULL); } else if ( // Start the last played game - app.settings.misc.start_last_played_game_on_startup + app.settings.emulation.start_last_played_game_on_startup && app.file.recent_roms[0] && strlen(app.file.recent_roms[0]) ) { @@ -258,7 +258,7 @@ main( } // Hide the cursor if the mouse is inactive for a while - if (app.settings.misc.hide_cursor_when_mouse_inactive) { + if (app.settings.video.hide_cursor_when_mouse_inactive) { bool show_cursor; bool is_cursor_visible; @@ -272,7 +272,7 @@ main( // Hide the menubar if it's hovering over the game, isn't focused and the mouse is inactive for a while // We set `visibility` to go from 1.0 to 0.0 over 50ms, after the mouse is inactive after 1950ms. - if (app.settings.misc.menubar_mode == MENUBAR_MODE_HOVER_OVER_GAME) { + if (app.settings.video.menubar_mode == MENUBAR_MODE_HOVER_OVER_GAME) { if (app.ui.time_elapsed_since_last_mouse_motion_ms < 1950.0) { app.ui.menubar.visibility = 1.0f; } else if (app.ui.time_elapsed_since_last_mouse_motion_ms >= 1950.0 && app.ui.time_elapsed_since_last_mouse_motion_ms <= 2000.0) { diff --git a/source/app/sdl/event.c b/source/app/sdl/event.c index 035245d..0527460 100644 --- a/source/app/sdl/event.c +++ b/source/app/sdl/event.c @@ -49,13 +49,13 @@ app_sdl_handle_events( break; }; case SDL_WINDOWEVENT_FOCUS_GAINED: { - if (app->settings.misc.pause_when_window_inactive && app->emulation.is_started && !app->emulation.is_running) { + if (app->settings.emulation.pause_when_window_inactive && app->emulation.is_started && !app->emulation.is_running) { app_emulator_run(app); } break; }; case SDL_WINDOWEVENT_FOCUS_LOST: { - if (app->settings.misc.pause_when_window_inactive && app->emulation.is_started && app->emulation.is_running) { + if (app->settings.emulation.pause_when_window_inactive && app->emulation.is_started && app->emulation.is_running) { app_emulator_pause(app); } break; diff --git a/source/app/sdl/video.c b/source/app/sdl/video.c index 269c3b5..83c6d3e 100644 --- a/source/app/sdl/video.c +++ b/source/app/sdl/video.c @@ -86,7 +86,7 @@ app_sdl_video_init( // unknown at this stage. // // The size given here is merely a guess as to what the real size will be, hence the magical +19.f for the window's height. - app->ui.menubar.size.y = app->settings.misc.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME ? 19.f * app->ui.scale : 0.f; + app->ui.menubar.size.y = app->settings.video.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME ? 19.f * app->ui.scale : 0.f; app->ui.display.win.width = GBA_SCREEN_WIDTH * app->settings.video.display_size * app->ui.scale; app->ui.display.win.height = (GBA_SCREEN_HEIGHT * app->settings.video.display_size * app->ui.scale) + app->ui.menubar.size.y; app_win_game_refresh_game_area(app); @@ -209,7 +209,7 @@ app_sdl_video_resize_window( h = GBA_SCREEN_HEIGHT * app->settings.video.display_size * app->ui.scale; // If relevant, expand the window by the size of the menubar - h += app->settings.misc.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME ? app->ui.menubar.size.y : 0; + h += app->settings.video.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME ? app->ui.menubar.size.y : 0; SDL_SetWindowSize(app->sdl.window, w, h); } diff --git a/source/app/windows/game.c b/source/app/windows/game.c index 328d374..f5f3089 100644 --- a/source/app/windows/game.c +++ b/source/app/windows/game.c @@ -25,7 +25,7 @@ app_win_game_refresh_game_area( app->ui.display.game.outer.y = 0; // Ensure the outer window is below the menubar - if (app->settings.misc.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME) { + if (app->settings.video.menubar_mode == MENUBAR_MODE_FIXED_ABOVE_GAME) { app->ui.display.game.outer.y += app->ui.menubar.size.y * app->ui.menubar.visibility; } diff --git a/source/app/windows/settings.c b/source/app/windows/settings.c index f4d26e4..536d923 100644 --- a/source/app/windows/settings.c +++ b/source/app/windows/settings.c @@ -17,7 +17,6 @@ static char const *menu_names[MENU_MAX] = { [MENU_VIDEO] = "Video", [MENU_AUDIO] = "Audio", [MENU_BINDINGS] = "Bindings", - [MENU_MISC] = "Misc", }; static char const *texture_filters_names[TEXTURE_FILTER_LEN] = { @@ -364,6 +363,32 @@ app_win_settings_emulation( igTableNextColumn(); igCheckbox("##ShowFPS", &app->settings.emulation.show_fps); + // Start the last played game on startup, when no game is provided + igTableNextRow(ImGuiTableRowFlags_None, 0.f); + igTableNextColumn(); + igTextWrapped("Start the last played game on startup"); + + igTableNextColumn(); + igCheckbox("##StartLastPlayedGameOnStartup", &app->settings.emulation.start_last_played_game_on_startup); + + // Pause when the window is inactive + igTableNextRow(ImGuiTableRowFlags_None, 0.f); + igTableNextColumn(); + igTextWrapped("Pause when the window is inactive"); + + igTableNextColumn(); + igCheckbox("##PauseWhenWindowInactive", &app->settings.emulation.pause_when_window_inactive); + +#ifdef WITH_DEBUGGER + // Pause when the game resets + igTableNextRow(ImGuiTableRowFlags_None, 0.f); + igTableNextColumn(); + igTextWrapped("Pause when the game resets"); + + igTableNextColumn(); + igCheckbox("##PauseWhenGameResets", &app->settings.emulation.pause_when_game_resets); +#endif + igEndTable(); } } @@ -390,6 +415,16 @@ app_win_settings_video( igTableSetupColumn("##VideoSettingsDisplayLabel", ImGuiTableColumnFlags_WidthFixed, vp->WorkSize.x / 5.f, 0); igTableSetupColumn("##VideoSettingsDisplayValue", ImGuiTableColumnFlags_WidthStretch, 0.f, 0); + // Menubar Mode + igTableNextRow(ImGuiTableRowFlags_None, 0.f); + igTableNextColumn(); + igTextWrapped("Menubar Mode"); + + igTableNextColumn(); + if (igCombo_Str_arr("##MenubarMode", (int *)&app->settings.video.menubar_mode, menubar_mode_names, array_length(menubar_mode_names), 0)) { + app->ui.display.request_resize = true; + } + // Display Mode igTableNextRow(ImGuiTableRowFlags_None, 0.f); igTableNextColumn(); @@ -498,6 +533,23 @@ app_win_settings_video( igEndTable(); } + igSeparatorText("Misc"); + + if (igBeginTable("##VideoSettingsMisc", 2, ImGuiTableFlags_None, (ImVec2){ .x = 0.f, .y = 0.f }, 0.f)) { + igTableSetupColumn("##VideoSettingsMiscLabel", ImGuiTableColumnFlags_WidthFixed, vp->WorkSize.x / 5.f, 0); + igTableSetupColumn("##VideoSettingsMiscValue", ImGuiTableColumnFlags_WidthStretch, 0.f, 0); + + // Hide the cursor when the mouse is inactive + igTableNextRow(ImGuiTableRowFlags_None, 0.f); + igTableNextColumn(); + igTextWrapped("Hide cursor when the mouse is inactive"); + + igTableNextColumn(); + igCheckbox("##HideCursorWhenMouseInactive", &app->settings.video.hide_cursor_when_mouse_inactive); + + igEndTable(); + } + #ifdef WITH_DEBUGGER igSeparatorText("Debug"); @@ -627,74 +679,6 @@ app_win_settings_audio( #endif } -static -void -app_win_settings_misc( - struct app *app -) { - ImGuiViewport *vp; - - vp = igGetMainViewport(); - - igTextWrapped("Misc Settings"); - igSpacing(); - igSeparator(); - igSpacing(); - - igSeparatorText("Interface"); - - if (igBeginTable("##MiscSettingsInterface", 2, ImGuiTableFlags_None, (ImVec2){ .x = 0.f, .y = 0.f }, 0.f)) { - igTableSetupColumn("##MiscSettingsInterfaceLabel", ImGuiTableColumnFlags_WidthFixed, vp->WorkSize.x / 5.f, 0); - igTableSetupColumn("##MiscSettingsInterfaceValue", ImGuiTableColumnFlags_WidthStretch, 0.f, 0); - - // Menubar Mode - igTableNextRow(ImGuiTableRowFlags_None, 0.f); - igTableNextColumn(); - igTextWrapped("Menubar Mode"); - - igTableNextColumn(); - if (igCombo_Str_arr("##Menubar Mode", (int *)&app->settings.misc.menubar_mode, menubar_mode_names, array_length(menubar_mode_names), 0)) { - app->ui.display.request_resize = true; - } - - // Start the last played game on startup, when no game is provided - igTableNextRow(ImGuiTableRowFlags_None, 0.f); - igTableNextColumn(); - igTextWrapped("Start the last played game on startup"); - - igTableNextColumn(); - igCheckbox("##StartLastPlayedGameOnStartup", &app->settings.misc.start_last_played_game_on_startup); - - // Pause when the window is inactive - igTableNextRow(ImGuiTableRowFlags_None, 0.f); - igTableNextColumn(); - igTextWrapped("Pause when the window is inactive"); - - igTableNextColumn(); - igCheckbox("##PauseWhenWindowInactive", &app->settings.misc.pause_when_window_inactive); - -#ifdef WITH_DEBUGGER - // Pause when the game resets - igTableNextRow(ImGuiTableRowFlags_None, 0.f); - igTableNextColumn(); - igTextWrapped("Pause when the game resets"); - - igTableNextColumn(); - igCheckbox("##PauseWhenGameResets", &app->settings.misc.pause_when_game_resets); -#endif - - // Hide the cursor when the mouse is inactive - igTableNextRow(ImGuiTableRowFlags_None, 0.f); - igTableNextColumn(); - igTextWrapped("Hide cursor when the mouse is inactive"); - - igTableNextColumn(); - igCheckbox("##HideCursorWhenMouseInactive", &app->settings.misc.hide_cursor_when_mouse_inactive); - - igEndTable(); - } -} - static void app_win_settings_bindings_bind_keyboard( @@ -859,7 +843,6 @@ static void (*menu_callbacks[MENU_MAX])(struct app *) = { [MENU_VIDEO] = &app_win_settings_video, [MENU_AUDIO] = &app_win_settings_audio, [MENU_BINDINGS] = &app_win_settings_bindings, - [MENU_MISC] = &app_win_settings_misc, }; void