mirror of
https://github.com/libretro/RetroArch
synced 2025-03-29 22:20:21 +00:00
Merge pull request #2403 from fr500/master
Allow core options to be game specific
This commit is contained in:
commit
8b9b4242f7
@ -517,6 +517,7 @@ static bool default_core_specific_config = true;
|
||||
static bool default_core_specific_config = false;
|
||||
#endif
|
||||
|
||||
static bool default_game_specific_options = true;
|
||||
static bool default_auto_overrides_enable = false;
|
||||
static bool default_auto_remaps_enable = false;
|
||||
|
||||
|
@ -729,6 +729,7 @@ static void config_set_defaults(void)
|
||||
*settings->menu_config_directory = '\0';
|
||||
#endif
|
||||
settings->core_specific_config = default_core_specific_config;
|
||||
settings->game_specific_options = default_game_specific_options;
|
||||
settings->auto_overrides_enable = default_auto_overrides_enable;
|
||||
settings->auto_remaps_enable = default_auto_remaps_enable;
|
||||
|
||||
@ -1749,6 +1750,7 @@ static bool config_load_file(const char *path, bool set_defaults)
|
||||
config_read_keybinds_conf(conf);
|
||||
|
||||
CONFIG_GET_BOOL_BASE(conf, settings, core_specific_config, "core_specific_config");
|
||||
CONFIG_GET_BOOL_BASE(conf, settings, game_specific_options, "game_specific_options");
|
||||
CONFIG_GET_BOOL_BASE(conf, settings, auto_overrides_enable, "auto_overrides_enable");
|
||||
CONFIG_GET_BOOL_BASE(conf, settings, auto_remaps_enable, "auto_remaps_enable");
|
||||
|
||||
@ -2787,6 +2789,8 @@ bool config_save_file(const char *path)
|
||||
|
||||
config_set_bool(conf, "core_specific_config",
|
||||
settings->core_specific_config);
|
||||
config_set_bool(conf, "game_specific_options",
|
||||
settings->game_specific_options);
|
||||
config_set_bool(conf, "auto_overrides_enable",
|
||||
settings->auto_overrides_enable);
|
||||
config_set_bool(conf, "auto_remaps_enable",
|
||||
|
@ -361,6 +361,7 @@ typedef struct settings
|
||||
bool load_dummy_on_core_shutdown;
|
||||
|
||||
bool core_specific_config;
|
||||
bool game_specific_options;
|
||||
bool auto_overrides_enable;
|
||||
bool auto_remaps_enable;
|
||||
|
||||
|
@ -237,6 +237,30 @@ bool core_option_flush(core_option_manager_t *opt)
|
||||
return config_file_write(opt->conf, opt->conf_path);
|
||||
}
|
||||
|
||||
/**
|
||||
* core_option_flush_game_specific:
|
||||
* @opt : options manager handle
|
||||
* @path : path for the core options file
|
||||
*
|
||||
* Writes core option key-pair values to a custom file.
|
||||
*
|
||||
* Returns: true (1) if core option values could be
|
||||
* successfully saved to disk, otherwise false (0).
|
||||
**/
|
||||
bool core_option_flush_game_specific(core_option_manager_t *opt, char* path)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0; i < opt->size; i++)
|
||||
{
|
||||
struct core_option *option = (struct core_option*)&opt->opts[i];
|
||||
|
||||
if (option)
|
||||
config_set_string(opt->conf, option->key, core_option_get_val(opt, i));
|
||||
}
|
||||
|
||||
return config_file_write(opt->conf, path);
|
||||
}
|
||||
|
||||
/**
|
||||
* core_option_size:
|
||||
* @opt : options manager handle
|
||||
|
@ -62,6 +62,18 @@ bool core_option_updated(core_option_manager_t *opt);
|
||||
**/
|
||||
bool core_option_flush(core_option_manager_t *opt);
|
||||
|
||||
/**
|
||||
* core_option_flush_game_specific:
|
||||
* @opt : options manager handle
|
||||
* @path : path for the core options file
|
||||
*
|
||||
* Writes core option key-pair values to a custom file.
|
||||
*
|
||||
* Returns: true (1) if core option values could be
|
||||
* successfully saved to disk, otherwise false (0).
|
||||
**/
|
||||
bool core_option_flush_game_specific(core_option_manager_t *opt, char* path);
|
||||
|
||||
/**
|
||||
* core_option_free:
|
||||
* @opt : options manager handle
|
||||
|
69
dynamic.c
69
dynamic.c
@ -589,6 +589,64 @@ static void rarch_log_libretro(enum retro_log_level level,
|
||||
va_end(vp);
|
||||
}
|
||||
|
||||
/**
|
||||
* rarch_game_specific_options:
|
||||
* @cmd : Output variable with path to core options file.
|
||||
*
|
||||
* Environment callback function implementation.
|
||||
*
|
||||
* Returns: true (1) if a game specific core options path has been found,
|
||||
* otherwise false (0).
|
||||
**/
|
||||
static bool rarch_game_specific_options(char **output)
|
||||
{
|
||||
settings_t *settings = config_get_ptr();
|
||||
global_t *global = global_get_ptr();
|
||||
rarch_system_info_t *system = rarch_system_info_get_ptr();
|
||||
|
||||
const char *core_name = NULL;
|
||||
const char *game_name = NULL;
|
||||
config_file_t *option_file = NULL;
|
||||
char game_path[PATH_MAX_LENGTH] = {0};
|
||||
char config_directory[PATH_MAX_LENGTH] = {0};
|
||||
|
||||
/* Config directory: config_directory.
|
||||
* Try config directory setting first,
|
||||
* fallback to the location of the current configuration file. */
|
||||
|
||||
if (settings->menu_config_directory[0] != '\0')
|
||||
strlcpy(config_directory, settings->menu_config_directory, PATH_MAX_LENGTH);
|
||||
else if (global->path.config[0] != '\0')
|
||||
fill_pathname_basedir(config_directory, global->path.config, PATH_MAX_LENGTH);
|
||||
else
|
||||
{
|
||||
RARCH_WARN("Per-game Options: no config directory set\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
core_name = system->info.library_name;
|
||||
game_name = path_basename(global->name.base);
|
||||
|
||||
RARCH_LOG("Per-game Options: core name: %s\n", core_name);
|
||||
RARCH_LOG("Per-game Options: game name: %s\n", game_name);
|
||||
|
||||
/* Concatenate strings into full paths for game_path */
|
||||
|
||||
fill_pathname_join(game_path, config_directory, core_name, PATH_MAX_LENGTH);
|
||||
fill_pathname_join(game_path, game_path, game_name, PATH_MAX_LENGTH);
|
||||
strlcat(game_path, ".opt", PATH_MAX_LENGTH);
|
||||
|
||||
option_file = config_file_new(game_path);
|
||||
if(option_file)
|
||||
{
|
||||
RARCH_LOG("Per-game options: game-specific core options found at %s\n", game_path);
|
||||
*output = game_path;
|
||||
return true;
|
||||
}
|
||||
config_file_free(option_file);
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* rarch_environment_cb:
|
||||
* @cmd : Identifier of command.
|
||||
@ -663,8 +721,17 @@ bool rarch_environment_cb(unsigned cmd, void *data)
|
||||
"retroarch-core-options.cfg", sizeof(buf));
|
||||
options_path = buf;
|
||||
}
|
||||
|
||||
char *game_options_path = NULL;
|
||||
bool ret = false;
|
||||
|
||||
if (settings->game_specific_options)
|
||||
ret = rarch_game_specific_options(&game_options_path);
|
||||
|
||||
system->core_options = core_option_new(options_path, vars);
|
||||
if(ret)
|
||||
system->core_options = core_option_new(game_options_path, vars);
|
||||
else
|
||||
system->core_options = core_option_new(options_path, vars);
|
||||
}
|
||||
|
||||
break;
|
||||
|
@ -958,6 +958,7 @@ static void menu_action_setting_disp_set_label(file_list_t* list,
|
||||
{
|
||||
rarch_system_info_t *system = rarch_system_info_get_ptr();
|
||||
uint32_t hash_label = menu_hash_calculate(label);
|
||||
global_t *global = global_get_ptr();
|
||||
|
||||
*s = '\0';
|
||||
*w = 19;
|
||||
@ -1029,6 +1030,14 @@ static void menu_action_setting_disp_set_label(file_list_t* list,
|
||||
|
||||
strlcpy(s, core_opt ? core_opt : "", len);
|
||||
}
|
||||
else if (type >= MENU_SETTINGS_CORE_OPTION_CREATE)
|
||||
{
|
||||
const char *core_opt = NULL;
|
||||
if (!system)
|
||||
return;
|
||||
|
||||
strlcpy(s, global->name.base ? path_basename(global->name.base) : "", len);
|
||||
}
|
||||
else
|
||||
menu_setting_get_label(list, s,
|
||||
len, w, type, label, entry_label, i);
|
||||
|
@ -1246,6 +1246,54 @@ static int action_ok_disk_cycle_tray_status(const char *path,
|
||||
return generic_action_ok_command(EVENT_CMD_DISK_EJECT_TOGGLE);
|
||||
}
|
||||
|
||||
static int action_ok_option_create(const char *path,
|
||||
const char *label, unsigned type, size_t idx, size_t entry_idx)
|
||||
{
|
||||
/* create folder and core options stub file for subsequent runs */
|
||||
settings_t *settings = config_get_ptr();
|
||||
global_t *global = global_get_ptr();
|
||||
rarch_system_info_t *system = rarch_system_info_get_ptr();
|
||||
|
||||
const char *core_name = NULL;
|
||||
const char *game_name = NULL;
|
||||
char core_path[PATH_MAX_LENGTH] = {0};
|
||||
char game_path[PATH_MAX_LENGTH] = {0};
|
||||
char config_directory[PATH_MAX_LENGTH] = {0};
|
||||
char msg[PATH_MAX_LENGTH] = {0};
|
||||
|
||||
/* Config directory: config_directory.
|
||||
* Try config directory setting first,
|
||||
* fallback to the location of the current configuration file. */
|
||||
if (settings->menu_config_directory[0] != '\0')
|
||||
strlcpy(config_directory, settings->menu_config_directory, PATH_MAX_LENGTH);
|
||||
else if (global->path.config[0] != '\0')
|
||||
fill_pathname_basedir(config_directory, global->path.config, PATH_MAX_LENGTH);
|
||||
else
|
||||
{
|
||||
RARCH_WARN("Per-game Options: no config directory set\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
core_name = system->info.library_name;
|
||||
game_name = path_basename(global->name.base);
|
||||
|
||||
/* Concatenate strings into full paths for game_path */
|
||||
fill_pathname_join(core_path, config_directory, core_name, PATH_MAX_LENGTH);
|
||||
fill_pathname_join(game_path, config_directory, core_name, PATH_MAX_LENGTH);
|
||||
fill_pathname_join(game_path, game_path, game_name, PATH_MAX_LENGTH);
|
||||
strlcat(game_path, ".opt", PATH_MAX_LENGTH);
|
||||
|
||||
if (!path_is_directory(core_path))
|
||||
path_mkdir(core_path);
|
||||
|
||||
if(core_option_flush_game_specific(system->core_options,game_path))
|
||||
menu_display_msg_queue_push("Core options file saved successfully", 1, 100, true);
|
||||
else
|
||||
menu_display_msg_queue_push("Error saving core options file", 1, 100, true);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int action_ok_close_content(const char *path,
|
||||
const char *label, unsigned type, size_t idx, size_t entry_idx)
|
||||
{
|
||||
@ -2316,6 +2364,9 @@ static int menu_cbs_init_bind_ok_compare_type(menu_file_list_cbs_t *cbs,
|
||||
case MENU_SETTINGS_CORE_DISK_OPTIONS_DISK_CYCLE_TRAY_STATUS:
|
||||
BIND_ACTION_OK(cbs, action_ok_disk_cycle_tray_status);
|
||||
break;
|
||||
case MENU_SETTINGS_CORE_OPTION_CREATE:
|
||||
BIND_ACTION_OK(cbs, action_ok_option_create);
|
||||
break;
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
|
@ -312,6 +312,8 @@ static const char *menu_hash_to_str_us_label(uint32_t hash)
|
||||
return "slowmotion_ratio";
|
||||
case MENU_LABEL_CORE_SPECIFIC_CONFIG:
|
||||
return "core_specific_config";
|
||||
case MENU_LABEL_GAME_SPECIFIC_OPTIONS:
|
||||
return "game_specific_options";
|
||||
case MENU_LABEL_AUTO_OVERRIDES_ENABLE:
|
||||
return "auto_overrides_enable";
|
||||
case MENU_LABEL_CONFIG_SAVE_ON_EXIT:
|
||||
@ -1024,6 +1026,10 @@ const char *menu_hash_to_str_us(uint32_t hash)
|
||||
return "Slow-Motion Ratio";
|
||||
case MENU_LABEL_VALUE_CORE_SPECIFIC_CONFIG:
|
||||
return "Configuration Per-Core";
|
||||
case MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS:
|
||||
return "Use per-game core options if available";
|
||||
case MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS_CREATE:
|
||||
return "Create game-options file";
|
||||
case MENU_LABEL_VALUE_AUTO_OVERRIDES_ENABLE:
|
||||
return "Load Override Files Automatically";
|
||||
case MENU_LABEL_VALUE_CONFIG_SAVE_ON_EXIT:
|
||||
|
@ -53,10 +53,12 @@
|
||||
#define MENU_SETTINGS_CORE_INFO_NONE 0xffff
|
||||
#define MENU_SETTINGS_CORE_OPTION_NONE 0xffff
|
||||
#define MENU_SETTINGS_CHEEVOS_NONE 0xffff
|
||||
#define MENU_SETTINGS_CORE_OPTION_CREATE 0x05000
|
||||
#define MENU_SETTINGS_CORE_OPTION_START 0x10000
|
||||
#define MENU_SETTINGS_PLAYLIST_ASSOCIATION_START 0x20000
|
||||
#define MENU_SETTINGS_CHEEVOS_START 0x40000
|
||||
|
||||
|
||||
#define MENU_KEYBOARD_BIND_TIMEOUT_SECONDS 5
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
@ -3000,6 +3000,12 @@ int menu_displaylist_push_list(menu_displaylist_info_t *info, unsigned type)
|
||||
{
|
||||
size_t opts = core_option_size(system->core_options);
|
||||
|
||||
if (settings->game_specific_options)
|
||||
{
|
||||
menu_entries_push(info->list,
|
||||
menu_hash_to_str(MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS_CREATE), "",
|
||||
MENU_SETTINGS_CORE_OPTION_CREATE, 0, 0);
|
||||
}
|
||||
if (opts == 0)
|
||||
{
|
||||
menu_entries_push(info->list,
|
||||
|
@ -304,6 +304,9 @@ extern "C" {
|
||||
#define MENU_LABEL_VALUE_VIDEO_FULLSCREEN 0x232743caU
|
||||
#define MENU_LABEL_CORE_SPECIFIC_CONFIG 0x3c9a55e8U
|
||||
#define MENU_LABEL_VALUE_CORE_SPECIFIC_CONFIG 0x8b8bec5aU
|
||||
#define MENU_LABEL_GAME_SPECIFIC_OPTIONS 0x142ec90fU
|
||||
#define MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS 0x6aed8a05U
|
||||
#define MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS_CREATE 0xf8d2456cU
|
||||
#define MENU_LABEL_AUTO_OVERRIDES_ENABLE 0x35ff91b6U
|
||||
#define MENU_LABEL_VALUE_AUTO_OVERRIDES_ENABLE 0xc21c3a11U
|
||||
#define MENU_LABEL_AUTO_REMAPS_ENABLE 0x98c8f98bU
|
||||
|
@ -3477,6 +3477,20 @@ static bool setting_append_list_configuration_options(
|
||||
general_write_handler,
|
||||
general_read_handler);
|
||||
|
||||
CONFIG_BOOL(
|
||||
settings->game_specific_options,
|
||||
menu_hash_to_str(MENU_LABEL_GAME_SPECIFIC_OPTIONS),
|
||||
menu_hash_to_str(MENU_LABEL_VALUE_GAME_SPECIFIC_OPTIONS),
|
||||
default_game_specific_options,
|
||||
menu_hash_to_str(MENU_VALUE_OFF),
|
||||
menu_hash_to_str(MENU_VALUE_ON),
|
||||
group_info.name,
|
||||
subgroup_info.name,
|
||||
parent_group,
|
||||
general_write_handler,
|
||||
general_read_handler);
|
||||
|
||||
|
||||
CONFIG_BOOL(
|
||||
settings->auto_overrides_enable,
|
||||
menu_hash_to_str(MENU_LABEL_AUTO_OVERRIDES_ENABLE),
|
||||
|
Loading…
x
Reference in New Issue
Block a user