diff --git a/config.def.h b/config.def.h index cd7c3c56ae..cdae199dc2 100644 --- a/config.def.h +++ b/config.def.h @@ -1511,6 +1511,7 @@ static const unsigned gfx_thumbnail_upscale_threshold = 0; #endif #define DEFAULT_MENU_TIMEDATE_STYLE MENU_TIMEDATE_STYLE_DDMM_HM #define DEFAULT_MENU_TIMEDATE_DATE_SEPARATOR MENU_TIMEDATE_DATE_SEPARATOR_HYPHEN +#define DEFAULT_MENU_REMEMBER_SELECTION MENU_REMEMBER_SELECTION_ALWAYS #endif #define DEFAULT_XMB_VERTICAL_THUMBNAILS false diff --git a/configuration.c b/configuration.c index 3e50f48754..31d2db160a 100644 --- a/configuration.c +++ b/configuration.c @@ -2218,6 +2218,9 @@ static struct config_uint_setting *populate_settings_uint( #if defined(HAVE_MATERIALUI) || defined(HAVE_XMB) || defined(HAVE_OZONE) SETTING_UINT("menu_screensaver_animation", &settings->uints.menu_screensaver_animation, true, DEFAULT_MENU_SCREENSAVER_ANIMATION, false); #endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) + SETTING_UINT("menu_remember_selection", &settings->uints.menu_remember_selection, true, DEFAULT_MENU_REMEMBER_SELECTION, false); +#endif #ifdef HAVE_RGUI SETTING_UINT("rgui_menu_color_theme", &settings->uints.menu_rgui_color_theme, true, DEFAULT_RGUI_COLOR_THEME, false); SETTING_UINT("rgui_thumbnail_downscaler", &settings->uints.menu_rgui_thumbnail_downscaler, true, rgui_thumbnail_downscaler, false); diff --git a/configuration.h b/configuration.h index d1b3cd3b1c..e8fe1ccf9d 100644 --- a/configuration.h +++ b/configuration.h @@ -289,6 +289,7 @@ typedef struct settings unsigned menu_content_show_contentless_cores; unsigned menu_screensaver_timeout; unsigned menu_screensaver_animation; + unsigned menu_remember_selection; unsigned playlist_entry_remove_enable; unsigned playlist_show_inline_core_name; diff --git a/intl/msg_hash_lbl.h b/intl/msg_hash_lbl.h index 01780fe541..cb10c76d6e 100644 --- a/intl/msg_hash_lbl.h +++ b/intl/msg_hash_lbl.h @@ -3388,6 +3388,10 @@ MSG_HASH( MENU_ENUM_LABEL_MENU_TICKER_SMOOTH, "menu_ticker_smooth" ) +MSG_HASH( + MENU_ENUM_LABEL_MENU_REMEMBER_SELECTION, + "menu_remember_selection" + ) MSG_HASH( MENU_ENUM_LABEL_UI_COMPANION_ENABLE, "ui_companion_enable" diff --git a/intl/msg_hash_us.h b/intl/msg_hash_us.h index 42bbe14e77..d46bebf1ce 100644 --- a/intl/msg_hash_us.h +++ b/intl/msg_hash_us.h @@ -5508,6 +5508,26 @@ MSG_HASH( MENU_ENUM_SUBLABEL_MENU_TICKER_SMOOTH, "Use smooth scrolling animation when displaying long menu text. Has a small performance impact." ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION, + "Remember Selection when Changing Tabs" + ) +MSG_HASH( + MENU_ENUM_SUBLABEL_MENU_REMEMBER_SELECTION, + "Remember the position of the cursor in the menu when switching to a different tab." + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_ALWAYS, + "Always" + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_PLAYLISTS, + "Only for Playlists" + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_MAIN, + "Only for Main Menu and Settings" + ) /* Settings > AI Service */ diff --git a/menu/cbs/menu_cbs_sublabel.c b/menu/cbs/menu_cbs_sublabel.c index ca96d7da6a..6b246045e6 100644 --- a/menu/cbs/menu_cbs_sublabel.c +++ b/menu/cbs/menu_cbs_sublabel.c @@ -704,6 +704,9 @@ DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_menu_screensaver_timeout, MENU_ DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_menu_screensaver_animation, MENU_ENUM_SUBLABEL_MENU_SCREENSAVER_ANIMATION) DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_menu_screensaver_animation_speed, MENU_ENUM_SUBLABEL_MENU_SCREENSAVER_ANIMATION_SPEED) #endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) +DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_menu_remember_selection, MENU_ENUM_SUBLABEL_MENU_REMEMBER_SELECTION) +#endif DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_video_driver, MENU_ENUM_SUBLABEL_VIDEO_DRIVER) DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_audio_driver, MENU_ENUM_SUBLABEL_AUDIO_DRIVER) DEFAULT_SUBLABEL_MACRO(action_bind_sublabel_input_driver, MENU_ENUM_SUBLABEL_INPUT_DRIVER) @@ -3511,6 +3514,11 @@ int menu_cbs_init_bind_sublabel(menu_file_list_cbs_t *cbs, case MENU_ENUM_LABEL_MENU_SCREENSAVER_ANIMATION_SPEED: BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_menu_screensaver_animation_speed); break; +#endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) + case MENU_ENUM_LABEL_MENU_REMEMBER_SELECTION: + BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_menu_remember_selection); + break; #endif case MENU_ENUM_LABEL_MENU_INPUT_SWAP_OK_CANCEL: BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_input_swap_ok_cancel); diff --git a/menu/drivers/ozone.c b/menu/drivers/ozone.c index 181efe3c92..d90543126a 100644 --- a/menu/drivers/ozone.c +++ b/menu/drivers/ozone.c @@ -4145,6 +4145,9 @@ static void ozone_leave_sidebar( uintptr_t tag) { struct gfx_animation_ctx_entry entry; + settings_t *settings = config_get_ptr(); + unsigned remember_selection_type = settings->uints.menu_remember_selection; + bool ozone_main_tab_selected = false; ozone_update_content_metadata(ozone); @@ -4156,8 +4159,15 @@ static void ozone_leave_sidebar( ozone->flags &= ~OZONE_FLAG_CURSOR_IN_SIDEBAR_OLD; ozone->flags &= ~OZONE_FLAG_CURSOR_IN_SIDEBAR; + if ((ozone->tabs[ozone->categories_selection_ptr] == OZONE_SYSTEM_TAB_MAIN) + || (ozone->tabs[ozone->categories_selection_ptr] == OZONE_SYSTEM_TAB_SETTINGS)) + ozone_main_tab_selected = true; + /* Restore last selection per tab */ - ozone_tab_set_selection(ozone); + if ((remember_selection_type == MENU_REMEMBER_SELECTION_ALWAYS) + || ((remember_selection_type == MENU_REMEMBER_SELECTION_PLAYLISTS) && (ozone->flags & OZONE_FLAG_IS_PLAYLIST)) + || ((remember_selection_type == MENU_REMEMBER_SELECTION_MAIN) && (ozone_main_tab_selected))) + ozone_tab_set_selection(ozone); /* Cursor animation */ ozone->animations.cursor_alpha = 0.0f; diff --git a/menu/drivers/xmb.c b/menu/drivers/xmb.c index 908f81e54c..a974f1c4e0 100644 --- a/menu/drivers/xmb.c +++ b/menu/drivers/xmb.c @@ -2134,11 +2134,14 @@ static void xmb_tab_set_selection(void *data) static void xmb_list_switch(xmb_handle_t *xmb) { gfx_animation_ctx_entry_t anim_entry; - int dir = -1; - file_list_t *selection_buf = menu_entries_get_selection_buf_ptr(0); - size_t selection = 0; - settings_t *settings = config_get_ptr(); - bool menu_horizontal_animation = settings->bools.menu_horizontal_animation; + int dir = -1; + file_list_t *selection_buf = menu_entries_get_selection_buf_ptr(0); + size_t selection = 0; + settings_t *settings = config_get_ptr(); + bool xmb_main_tab_selected = false; + bool menu_horizontal_animation = settings->bools.menu_horizontal_animation; + unsigned remember_selection_type = settings->uints.menu_remember_selection; + unsigned xmb_system_tab = xmb_get_system_tab(xmb, (unsigned)xmb->categories_selection_ptr); if ( xmb->categories_selection_ptr > xmb->categories_selection_ptr_old) @@ -2146,8 +2149,14 @@ static void xmb_list_switch(xmb_handle_t *xmb) xmb->categories_active_idx += dir; + if ((xmb_system_tab == XMB_SYSTEM_TAB_MAIN) || (xmb_system_tab == XMB_SYSTEM_TAB_SETTINGS)) + xmb_main_tab_selected = true; + /* Restore last selection per tab */ - xmb_tab_set_selection(xmb); + if ((remember_selection_type == MENU_REMEMBER_SELECTION_ALWAYS) + || ((remember_selection_type == MENU_REMEMBER_SELECTION_PLAYLISTS) && (xmb->is_playlist)) + || ((remember_selection_type == MENU_REMEMBER_SELECTION_MAIN) && (xmb_main_tab_selected))) + xmb_tab_set_selection(xmb); /* Selection needs to be taken after tab restore */ selection = menu_navigation_get_selection(); diff --git a/menu/menu_defines.h b/menu/menu_defines.h index e101e69510..422e70840c 100644 --- a/menu/menu_defines.h +++ b/menu/menu_defines.h @@ -108,6 +108,15 @@ enum menu_timedate_style_type MENU_TIMEDATE_STYLE_LAST }; +enum menu_remember_selection_type +{ + MENU_REMEMBER_SELECTION_OFF = 0, + MENU_REMEMBER_SELECTION_ALWAYS, + MENU_REMEMBER_SELECTION_PLAYLISTS, + MENU_REMEMBER_SELECTION_MAIN, + MENU_REMEMBER_SELECTION_LAST +}; + /* Note: These must be kept synchronised with * 'enum playlist_sublabel_last_played_date_separator_type' * in 'runtime_file.h' */ diff --git a/menu/menu_displaylist.c b/menu/menu_displaylist.c index 13e7022d43..eeb7d4b1bd 100644 --- a/menu/menu_displaylist.c +++ b/menu/menu_displaylist.c @@ -8400,6 +8400,7 @@ unsigned menu_displaylist_build_list( {MENU_ENUM_LABEL_MENU_SCREENSAVER_TIMEOUT, PARSE_ONLY_UINT, false}, {MENU_ENUM_LABEL_MENU_SCREENSAVER_ANIMATION, PARSE_ONLY_UINT, false}, {MENU_ENUM_LABEL_MENU_SCREENSAVER_ANIMATION_SPEED, PARSE_ONLY_FLOAT, false}, + {MENU_ENUM_LABEL_MENU_REMEMBER_SELECTION, PARSE_ONLY_UINT, false}, {MENU_ENUM_LABEL_MOUSE_ENABLE, PARSE_ONLY_BOOL, true}, {MENU_ENUM_LABEL_POINTER_ENABLE, PARSE_ONLY_BOOL, true}, {MENU_ENUM_LABEL_THREADED_DATA_RUNLOOP_ENABLE, PARSE_ONLY_BOOL, true}, @@ -8439,6 +8440,11 @@ unsigned menu_displaylist_build_list( build_list[i].checked = true; break; #endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) + case MENU_ENUM_LABEL_MENU_REMEMBER_SELECTION: + build_list[i].checked = true; + break; +#endif #if defined(HAVE_QT) || defined(HAVE_COCOA) case MENU_ENUM_LABEL_UI_COMPANION_TOGGLE: if (desktop_menu_enable) diff --git a/menu/menu_setting.c b/menu/menu_setting.c index ad7283fd6b..32f73ae0b7 100644 --- a/menu/menu_setting.c +++ b/menu/menu_setting.c @@ -6963,6 +6963,44 @@ static void setting_get_string_representation_uint_menu_screensaver_animation( } #endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) +static void setting_get_string_representation_uint_menu_remember_selection( + rarch_setting_t *setting, + char *s, size_t len) +{ + if (!setting) + return; + + switch (*setting->value.target.unsigned_integer) + { + case MENU_REMEMBER_SELECTION_ALWAYS: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_ALWAYS), + len); + break; + case MENU_REMEMBER_SELECTION_PLAYLISTS: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_PLAYLISTS), + len); + break; + case MENU_REMEMBER_SELECTION_MAIN: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_MAIN), + len); + break; + case MENU_REMEMBER_SELECTION_OFF: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_OFF), + len); + break; + } +} +#endif + #ifdef HAVE_MIST static void setting_get_string_representation_steam_rich_presence_format( rarch_setting_t *setting, @@ -15977,6 +16015,30 @@ static bool setting_append_list( (*list)[list_info->index - 1].action_ok = &setting_action_ok_uint; menu_settings_list_current_add_range(list, list_info, 0.1, 10.0, 0.1, true, true); } +#endif +#if defined(HAVE_XMB) || defined(HAVE_OZONE) + if (string_is_equal(settings->arrays.menu_driver, "xmb") || + string_is_equal(settings->arrays.menu_driver, "ozone")) + { + CONFIG_UINT( + list, list_info, + &settings->uints.menu_remember_selection, + MENU_ENUM_LABEL_MENU_REMEMBER_SELECTION, + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION, + DEFAULT_MENU_REMEMBER_SELECTION, + &group_info, + &subgroup_info, + parent_group, + general_write_handler, + general_read_handler); + (*list)[list_info->index - 1].action_ok = &setting_action_ok_uint; + (*list)[list_info->index - 1].action_left = &setting_uint_action_left_with_refresh; + (*list)[list_info->index - 1].action_right = &setting_uint_action_right_with_refresh; + (*list)[list_info->index - 1].get_string_representation = + &setting_get_string_representation_uint_menu_remember_selection; + menu_settings_list_current_add_range(list, list_info, 0, MENU_REMEMBER_SELECTION_LAST-1, 1, true, true); + (*list)[list_info->index - 1].ui_type = ST_UI_TYPE_UINT_COMBOBOX; + } #endif CONFIG_BOOL( list, list_info, diff --git a/msg_hash.h b/msg_hash.h index ab3f3f81c8..134d3db280 100644 --- a/msg_hash.h +++ b/msg_hash.h @@ -1380,6 +1380,12 @@ enum msg_hash_enums MENU_ENUM_LABEL_VALUE_MENU_ADD_CONTENT_ENTRY_DISPLAY_MAIN_TAB, MENU_ENUM_LABEL_VALUE_MENU_ADD_CONTENT_ENTRY_DISPLAY_PLAYLISTS_TAB, + MENU_LABEL(MENU_REMEMBER_SELECTION), + + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_ALWAYS, + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_PLAYLISTS, + MENU_ENUM_LABEL_VALUE_MENU_REMEMBER_SELECTION_MAIN, + /* UI settings */ MENU_LABEL(VIDEO_DISABLE_COMPOSITION), MENU_LABEL(UI_COMPANION_ENABLE),