Index: apps/settings.c =================================================================== --- apps/settings.c (revision 15674) +++ apps/settings.c (working copy) @@ -303,7 +303,17 @@ } else { - cfg_string_to_int(i,(int*)settings[i].setting,value); + int temp, *v = (int*)settings[i].setting; + bool found = cfg_string_to_int(i, &temp, value); + if (found) + { + if (settings[i].flags&F_TABLE_SETTING) + *v = settings[i].table_setting->values[temp]; + else + *v = temp; + } + else + *v = atoi(value); } break; case F_T_BOOL: @@ -357,9 +367,40 @@ bool cfg_int_to_string(int setting_id, int val, char* buf, int buf_len) { + int flags = settings[setting_id].flags; const char* start = settings[setting_id].cfg_vals; char* end = NULL; int count = 0; + + if ((flags&F_T_MASK)==F_T_INT && + flags&F_TABLE_SETTING) + { + int *value = settings[setting_id].table_setting->values; + while (start) + { + end = strchr(start,','); + if (value[count] == val) + { + if (end == NULL) + strncpy(buf, start, buf_len); + else + { + int len = (buf_len > (end-start))? end-start: buf_len; + strncpy(buf, start, len); + buf[len] = '\0'; + } + return true; + } + count++; + + if (end) + start = end+1; + else + break; + } + return false; + } + while (count < val) { start = strchr(start,','); @@ -461,8 +502,11 @@ } else { - cfg_int_to_string(i, *(int*)settings[i].setting, - value, MAX_PATH); + if (cfg_int_to_string(i, *(int*)settings[i].setting, + value, MAX_PATH) == false) + { + snprintf(value,MAX_PATH,"%d",*(int*)settings[i].setting); + } } break; case F_T_BOOL: Index: apps/gui/option_select.c =================================================================== --- apps/gui/option_select.c (revision 15674) +++ apps/gui/option_select.c (working copy) @@ -56,7 +56,9 @@ [UNIT_MB] = "MB", [UNIT_KBIT] = "kb/s", [UNIT_PM_TICK] = "units/10ms", }; - +/* these two vars are needed so arbitrary values can be added to the + TABLE_SETTING settings if the F_ALLOW_ARBITRARY_VALS flag is set */ +static int table_setting_oldval = 0, table_setting_array_position = 0; static char *option_get_valuestring(struct settings_list *setting, char *buffer, int buf_len, intptr_t temp_var) @@ -76,16 +78,27 @@ (char*)temp_var, info->suffix); } #endif - else if ((setting->flags & F_INT_SETTING) == F_INT_SETTING) + else if (((setting->flags & F_INT_SETTING) == F_INT_SETTING) || + ((setting->flags & F_TABLE_SETTING) == F_TABLE_SETTING)) { - struct int_setting *info = setting->int_setting; - if (info->formatter) - info->formatter(buffer, buf_len, (int)temp_var, - unit_strings[info->unit]); + struct int_setting *int_info = setting->int_setting; + struct table_setting *tbl_info = setting->table_setting; + const char *unit; + void (*formatter)(char*, size_t, int, const char*); + if ((setting->flags & F_INT_SETTING) == F_INT_SETTING) + { + formatter = int_info->formatter; + unit = unit_strings[int_info->unit]; + } else - snprintf(buffer, buf_len, "%d %s", (int)temp_var, - unit_strings[info->unit]? - unit_strings[info->unit]:""); + { + formatter = tbl_info->formatter; + unit = unit_strings[tbl_info->unit]; + } + if (formatter) + formatter(buffer, buf_len, (int)temp_var, unit); + else + snprintf(buffer, buf_len, "%d %s", (int)temp_var, unit?unit:""); } else if ((setting->flags & F_T_SOUND) == F_T_SOUND) { @@ -148,13 +161,27 @@ { } #endif - else if ((setting->flags & F_INT_SETTING) == F_INT_SETTING) + else if (((setting->flags & F_INT_SETTING) == F_INT_SETTING) || + ((setting->flags & F_TABLE_SETTING) == F_TABLE_SETTING)) { - struct int_setting *info = setting->int_setting; - if (info->get_talk_id) - talk_id(info->get_talk_id((int)temp_var), false); + struct int_setting *int_info = setting->int_setting; + struct table_setting *tbl_info = setting->table_setting; + int unit; + long (*get_talk_id)(int); + if ((setting->flags & F_INT_SETTING) == F_INT_SETTING) + { + unit = int_info->unit; + get_talk_id = int_info->get_talk_id; + } + else + { + unit = tbl_info->unit; + get_talk_id = tbl_info->get_talk_id; + } + if (get_talk_id) + talk_id(get_talk_id((int)temp_var), false); else - talk_value((int)temp_var, info->unit, false); + talk_value((int)temp_var, unit, false); } else if ((setting->flags & F_T_SOUND) == F_T_SOUND) { @@ -259,6 +286,20 @@ if (((setting->flags & F_BOOL_SETTING) == F_BOOL_SETTING) || ((setting->flags & F_CHOICE_SETTING) == F_CHOICE_SETTING)) return selection; + else if ((setting->flags & F_TABLE_SETTING) == F_TABLE_SETTING) + { + struct table_setting *info = setting->table_setting; + if (setting->flags&F_ALLOW_ARBITRARY_VALS && + table_setting_array_position != -1 && + (selection >= table_setting_array_position)) + { + if (selection == table_setting_array_position) + return table_setting_oldval; + return info->values[selection-1]; + } + else + return info->values[selection]; + } else if ((setting->flags & F_T_SOUND) == F_T_SOUND) { int setting_id = setting->sound_setting->setting; @@ -350,6 +391,27 @@ selected = oldvalue; function = setting->choice_setting->option_callback; } + else if (setting->flags&F_TABLE_SETTING) + { + struct table_setting *info = setting->table_setting; + int i; + nb_items = info->count; + selected = 0; + table_setting_array_position = -1; + for (i=0;selected==0 && iflags&F_ALLOW_ARBITRARY_VALS && + (oldvalue < info->values[i])) + { + table_setting_oldval = oldvalue; + table_setting_array_position = i; + selected = i; + nb_items++; + } + else if (oldvalue == info->values[i]) + selected = i; + } + } else if (setting->flags&F_T_SOUND) { int setting_id = setting->sound_setting->setting; @@ -388,7 +450,6 @@ if (boolfunction) function = bool_funcwrapper; } - gui_synclist_set_nb_items(&lists, nb_items); gui_synclist_select_item(&lists, selected); Index: apps/settings_list.c =================================================================== --- apps/settings_list.c (revision 15674) +++ apps/settings_list.c (working copy) @@ -145,8 +145,13 @@ {.int_setting = (struct int_setting[]){ \ {cb, unit, min, max, step, formatter, get_talk_id}}}} +#define TABLE_SETTING(flags, var, lang_id, default, name, cfg_vals, \ + unit, formatter, get_talk_id, cb, count, ...) \ + {flags|F_TABLE_SETTING|F_T_INT, &global_settings.var, \ + lang_id, INT(default), name, cfg_vals, \ + {.table_setting = (struct table_setting[]) { \ + {cb, formatter, get_talk_id, unit, count, (int[]){__VA_ARGS__}}}}} - /* some sets of values which are used more than once, to save memory */ static const char off_on[] = "off,on"; static const char off_on_ask[] = "off,on,ask"; @@ -373,6 +378,14 @@ const struct settings_list settings[] = { +#if 0 + /* TABLE_SETTING example... remove once its acutally used by a setting + the config string is used to map a string in the .cfg to an actual + value. the first string is the first value, etc... */ + TABLE_SETTING(F_ALLOW_ARBITRARY_VALS, test, LANG_VOLUME, 15, "test", "always on,off", UNIT_SEC, + NULL, backlight_getlang, NULL, 21, + -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 15, 20, 25, 30, 45, 60, 75, 90, 120), +#endif /* sound settings */ SOUND_SETTING(F_NO_WRAP,volume, LANG_VOLUME, "volume", SOUND_VOLUME), SOUND_SETTING(0, balance, LANG_BALANCE, "balance", SOUND_BALANCE), Index: apps/settings_list.h =================================================================== --- apps/settings_list.h (revision 15674) +++ apps/settings_list.h (working copy) @@ -85,6 +85,17 @@ #define F_CHOICE_SETTING 0x100 #define F_CHOICETALKS 0x200 /* uses .talks in the above struct for the talks */ /* and cfg_vals for the strings to display */ + +struct table_setting { + void (*option_callback)(int); + void (*formatter)(char*, size_t, int, const char*); + long (*get_talk_id)(int); + int unit; + int count; + int *values; +}; +#define F_TABLE_SETTING 0x1000 +#define F_ALLOW_ARBITRARY_VALS 0x2000 /* these use the _isfunc_type type for the function */ /* typedef int (*_isfunc_type)(void); */ #define F_MIN_ISFUNC 0x100000 /* min(above) is function pointer to above type */ @@ -94,8 +105,8 @@ #define F_THEMESETTING 0x0800000 #define F_RECSETTING 0x1000000 -#define F_NVRAM_BYTES_MASK 0xE000 /*0-4 bytes can be stored */ -#define F_NVRAM_MASK_SHIFT 13 +#define F_NVRAM_BYTES_MASK 0xE0000 /*0-4 bytes can be stored */ +#define F_NVRAM_MASK_SHIFT 17 #define NVRAM_CONFIG_VERSION 4 /* Above define should be bumped if - a new NVRAM setting is added between 2 other NVRAM settings @@ -107,7 +118,7 @@ #define F_NO_WRAP 0x1000 /* used if the list should not wrap */ struct settings_list { - uint32_t flags; /* ____ ___R TFFF ____ NNN_ PTVC IFRB STTT */ + uint32_t flags; /* ____ ___R TFFF NNN_ __AT PTVC IFRB STTT */ void *setting; int lang_id; /* -1 for none */ union storage_type default_val; @@ -121,6 +132,7 @@ struct filename_setting *filename_setting; /* use F_FILENAME */ struct int_setting *int_setting; /* use F_INT_SETTING */ struct choice_setting *choice_setting; /* F_CHOICE_SETTING */ + struct table_setting *table_setting; /* F_TABLE_SETTING */ }; };