From 02ddbc41cc5c92ef93e046d239a3a8b92e5da6ec Mon Sep 17 00:00:00 2001 From: Jamiras Date: Fri, 25 Sep 2020 14:01:07 -0600 Subject: [PATCH 1/2] allow disabling leaderboard notifications and trackers separately --- cheevos/cheevos.c | 107 +++++++++++++++++++++++++++-------- configuration.c | 2 +- configuration.h | 2 +- intl/msg_hash_us.h | 8 +++ menu/cbs/menu_cbs_ok.c | 19 ++++++- menu/menu_displaylist.c | 29 ++++++++-- menu/menu_setting.c | 122 +++++++++++++++++++++++++++++++++++++--- msg_hash.h | 2 + 8 files changed, 250 insertions(+), 41 deletions(-) diff --git a/cheevos/cheevos.c b/cheevos/cheevos.c index 5295a124f6..d4676b9077 100644 --- a/cheevos/cheevos.c +++ b/cheevos/cheevos.c @@ -140,6 +140,9 @@ typedef struct bool hardcore_active; bool loaded; bool core_supports; + bool leaderboards_enabled; + bool leaderboard_notifications; + bool leaderboard_trackers; } rcheevos_locals_t; static rcheevos_locals_t rcheevos_locals = @@ -157,6 +160,9 @@ static rcheevos_locals_t rcheevos_locals = false,/* hardcore_active */ false,/* loaded */ true, /* core_supports */ + false,/* leaderboards_enabled */ + false,/* leaderboard_notifications */ + false /* leaderboard_trackers */ }; #ifdef HAVE_THREADS @@ -757,7 +763,7 @@ static int rcheevos_parse( locals->patchdata.unofficial_count, RCHEEVOS_ACTIVE_UNOFFICIAL); } - if (locals->hardcore_active && settings->bools.cheevos_leaderboards_enable) + if (locals->hardcore_active && locals->leaderboards_enabled) { lboard = locals->patchdata.lboards; count = locals->patchdata.lboard_count; @@ -966,7 +972,7 @@ static void rcheevos_lboard_submit(rcheevos_locals_t *locals, char buffer[256]; char formatted_value[16]; - /* Show the OSD message. */ + /* Show the OSD message (regardless of notifications setting). */ rc_format_value(formatted_value, sizeof(formatted_value), value, lboard->format); CHEEVOS_LOG(RCHEEVOS_TAG "Submitting %s for leaderboard %u\n", formatted_value, lboard->id); @@ -1007,9 +1013,12 @@ static void rcheevos_lboard_canceled(rcheevos_ralboard_t * lboard) gfx_widgets_set_leaderboard_display(lboard->id, NULL); #endif - snprintf(buffer, sizeof(buffer), "Leaderboard attempt failed: %s", lboard->title); - runloop_msg_queue_push(buffer, 0, 2 * 60, false, NULL, - MESSAGE_QUEUE_ICON_DEFAULT, MESSAGE_QUEUE_CATEGORY_INFO); + if (rcheevos_locals.leaderboard_notifications) + { + snprintf(buffer, sizeof(buffer), "Leaderboard attempt failed: %s", lboard->title); + runloop_msg_queue_push(buffer, 0, 2 * 60, false, NULL, + MESSAGE_QUEUE_ICON_DEFAULT, MESSAGE_QUEUE_CATEGORY_INFO); + } } static void rcheevos_lboard_started(rcheevos_ralboard_t * lboard, int value) @@ -1021,20 +1030,23 @@ static void rcheevos_lboard_started(rcheevos_ralboard_t * lboard, int value) CHEEVOS_LOG(RCHEEVOS_TAG "Leaderboard %u started: %s\n", lboard->id, lboard->title); #if defined(HAVE_GFX_WIDGETS) - if (gfx_widgets_ready()) + if (gfx_widgets_ready() && rcheevos_locals.leaderboard_trackers) { rc_format_value(buffer, sizeof(buffer), value, lboard->format); gfx_widgets_set_leaderboard_display(lboard->id, buffer); } #endif - if (lboard->description && *lboard->description) - snprintf(buffer, sizeof(buffer), "Leaderboard attempt started: %s - %s", lboard->title, lboard->description); - else - snprintf(buffer, sizeof(buffer), "Leaderboard attempt started: %s", lboard->title); + if (rcheevos_locals.leaderboard_notifications) + { + if (lboard->description && *lboard->description) + snprintf(buffer, sizeof(buffer), "Leaderboard attempt started: %s - %s", lboard->title, lboard->description); + else + snprintf(buffer, sizeof(buffer), "Leaderboard attempt started: %s", lboard->title); - runloop_msg_queue_push(buffer, 0, 2 * 60, false, NULL, - MESSAGE_QUEUE_ICON_DEFAULT, MESSAGE_QUEUE_CATEGORY_INFO); + runloop_msg_queue_push(buffer, 0, 2 * 60, false, NULL, + MESSAGE_QUEUE_ICON_DEFAULT, MESSAGE_QUEUE_CATEGORY_INFO); + } } #if defined(HAVE_GFX_WIDGETS) @@ -1043,7 +1055,7 @@ static void rcheevos_lboard_updated(rcheevos_ralboard_t* lboard, int value) if (!lboard) return; - if (gfx_widgets_ready()) + if (gfx_widgets_ready() && rcheevos_locals.leaderboard_trackers) { char buffer[32]; rc_format_value(buffer, sizeof(buffer), value, lboard->format); @@ -1350,17 +1362,60 @@ static void rcheevos_deactivate_leaderboards(rcheevos_locals_t* locals) void rcheevos_leaderboards_enabled_changed(void) { + const settings_t* settings = config_get_ptr(); + const bool leaderboards_enabled = rcheevos_locals.leaderboards_enabled; + const bool leaderboard_trackers = rcheevos_locals.leaderboard_trackers; + + rcheevos_locals.leaderboards_enabled = rcheevos_hardcore_active(); + + if (string_is_equal(settings->arrays.cheevos_leaderboards_enable, "true")) + { + rcheevos_locals.leaderboard_notifications = true; + rcheevos_locals.leaderboard_trackers = true; + } +#if defined(HAVE_GFX_WIDGETS) + else if (string_is_equal(settings->arrays.cheevos_leaderboards_enable, "trackers")) + { + rcheevos_locals.leaderboard_notifications = false; + rcheevos_locals.leaderboard_trackers = true; + } + else if (string_is_equal(settings->arrays.cheevos_leaderboards_enable, "notifications")) + { + rcheevos_locals.leaderboard_notifications = true; + rcheevos_locals.leaderboard_trackers = false; + } +#endif + else + { + rcheevos_locals.leaderboards_enabled = false; + rcheevos_locals.leaderboard_notifications = false; + rcheevos_locals.leaderboard_trackers = false; + } + if (rcheevos_locals.loaded) { - const settings_t* settings = config_get_ptr(); - const bool enabled = settings && settings->bools.cheevos_enable && - settings->bools.cheevos_leaderboards_enable && - settings->bools.cheevos_hardcore_mode_enable; + if (leaderboards_enabled != rcheevos_locals.leaderboards_enabled) + { + if (rcheevos_locals.leaderboards_enabled) + rcheevos_activate_leaderboards(&rcheevos_locals); + else + rcheevos_deactivate_leaderboards(&rcheevos_locals); + } - if (enabled) - rcheevos_activate_leaderboards(&rcheevos_locals); - else - rcheevos_deactivate_leaderboards(&rcheevos_locals); +#if defined(HAVE_GFX_WIDGETS) + if (!rcheevos_locals.leaderboard_trackers && leaderboard_trackers) + { + /* Hide any visible trackers */ + rcheevos_ralboard_t* lboard = rcheevos_locals.patchdata.lboards; + unsigned i; + + for (i = 0; i < rcheevos_locals.patchdata.lboard_count; ++i, ++lboard) + { + if (lboard->mem) + gfx_widgets_set_leaderboard_display(lboard->id, NULL); + } + } +#endif } } @@ -1382,7 +1437,7 @@ static void rcheevos_toggle_hardcore_active(rcheevos_locals_t* locals) MESSAGE_QUEUE_ICON_DEFAULT, MESSAGE_QUEUE_CATEGORY_INFO); /* reactivate leaderboards */ - if (settings->bools.cheevos_leaderboards_enable) + if (locals->leaderboards_enabled) rcheevos_activate_leaderboards(locals); /* reset the game */ @@ -1437,7 +1492,12 @@ void rcheevos_hardcore_enabled_changed(void) const bool enabled = settings && settings->bools.cheevos_enable && settings->bools.cheevos_hardcore_mode_enable; if (enabled != rcheevos_locals.hardcore_active) + { rcheevos_toggle_hardcore_active(&rcheevos_locals); + + /* update leaderboard state flags */ + rcheevos_leaderboards_enabled_changed(); + } } static void rcheevos_runtime_event_handler(const rc_runtime_event_t* runtime_event) @@ -2355,8 +2415,9 @@ bool rcheevos_load(const void *data) return false; } - /* reset hardcore mode based on configs */ + /* reset hardcore mode and leaderboard settings based on configs */ rcheevos_hardcore_enabled_changed(); + rcheevos_leaderboards_enabled_changed(); coro = (rcheevos_coro_t*)calloc(1, sizeof(*coro)); diff --git a/configuration.c b/configuration.c index c160a2ce8e..f5f0898b14 100644 --- a/configuration.c +++ b/configuration.c @@ -1207,6 +1207,7 @@ static struct config_array_setting *populate_settings_array(settings_t *settings SETTING_ARRAY("cheevos_username", settings->arrays.cheevos_username, false, NULL, true); SETTING_ARRAY("cheevos_password", settings->arrays.cheevos_password, false, NULL, true); SETTING_ARRAY("cheevos_token", settings->arrays.cheevos_token, false, NULL, true); + SETTING_ARRAY("cheevos_leaderboards_enable", settings->arrays.cheevos_leaderboards_enable, true, "false", true); #endif SETTING_ARRAY("video_context_driver", settings->arrays.video_context_driver, false, NULL, true); SETTING_ARRAY("audio_driver", settings->arrays.audio_driver, false, NULL, true); @@ -1653,7 +1654,6 @@ static struct config_bool_setting *populate_settings_bool( SETTING_BOOL("cheevos_enable", &settings->bools.cheevos_enable, true, DEFAULT_CHEEVOS_ENABLE, false); SETTING_BOOL("cheevos_test_unofficial", &settings->bools.cheevos_test_unofficial, true, false, false); SETTING_BOOL("cheevos_hardcore_mode_enable", &settings->bools.cheevos_hardcore_mode_enable, true, false, false); - SETTING_BOOL("cheevos_leaderboards_enable", &settings->bools.cheevos_leaderboards_enable, true, false, false); SETTING_BOOL("cheevos_richpresence_enable", &settings->bools.cheevos_richpresence_enable, true, true, false); SETTING_BOOL("cheevos_unlock_sound_enable", &settings->bools.cheevos_unlock_sound_enable, true, false, false); SETTING_BOOL("cheevos_verbose_enable", &settings->bools.cheevos_verbose_enable, true, false, false); diff --git a/configuration.h b/configuration.h index d63cf24e00..da6bec10b7 100644 --- a/configuration.h +++ b/configuration.h @@ -338,6 +338,7 @@ typedef struct settings char cheevos_username[32]; char cheevos_password[256]; char cheevos_token[32]; + char cheevos_leaderboards_enable[32]; char video_context_driver[32]; char audio_driver[32]; char audio_resampler[32]; @@ -675,7 +676,6 @@ typedef struct settings bool cheevos_enable; bool cheevos_test_unofficial; bool cheevos_hardcore_mode_enable; - bool cheevos_leaderboards_enable; bool cheevos_richpresence_enable; bool cheevos_badges_enable; bool cheevos_verbose_enable; diff --git a/intl/msg_hash_us.h b/intl/msg_hash_us.h index b015a4213e..26d70206a6 100644 --- a/intl/msg_hash_us.h +++ b/intl/msg_hash_us.h @@ -7559,6 +7559,14 @@ MSG_HASH( MENU_ENUM_LABEL_VALUE_CHEEVOS_UNSUPPORTED_ENTRY, "Unsupported" ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_CHEEVOS_TRACKERS_ONLY, + "Trackers Only" + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_CHEEVOS_NOTIFICATIONS_ONLY, + "Notifications Only" +) MSG_HASH( MENU_ENUM_LABEL_VALUE_DONT_CARE, "Don't care" diff --git a/menu/cbs/menu_cbs_ok.c b/menu/cbs/menu_cbs_ok.c index d4c5f2fe90..1bc68fb2b5 100644 --- a/menu/cbs/menu_cbs_ok.c +++ b/menu/cbs/menu_cbs_ok.c @@ -5793,8 +5793,25 @@ static int generic_action_ok_dropdown_setting(const char *path, const char *labe *setting->value.target.fraction = (float)val; } break; - case ST_STRING: case ST_STRING_OPTIONS: + if (setting->get_string_representation) + { + struct string_list tmp_str_list = { 0 }; + string_list_initialize(&tmp_str_list); + string_split_noalloc(&tmp_str_list, + setting->values, "|"); + + if (idx < tmp_str_list.size) + { + strlcpy(setting->value.target.string, + tmp_str_list.elems[idx].data, setting->size); + } + + string_list_deinitialize(&tmp_str_list); + break; + } + /* fallthrough */ + case ST_STRING: case ST_PATH: case ST_DIR: strlcpy(setting->value.target.string, path, diff --git a/menu/menu_displaylist.c b/menu/menu_displaylist.c index f38523bdf0..afe81c1d57 100644 --- a/menu/menu_displaylist.c +++ b/menu/menu_displaylist.c @@ -7056,7 +7056,7 @@ unsigned menu_displaylist_build_list( {MENU_ENUM_LABEL_CHEEVOS_USERNAME, PARSE_ONLY_STRING, false }, {MENU_ENUM_LABEL_CHEEVOS_PASSWORD, PARSE_ONLY_STRING, false }, {MENU_ENUM_LABEL_CHEEVOS_HARDCORE_MODE_ENABLE, PARSE_ONLY_BOOL, false }, - {MENU_ENUM_LABEL_CHEEVOS_LEADERBOARDS_ENABLE, PARSE_ONLY_BOOL, false }, + {MENU_ENUM_LABEL_CHEEVOS_LEADERBOARDS_ENABLE, PARSE_ONLY_STRING_OPTIONS, false }, {MENU_ENUM_LABEL_CHEEVOS_RICHPRESENCE_ENABLE, PARSE_ONLY_BOOL, false }, {MENU_ENUM_LABEL_CHEEVOS_BADGES_ENABLE, PARSE_ONLY_BOOL, false }, {MENU_ENUM_LABEL_CHEEVOS_TEST_UNOFFICIAL, PARSE_ONLY_BOOL, false }, @@ -10481,7 +10481,6 @@ bool menu_displaylist_ctl(enum menu_displaylist_ctl_state type, info->need_push = true; info->need_refresh = true; break; - case DISPLAYLIST_CORES_SUPPORTED: menu_entries_ctl(MENU_ENTRIES_CTL_CLEAR, info->list); info->need_sort = true; @@ -12159,12 +12158,24 @@ bool menu_displaylist_ctl(enum menu_displaylist_ctl_state type, bool checked_found = false; unsigned checked = 0; + char* orig_val = setting->get_string_representation ? + strdup(setting->value.target.string) : setting->value.target.string; + char val_s[256], val_d[32]; + snprintf(val_d, sizeof(val_d), "%d", setting->enum_idx); + for (i = 0; i < size; i++) { - char val_d[256]; - snprintf(val_d, sizeof(val_d), "%d", setting->enum_idx); + const char* val = tmp_str_list.elems[i].data; + if (setting->get_string_representation) + { + strlcpy(setting->value.target.string, val, setting->size); + setting->get_string_representation(setting, + val_s, sizeof(val_s)); + val = val_s; + } + if (menu_entries_append_enum(info->list, - tmp_str_list.elems[i].data, + val, val_d, MENU_ENUM_LABEL_NO_ITEMS, MENU_SETTING_DROPDOWN_SETTING_STRING_OPTIONS_ITEM, i, 0)) @@ -12172,13 +12183,19 @@ bool menu_displaylist_ctl(enum menu_displaylist_ctl_state type, if (!checked_found && string_is_equal( tmp_str_list.elems[i].data, - setting->value.target.string)) + orig_val)) { checked = i; checked_found = true; } } + if (setting->get_string_representation) + { + strlcpy(setting->value.target.string, orig_val, setting->size); + free(orig_val); + } + if (checked_found) { menu_entries_set_checked(info->list, checked, true); diff --git a/menu/menu_setting.c b/menu/menu_setting.c index a18d65fb50..191313db55 100644 --- a/menu/menu_setting.c +++ b/menu/menu_setting.c @@ -2756,6 +2756,80 @@ static int setting_action_ok_uint( return 0; } +static int setting_string_action_left_string_options( + rarch_setting_t* setting, size_t idx, bool wraparound) +{ + struct string_list tmp_str_list = { 0 }; + size_t i; + + if (!setting) + return -1; + + string_list_initialize(&tmp_str_list); + string_split_noalloc(&tmp_str_list, + setting->values, "|"); + + for (i = 0; i < tmp_str_list.size; ++i) + { + if (string_is_equal(tmp_str_list.elems[i].data, setting->value.target.string)) + { + i = (i + tmp_str_list.size - 1) % tmp_str_list.size; + strlcpy(setting->value.target.string, + tmp_str_list.elems[i].data, setting->size); + + if (setting->change_handler) + setting->change_handler(setting); + + string_list_deinitialize(&tmp_str_list); + return 0; + } + } + + string_list_deinitialize(&tmp_str_list); + return -1; +} + +static int setting_string_action_right_string_options( + rarch_setting_t* setting, size_t idx, bool wraparound) +{ + struct string_list tmp_str_list = { 0 }; + size_t i; + + if (!setting) + return -1; + + string_list_initialize(&tmp_str_list); + string_split_noalloc(&tmp_str_list, + setting->values, "|"); + + for (i = 0; i < tmp_str_list.size; ++i) + { + if (string_is_equal(tmp_str_list.elems[i].data, setting->value.target.string)) + { + i = (i + 1) % tmp_str_list.size; + strlcpy(setting->value.target.string, + tmp_str_list.elems[i].data, setting->size); + + if (setting->change_handler) + setting->change_handler(setting); + + string_list_deinitialize(&tmp_str_list); + return 0; + } + } + + string_list_deinitialize(&tmp_str_list); + return -1; +} + +static int setting_action_ok_mapped_string( + rarch_setting_t* setting, size_t idx, bool wraparound) +{ + /* this is functionally the same as setting_action_ok_uint. + * the mapping happens in menu_displaylist_ctl */ + return setting_action_ok_uint(setting, idx, wraparound); +} + static void setting_get_string_representation_streaming_mode( rarch_setting_t *setting, char *s, size_t len) @@ -7436,6 +7510,28 @@ static void achievement_leaderboards_enabled_write_handler(rarch_setting_t* sett { rcheevos_leaderboards_enabled_changed(); } + +static void achievement_leaderboards_get_string_representation(rarch_setting_t* setting, char* s, size_t len) +{ + const char* value = setting->value.target.string; +#if defined(HAVE_GFX_WIDGETS) + if (string_is_equal(value, "true")) + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_ENABLED), len); + else if (string_is_equal(value, "trackers")) + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_CHEEVOS_TRACKERS_ONLY), len); + else if (string_is_equal(value, "notifications")) + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_CHEEVOS_NOTIFICATIONS_ONLY), len); + else + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_DISABLED), len); +#else + /* using these enum strings makes the widget behave like a boolean toggle */ + if (string_is_equal(value, "true")) + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_ON), len); + else + strlcpy(s, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF), len); +#endif +} + #endif static void update_streaming_url_write_handler(rarch_setting_t *setting) @@ -16775,21 +16871,29 @@ static bool setting_append_list( SD_FLAG_ADVANCED ); - CONFIG_BOOL( + CONFIG_STRING_OPTIONS( list, list_info, - &settings->bools.cheevos_leaderboards_enable, + settings->arrays.cheevos_leaderboards_enable, + sizeof(settings->arrays.cheevos_leaderboards_enable), MENU_ENUM_LABEL_CHEEVOS_LEADERBOARDS_ENABLE, MENU_ENUM_LABEL_VALUE_CHEEVOS_LEADERBOARDS_ENABLE, - false, - MENU_ENUM_LABEL_VALUE_OFF, - MENU_ENUM_LABEL_VALUE_ON, + "false", + "false|true", &group_info, &subgroup_info, parent_group, achievement_leaderboards_enabled_write_handler, - general_read_handler, - SD_FLAG_NONE - ); + general_read_handler); +#if defined(HAVE_GFX_WIDGETS) + (*list)[list_info->index - 1].values = "false|true|trackers|notifications"; + (*list)[list_info->index - 1].action_ok = setting_action_ok_mapped_string; +#else + (*list)[list_info->index - 1].action_ok = setting_string_action_left_string_options; +#endif + (*list)[list_info->index - 1].action_left = setting_string_action_left_string_options; + (*list)[list_info->index - 1].action_right = setting_string_action_right_string_options; + (*list)[list_info->index - 1].get_string_representation = achievement_leaderboards_get_string_representation; + (*list)[list_info->index - 1].free_flags &= ~SD_FREE_FLAG_VALUES; CONFIG_BOOL( list, list_info, @@ -18640,7 +18744,7 @@ static rarch_setting_t *menu_setting_new_internal(rarch_setting_info_t *list_inf root = msg_hash_to_str(MENU_ENUM_LABEL_MAIN_MENU); - for (i = 0; i < list_info->size; i++) + for (i = 0; i < (unsigned)list_info->size; i++) { MENU_SETTING_INITIALIZE(list, i); } diff --git a/msg_hash.h b/msg_hash.h index ec0806cdc6..460c0f66a4 100644 --- a/msg_hash.h +++ b/msg_hash.h @@ -683,6 +683,8 @@ enum msg_hash_enums MENU_LABEL(CHEEVOS_LOCKED_ENTRY), MENU_LABEL(CHEEVOS_UNSUPPORTED_ENTRY), MENU_LABEL(CHEEVOS_UNOFFICIAL_ENTRY), + MENU_ENUM_LABEL_VALUE_CHEEVOS_TRACKERS_ONLY, + MENU_ENUM_LABEL_VALUE_CHEEVOS_NOTIFICATIONS_ONLY, MENU_ENUM_LABEL_SHADER_PARAMETERS_ENTRY, MENU_ENUM_LABEL_RDB_ENTRY, From 376342a2c3cab2358db95559f66891493fba7860 Mon Sep 17 00:00:00 2001 From: Jamiras Date: Sat, 26 Sep 2020 09:59:50 -0600 Subject: [PATCH 2/2] hook up reset for all config_string_options --- menu/menu_setting.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/menu/menu_setting.c b/menu/menu_setting.c index 191313db55..ec64fef6cd 100644 --- a/menu/menu_setting.c +++ b/menu/menu_setting.c @@ -1955,6 +1955,8 @@ static rarch_setting_t setting_string_setting_options(enum setting_type type, subgroup, parent_group, change_handler, read_handler, dont_use_enum_idx); + result.action_start = setting_generic_action_start_default; + result.parent_group = parent_group; result.values = values; return result; @@ -8911,7 +8913,6 @@ static bool setting_append_list( general_read_handler, general_write_handler); SETTINGS_DATA_LIST_CURRENT_ADD_FLAGS(list, list_info, SD_FLAG_IS_DRIVER); - (*list)[list_info->index - 1].action_start = setting_generic_action_start_default; (*list)[list_info->index - 1].action_ok = setting_action_ok_uint; (*list)[list_info->index - 1].action_left = setting_string_action_left_driver; (*list)[list_info->index - 1].action_right = setting_string_action_right_driver;