source: branches/reyalp-flt/core/gui.c @ 1511

Revision 1511, 117.5 KB checked in by philmoz, 2 years ago (diff)

Merge recent changes from main trunk to reyalp-flt branch.

  • Property svn:eol-style set to native
Line 
1#include "stdlib.h"
2#include "platform.h"
3#include "core.h"
4#include "keyboard.h"
5#include "conf.h"
6#include "camera.h"
7#include "font.h"
8#include "lang.h"
9#include "gui.h"
10#include "gui_lang.h"
11#include "gui_draw.h"
12#include "gui_menu.h"
13#include "gui_palette.h"
14#include "gui_mbox.h"
15#include "gui_mpopup.h"
16#include "console.h"
17#ifdef OPT_DEBUGGING
18#include "gui_debug.h"
19#endif
20#include "gui_fselect.h"
21#include "gui_batt.h"
22#include "gui_usb.h"
23#include "gui_space.h"
24#include "gui_osd.h"
25#ifdef OPT_TEXTREADER
26        #include "gui_read.h"
27#endif
28#include "gui_grid.h"
29#include "histogram.h"
30#include "motion_detector.h"
31#include "raw.h"
32#include "dng.h"
33#ifdef OPT_CURVES
34        #include "curves.h"
35#endif
36#ifdef OPT_EDGEOVERLAY
37        #include "modules.h"
38#endif
39#ifdef OPT_SCRIPTING
40    #include "script.h"
41    int script_params_has_changed=0;
42#endif
43#include "module_load.h"
44
45//-------------------------------------------------------------------
46
47#define OPTIONS_AUTOSAVE
48#define SPLASH_TIME               20
49
50//shortcuts
51//------------------------------------------------------------------
52// #define KEY_NONE (KEY_DUMMY+1)
53
54#if defined(CAMERA_a580) // Cam has not erase button AND Half press shoot button + Left sets AFL, + Up sets AEL!
55    //Alt mode
56    #define SHORTCUT_TOGGLE_RAW          KEY_DISPLAY
57    #define SHORTCUT_MF_TOGGLE           KEY_UP
58    //Half press shoot button
59    #define SHORTCUT_TOGGLE_HISTO        KEY_DOWN
60    #define SHORTCUT_TOGGLE_ZEBRA        KEY_MENU
61    #define SHORTCUT_TOGGLE_OSD          KEY_RIGHT
62    #define SHORTCUT_DISABLE_OVERRIDES   KEY_DISPLAY
63    //Alt mode & Manual mode   
64    #define SHORTCUT_SET_INFINITY        KEY_DISPLAY
65    #define SHORTCUT_SET_HYPERFOCAL      KEY_DOWN
66    // For models without ZOOM_LEVER  (#if !CAM_HAS_ZOOM_LEVER)
67    // SHORTCUT_SET_INFINITY is not used
68    // KEY_DISPLAY is used for gui_subj_dist_override_koef_enum;
69    // KEY_LEFT/KEY_RIGHT is used for gui_subj_dist_override_value_enum (because of no separate ZOOM_IN/OUT)
70
71#elif !CAM_HAS_ERASE_BUTTON
72//Alt mode
73 #define SHORTCUT_TOGGLE_RAW          KEY_DISPLAY
74 #define SHORTCUT_MF_TOGGLE           KEY_UP
75//Half press shoot button
76 #define SHORTCUT_TOGGLE_HISTO        KEY_DOWN
77 #define SHORTCUT_TOGGLE_ZEBRA        KEY_MENU
78 #define SHORTCUT_TOGGLE_OSD          KEY_RIGHT
79 #define SHORTCUT_DISABLE_OVERRIDES   KEY_LEFT
80//Alt mode & Manual mode
81 #define SHORTCUT_SET_INFINITY        KEY_DISPLAY
82 #define SHORTCUT_SET_HYPERFOCAL      KEY_DOWN
83 // For models without ZOOM_LEVER  (#if !CAM_HAS_ZOOM_LEVER)
84 // SHORTCUT_SET_INFINITY is not used
85 // KEY_DISPLAY is used for gui_subj_dist_override_koef_enum;
86 // KEY_LEFT/KEY_RIGHT is used for gui_subj_dist_override_value_enum (because of no separate ZOOM_IN/OUT)
87
88#elif defined(CAMERA_g7) || defined(CAMERA_sx10) || defined(CAMERA_sx1) || defined(CAMERA_sx120is) || defined(CAMERA_sx20) || defined(CAMERA_sx30) || defined(CAMERA_sx40hs)
89//Alt mode
90 #define SHORTCUT_TOGGLE_RAW          KEY_ERASE
91//Half press shoot button
92 #define SHORTCUT_TOGGLE_HISTO        KEY_DOWN
93 #define SHORTCUT_TOGGLE_ZEBRA        KEY_LEFT
94 #define SHORTCUT_TOGGLE_OSD          KEY_RIGHT
95 #define SHORTCUT_DISABLE_OVERRIDES   KEY_UP
96//Alt mode & Manual mode
97 #define SHORTCUT_SET_INFINITY        KEY_UP
98 #define SHORTCUT_SET_HYPERFOCAL      KEY_DOWN
99
100#elif defined(CAMERA_sx100is) ||defined(CAMERA_sx110is)
101//Alt mode
102 #define SHORTCUT_TOGGLE_RAW          KEY_ERASE
103//Half press shoot button
104 #define SHORTCUT_TOGGLE_HISTO        KEY_UP
105 #define SHORTCUT_TOGGLE_ZEBRA        KEY_DOWN
106 #define SHORTCUT_TOGGLE_OSD          KEY_RIGHT
107 #define SHORTCUT_DISABLE_OVERRIDES   KEY_LEFT
108//Alt mode & Manual mode
109 #define SHORTCUT_SET_INFINITY        KEY_UP
110 #define SHORTCUT_SET_HYPERFOCAL      KEY_DOWN
111
112 #else
113
114//Alt mode
115 #define SHORTCUT_TOGGLE_RAW          KEY_ERASE
116//Half press shoot button
117 #define SHORTCUT_TOGGLE_HISTO        KEY_UP
118 #define SHORTCUT_TOGGLE_ZEBRA        KEY_LEFT
119 #define SHORTCUT_TOGGLE_OSD          KEY_RIGHT
120 #define SHORTCUT_DISABLE_OVERRIDES   KEY_DOWN
121//Alt mode & Manual mode
122 #define SHORTCUT_SET_INFINITY        KEY_UP
123 #define SHORTCUT_SET_HYPERFOCAL      KEY_DOWN
124 #ifndef CAM_HAS_MANUAL_FOCUS
125 #define SHORTCUT_MF_TOGGLE           KEY_DISPLAY
126 #endif
127#endif
128
129
130// forward declarations
131//-------------------------------------------------------------------
132extern void dump_memory();
133// both from platform/generic/shooting.c
134extern const char* tv_override[];
135extern const int tv_override_amount;
136extern const int tv_override_zero_shift;
137
138static void gui_draw_osd();
139
140static void gui_draw_splash(char* logo, int logo_size);
141
142void user_menu_save();
143void user_menu_restore();
144// Menu procs
145//-------------------------------------------------------------------
146static void gui_show_build_info(int arg);
147static void gui_show_memory_info(int arg);
148static void     gui_modules_menu_load();
149
150#ifdef OPT_DEBUGGING
151    void gui_compare_props(int arg);
152    static void gui_menuproc_break_card(int arg);
153        static void gui_debug_shortcut(void);
154        static void save_romlog(int arg);
155#endif
156static void gui_draw_fselect(int arg);
157static void gui_draw_osd_le(int arg);
158#ifdef OPT_TEXTREADER
159static void gui_draw_read(int arg);
160static void gui_draw_read_last(int arg);
161#endif
162static void gui_draw_load_menu_rbf(int arg);
163static void gui_draw_load_symbol_rbf(int arg);          //AKA
164#ifdef OPT_TEXTREADER
165        static void gui_draw_load_rbf(int arg);
166#endif
167#ifdef OPT_CALENDAR
168static void gui_draw_calendar(int arg);
169#endif
170static void gui_draw_load_lang(int arg);
171static void gui_menuproc_mkbootdisk(int arg);
172#ifndef OPTIONS_AUTOSAVE
173static void gui_menuproc_save(int arg);
174#endif
175static void gui_menuproc_reset(int arg);
176static void gui_grid_lines_load(int arg);
177static void gui_raw_develop(int arg);
178static void gui_menuproc_swap_partitions(int arg);
179static void gui_menuproc_reset_files(int arg);
180#ifdef OPT_CURVES
181        static void gui_load_curve_selected(const char *fn);
182        static void gui_load_curve(int arg);
183#endif
184static const char* gui_histo_mode_enum(int change, int arg);
185static const char* gui_histo_layout_enum(int change, int arg);
186static const char* gui_font_enum(int change, int arg);
187
188#if CAM_ADJUSTABLE_ALT_BUTTON
189static const char* gui_alt_mode_button_enum(int change, int arg);
190#endif
191static const char* gui_alt_power_enum(int change, int arg);
192static const char* gui_video_bitrate_enum(int change, int arg);
193static const char* gui_av_override_enum(int change, int arg);
194#if ZOOM_OVERRIDE
195static const char* gui_zoom_override_enum(int change, int arg);
196#endif
197static const char* gui_tv_override_koef_enum(int change, int arg);
198static const char* gui_tv_override_value_enum(int change, int arg);
199static const char* gui_tv_enum_type_enum(int change, int arg);
200static const char* gui_subj_dist_override_value_enum(int change, int arg);
201static const char* gui_subj_dist_override_koef_enum(int change, int arg);
202/*
203static const char* gui_tv_exposure_order_enum(int change, int arg);
204static const char* gui_av_exposure_order_enum(int change, int arg);
205static const char* gui_iso_exposure_order_enum(int change, int arg);
206*/
207const char* gui_user_menu_show_enum(int change, int arg);
208static const char* gui_bad_pixel_enum(int change, int arg);
209static const char* gui_video_af_key_enum(int change, int arg);
210#ifdef OPT_CURVES
211        static const char* gui_conf_curve_enum(int change, int arg);
212#endif
213
214#ifdef OPT_EDGEOVERLAY
215static void gui_menuproc_edge_save(int arg);
216static void gui_menuproc_edge_load(int arg);
217#endif
218
219#ifdef OPT_SCRIPTING
220static void gui_load_script(int arg);
221static void gui_load_script_default(int arg);
222static const char* gui_script_param_set_enum(int change, int arg);
223#endif
224
225void rinit();
226
227// Menu callbacks
228//-------------------------------------------------------------------
229static void cb_step_25();
230static void cb_perc();
231static void cb_volts();
232static void cb_space_perc();
233static void cb_space_mb();
234static void cb_battery_menu_change(unsigned int item);
235static void cb_zebra_restore_screen();
236static void cb_zebra_restore_osd();
237#if DNG_SUPPORT
238static void cb_change_dng();
239void gui_menuproc_badpixel_create(int arg);
240#endif
241#if defined (DNG_EXT_FROM)
242static void cb_change_dng_usb_ext();
243#endif
244
245// for memory info, duplicated from lowlevel
246extern const char _start,_end;
247
248#ifdef OPT_DEBUGGING
249static int debug_tasklist_start;
250static int debug_display_direction=1;
251#endif
252// Menu definition
253//-------------------------------------------------------------------
254static CMenuItem remote_submenu_items[] = {
255    MENU_ITEM(0x71,LANG_MENU_REMOTE_ENABLE,            MENUITEM_BOOL,                    &conf.remote_enable, 0),
256    MENU_ITEM(0x0,LANG_MENU_SYNCHABLE_REMOTE,          MENUITEM_SEPARATOR, 0, 0 ),
257    MENU_ITEM(0x71,LANG_MENU_SYNCHABLE_REMOTE_ENABLE,  MENUITEM_BOOL,                    &conf.ricoh_ca1_mode, 0),
258    MENU_ITEM(0x5c,LANG_MENU_SYNCH_ENABLE,             MENUITEM_BOOL,                    &conf.synch_enable, 0),
259    MENU_ITEM(0x5c,LANG_MENU_SYNCH_DELAY_ENABLE,       MENUITEM_BOOL,                    &conf.synch_delay_enable, 0),
260    MENU_ITEM(0x5c,LANG_MENU_SYNCH_DELAY_VALUE,        MENUITEM_INT|MENUITEM_F_UNSIGNED, &conf.synch_delay_value, 0),
261    MENU_ITEM(0x5c,LANG_MENU_SYNCH_DELAY_COARSE_VALUE, MENUITEM_INT|MENUITEM_F_UNSIGNED, &conf.synch_delay_coarse_value, 0),
262    MENU_ITEM(0x5c,LANG_MENU_REMOTE_ZOOM_ENABLE,       MENUITEM_BOOL,                    &conf.remote_zoom_enable, 0),
263    MENU_ITEM(0x5f,LANG_MENU_REMOTE_ZOOM_TIMEOUT,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.zoom_timeout, MENU_MINMAX(2,10)),
264    MENU_ITEM(0x51,LANG_MENU_BACK,                     MENUITEM_UP, 0, 0),
265    {0}
266};
267static CMenu remote_submenu = {0x86,LANG_MENU_REMOTE_PARAM_TITLE, NULL, remote_submenu_items };
268
269
270#ifdef OPT_SCRIPTING
271static const char* gui_script_autostart_modes[]={ "Off", "On", "Once"};
272static CMenuItem script_submenu_items_top[] = {
273    MENU_ITEM(0x35,LANG_MENU_SCRIPT_LOAD,             MENUITEM_PROC,                      gui_load_script, 0 ),
274    MENU_ITEM(0x5f,LANG_MENU_SCRIPT_DELAY,            MENUITEM_INT|MENUITEM_F_UNSIGNED,   &conf.script_shoot_delay, 0 ),
275        // remote autostart
276        MENU_ENUM2(0x5f,LANG_MENU_SCRIPT_AUTOSTART,               &conf.script_startup, gui_script_autostart_modes ),
277
278#if CAM_REMOTE
279    MENU_ITEM(0x86,LANG_MENU_REMOTE_PARAM,            MENUITEM_SUBMENU,   &remote_submenu, 0 ),
280        //MENU_ITEM(0x71,LANG_MENU_SCRIPT_REMOTE_ENABLE,        MENUITEM_BOOL,                                          &conf.remote_enable, 0),
281#endif
282    MENU_ITEM(0x5d,LANG_MENU_SCRIPT_DEFAULT_VAL,     MENUITEM_PROC,                      gui_load_script_default, 0 ),
283    MENU_ITEM(0x5e,LANG_MENU_SCRIPT_PARAM_SET,     MENUITEM_ENUM,                         gui_script_param_set_enum, 0 ),
284    MENU_ITEM(0x5c,LANG_MENU_SCRIPT_PARAM_SAVE,             MENUITEM_BOOL,                    &conf.script_param_save, 0 ),
285    MENU_ITEM(0x0,(int)script_title,                 MENUITEM_SEPARATOR, 0, 0 ),
286//    MENU_ITEM(0x0,LANG_MENU_SCRIPT_CURRENT,          MENUITEM_SEPARATOR, 0, 0 ),
287//    MENU_ITEM(0x0,(int)script_title,                 MENUITEM_TEXT, 0, 0 ),
288//    MENU_ITEM(0x0,LANG_MENU_SCRIPT_PARAMS,           MENUITEM_SEPARATOR, 0, 0)
289};
290
291static CMenuItem script_submenu_items_bottom[] = {
292    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
293    {0}
294};
295
296static CMenuItem script_submenu_items[sizeof(script_submenu_items_top)/sizeof(script_submenu_items_top[0])+SCRIPT_NUM_PARAMS+
297                               sizeof(script_submenu_items_bottom)/sizeof(script_submenu_items_bottom[0])];
298static CMenu script_submenu = {0x27,LANG_MENU_SCRIPT_TITLE, NULL, script_submenu_items };
299#endif
300
301static const char* gui_autoiso_shutter_modes[] = { "Auto", "1/8s", "1/15s", "1/30s", "1/60s", "1/125s", "1/250s", "1/500s", "1/1000s"};
302static CMenuItem autoiso_submenu_items[] = {
303    MENU_ITEM(0x5c,LANG_MENU_AUTOISO_ENABLED,          MENUITEM_BOOL,   &conf.autoiso_enable, 0),
304    MENU_ENUM2(0x5f,LANG_MENU_AUTOISO_MIN_SHUTTER,  &conf.autoiso_shutter, gui_autoiso_shutter_modes ),
305    MENU_ITEM(0x5f,LANG_MENU_AUTOISO_USER_FACTOR,   MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.autoiso_user_factor, MENU_MINMAX(1, 8) ),
306#if CAM_HAS_IS
307    MENU_ITEM(0x5f,LANG_MENU_AUTOISO_IS_FACTOR,       MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.autoiso_is_factor, MENU_MINMAX(1, 8) ),
308#endif
309    MENU_ITEM(0x5f,LANG_MENU_AUTOISO_MAX_ISO_HI,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.autoiso_max_iso_hi, MENU_MINMAX(20, 160) ),
310    MENU_ITEM(0x5f,LANG_MENU_AUTOISO_MAX_ISO_AUTO, MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.autoiso_max_iso_auto, MENU_MINMAX(10, 80) ),
311    MENU_ITEM(0x5f,LANG_MENU_AUTOISO_MIN_ISO,           MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.autoiso_min_iso, MENU_MINMAX(1, 20) ),
312    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
313    {0}
314};
315static CMenu autoiso_submenu = {0x2d,LANG_MENU_AUTOISO_TITLE, NULL, autoiso_submenu_items };
316
317
318#ifdef OPT_TEXTREADER
319static const char* gui_reader_codepage_cps[] = { "Win1251", "DOS"};
320static CMenuItem reader_submenu_items[] = {
321    MENU_ITEM(0x35,LANG_MENU_READ_OPEN_NEW,           MENUITEM_PROC,    gui_draw_read, 0 ),
322    MENU_ITEM(0x35,LANG_MENU_READ_OPEN_LAST,          MENUITEM_PROC,    gui_draw_read_last, 0 ),
323    MENU_ITEM(0x35,LANG_MENU_READ_SELECT_FONT,        MENUITEM_PROC,    gui_draw_load_rbf, 0 ),
324    MENU_ENUM2(0x5f,LANG_MENU_READ_CODEPAGE,          &conf.reader_codepage, gui_reader_codepage_cps ),
325    MENU_ITEM(0x5c,LANG_MENU_READ_WORD_WRAP,          MENUITEM_BOOL,    &conf.reader_wrap_by_words, 0 ),
326    MENU_ITEM(0x5c,LANG_MENU_READ_AUTOSCROLL,         MENUITEM_BOOL,    &conf.reader_autoscroll, 0 ),
327    MENU_ITEM(0x5f,LANG_MENU_READ_AUTOSCROLL_DELAY,   MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.reader_autoscroll_delay, MENU_MINMAX(0, 60) ),
328    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
329    {0}
330};
331static CMenu reader_submenu = {0x37,LANG_MENU_READ_TITLE, NULL, reader_submenu_items };
332#endif
333
334#ifdef OPT_DEBUGGING
335static const char* gui_debug_shortcut_modes[] = { "None", "DmpRAM", "Page", "CmpProps"};
336static const char* gui_debug_display_modes[] = { "None", "Props", "Params", "Tasks"};
337static CMenuItem debug_submenu_items[] = {
338    MENU_ENUM2(0x5c,LANG_MENU_DEBUG_DISPLAY,          &conf.debug_display, gui_debug_display_modes ),
339    MENU_ITEM(0x2a,LANG_MENU_DEBUG_PROPCASE_PAGE,     MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,   &conf.debug_propcase_page, MENU_MINMAX(0, 128) ),
340    MENU_ITEM(0x2a,LANG_MENU_DEBUG_TASKLIST_START,    MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,   &debug_tasklist_start, MENU_MINMAX(0, 63) ),
341    MENU_ITEM(0x5c,LANG_MENU_DEBUG_SHOW_MISC_VALS,    MENUITEM_BOOL,          &conf.debug_misc_vals_show, 0 ),
342    MENU_ENUM2(0x5c,LANG_MENU_DEBUG_SHORTCUT_ACTION,  &conf.debug_shortcut_action, gui_debug_shortcut_modes ),
343    MENU_ITEM(0x5c,LANG_MENU_RAW_TIMER,               MENUITEM_BOOL,          &conf.raw_timer, 0 ),
344#ifdef OPT_LUA
345    MENU_ITEM(0x5c,LANG_MENU_LUA_RESTART,             MENUITEM_BOOL,          &conf.debug_lua_restart_on_error, 0 ),
346#endif
347#if CAM_MULTIPART
348    MENU_ITEM(0x33,LANG_MENU_DEBUG_CREATE_MULTIPART , MENUITEM_PROC,          gui_menuproc_break_card, 0 ),
349#endif
350    MENU_ITEM(0x2a,LANG_SAVE_ROMLOG,                  MENUITEM_PROC,          save_romlog, 0 ),
351    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
352    {0}
353};
354static CMenu debug_submenu = {0x2a,LANG_MENU_DEBUG_TITLE, NULL, debug_submenu_items };
355#endif
356
357
358static CMenuItem misc_submenu_items[] = {
359    MENU_ITEM(0x35,LANG_MENU_MISC_FILE_BROWSER,       MENUITEM_PROC,    gui_draw_fselect, 0 ),
360    MENU_ITEM(0x65,(int)"Modules",                        MENUITEM_TEXT,    0, 0 ),
361#ifdef OPT_TEXTREADER
362    MENU_ITEM(0x37,LANG_MENU_MISC_TEXT_READER,        MENUITEM_SUBMENU, &reader_submenu, 0 ),
363#endif
364#if CAM_SWIVEL_SCREEN
365    MENU_ITEM(0x28,LANG_MENU_MISC_FLASHLIGHT,         MENUITEM_BOOL,    &conf.flashlight, 0 ),
366#endif
367    MENU_ITEM(0x5c,LANG_MENU_MISC_SHOW_SPLASH,        MENUITEM_BOOL,    &conf.splash_show, 0 ),
368    MENU_ITEM(0x5c,LANG_MENU_MISC_START_SOUND,        MENUITEM_BOOL,    &conf.start_sound, 0 ),
369#if CAM_USE_ZOOM_FOR_MF
370    MENU_ITEM(0x59,LANG_MENU_MISC_ZOOM_FOR_MF,        MENUITEM_BOOL,    &conf.use_zoom_mf, 0 ),
371#endif
372#if CAM_ADJUSTABLE_ALT_BUTTON
373    MENU_ITEM(0x22,LANG_MENU_MISC_ALT_BUTTON,         MENUITEM_ENUM,    gui_alt_mode_button_enum, 0 ),
374#endif
375    MENU_ITEM(0x5d,LANG_MENU_MISC_DISABLE_LCD_OFF,    MENUITEM_ENUM,    gui_alt_power_enum, 0 ),
376    MENU_ITEM(0x80,LANG_MENU_MISC_BUILD_INFO,         MENUITEM_PROC,    gui_show_build_info, 0 ),
377    MENU_ITEM(0x80,LANG_MENU_MISC_MEMORY_INFO,        MENUITEM_PROC,    gui_show_memory_info, 0 ),
378    MENU_ITEM(0x33,LANG_MENU_DEBUG_MAKE_BOOTABLE,     MENUITEM_PROC,    gui_menuproc_mkbootdisk, 0 ),
379#if CAM_MULTIPART
380    MENU_ITEM(0x33,LANG_MENU_DEBUG_SWAP_PART,         MENUITEM_PROC,            gui_menuproc_swap_partitions, 0 ),
381#endif
382    MENU_ITEM(0x2b,LANG_MENU_MAIN_RESET_OPTIONS,      MENUITEM_PROC,      gui_menuproc_reset, 0 ),
383#ifdef OPT_DEBUGGING
384    MENU_ITEM(0x2a,LANG_MENU_MAIN_DEBUG,              MENUITEM_SUBMENU,   &debug_submenu, 0 ),
385#endif
386    MENU_ITEM(0x86,LANG_MENU_REMOTE_PARAM,            MENUITEM_SUBMENU,   &remote_submenu, 0 ),
387#if defined (DNG_EXT_FROM)
388    MENU_ITEM(0x71,LANG_MENU_DNG_VIA_USB,             MENUITEM_BOOL | MENUITEM_ARG_CALLBACK, &conf.dng_usb_ext , (int)cb_change_dng_usb_ext ),
389#endif
390    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
391    {0},
392};
393static CMenu misc_submenu = {0x29,LANG_MENU_MISC_TITLE, NULL, misc_submenu_items };
394
395static int voltage_step;
396static CMenuItem battery_submenu_items[] = {
397    MENU_ITEM(0x66,LANG_MENU_BATT_VOLT_MAX,           MENUITEM_INT|MENUITEM_ARG_ADDR_INC,     &conf.batt_volts_max,   (int)&voltage_step ),
398    MENU_ITEM(0x67,LANG_MENU_BATT_VOLT_MIN,           MENUITEM_INT|MENUITEM_ARG_ADDR_INC,     &conf.batt_volts_min,   (int)&voltage_step ),
399    MENU_ITEM(0x68,LANG_MENU_BATT_STEP_25,            MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,    &conf.batt_step_25,     (int)cb_step_25 ),
400    MENU_ITEM(0x0,(int)"",                            MENUITEM_SEPARATOR, 0, 0 ),
401    MENU_ITEM(0x73,LANG_MENU_BATT_SHOW_PERCENT,       MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,    &conf.batt_perc_show,   (int)cb_perc ),
402    MENU_ITEM(0x73,LANG_MENU_BATT_SHOW_VOLTS,         MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,    &conf.batt_volts_show,  (int)cb_volts ),
403    MENU_ITEM(0x32,LANG_MENU_BATT_SHOW_ICON,          MENUITEM_BOOL,                          &conf.batt_icon_show, 0 ),
404    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
405    {0}
406};
407static CMenu battery_submenu = {0x32,LANG_MENU_BATT_TITLE, cb_battery_menu_change, battery_submenu_items };
408
409static const char* gui_space_bar_modes[] = { "Don't", "Horizontal", "Vertical"};
410static const char* gui_space_bar_size_modes[] = { "1/4", "1/2", "1"};
411static const char* gui_space_bar_width_modes[] = { "1", "2", "3","4","5","6","7","8","9","10"};
412static const char* gui_space_warn_type_modes[] = { "Percent", "MB", "Don't"};
413static CMenuItem space_submenu_items[] = {
414    MENU_ITEM(0x5c,LANG_MENU_SPACE_SHOW_ICON,         MENUITEM_BOOL,                          &conf.space_icon_show, 0 ),
415    MENU_ENUM2(0x69,LANG_MENU_SPACE_SHOW_BAR,     &conf.space_bar_show, gui_space_bar_modes ),
416    MENU_ENUM2(0x6a,LANG_MENU_SPACE_BAR_SIZE,     &conf.space_bar_size, gui_space_bar_size_modes ),
417    MENU_ENUM2(0x6b,LANG_MENU_SPACE_BAR_WIDTH,    &conf.space_bar_width, gui_space_bar_width_modes ),
418    MENU_ITEM(0x5c,LANG_MENU_SPACE_SHOW_PERCENT,      MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,    &conf.space_perc_show,   (int)cb_space_perc ),
419    MENU_ITEM(0x5c,LANG_MENU_SPACE_SHOW_MB,           MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,    &conf.space_mb_show,  (int)cb_space_mb ),
420    MENU_ENUM2(0x5f,LANG_MENU_SPACE_WARN_TYPE,    &conf.space_warn_type, gui_space_warn_type_modes ),
421    MENU_ITEM(0x58,LANG_MENU_SPACE_WARN_PERCENT,     MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,   &conf.space_perc_warn, MENU_MINMAX(1, 99) ),
422    MENU_ITEM(0x58,LANG_MENU_SPACE_WARN_MB,     MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,   &conf.space_mb_warn, MENU_MINMAX(1, 4000) ),
423    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
424    {0}
425};
426static CMenu space_submenu = {0x33,LANG_MENU_OSD_SPACE_PARAMS_TITLE, NULL, space_submenu_items};
427
428static const char* gui_dof_show_value_modes[] = { "Don't", "Separate", "In Misc" };
429static CMenuItem dof_submenu_items[] = {
430          MENU_ENUM2(0x5f,LANG_MENU_OSD_SHOW_DOF_CALC,           &conf.show_dof, gui_dof_show_value_modes ),
431          MENU_ITEM(0x5c,LANG_MENU_DOF_SUBJ_DIST_AS_NEAR_LIMIT,  MENUITEM_BOOL,      &conf.dof_subj_dist_as_near_limit, 0),
432          MENU_ITEM(0x5c,LANG_MENU_DOF_USE_EXIF_SUBJ_DIST,       MENUITEM_BOOL,      &conf.dof_use_exif_subj_dist, 0),
433          MENU_ITEM(0x5c,LANG_MENU_DOF_SUBJ_DIST_IN_MISC,        MENUITEM_BOOL,      &conf.dof_subj_dist_in_misc, 0),
434          MENU_ITEM(0x5c,LANG_MENU_DOF_NEAR_LIMIT_IN_MISC,       MENUITEM_BOOL,      &conf.dof_near_limit_in_misc, 0),
435      MENU_ITEM(0x5c,LANG_MENU_DOF_FAR_LIMIT_IN_MISC,        MENUITEM_BOOL,                      &conf.dof_far_limit_in_misc, 0),
436      MENU_ITEM(0x5c,LANG_MENU_DOF_HYPERFOCAL_IN_MISC,       MENUITEM_BOOL,      &conf.dof_hyperfocal_in_misc, 0),
437      MENU_ITEM(0x5c,LANG_MENU_DOF_DEPTH_LIMIT_IN_MISC,      MENUITEM_BOOL,      &conf.dof_depth_in_misc, 0),
438#if !CAM_DRYOS
439      MENU_ITEM(0x5c,LANG_MENU_DOF_DIST_FROM_LENS,           MENUITEM_BOOL,      &conf.dof_dist_from_lens, 0),
440#endif
441          MENU_ITEM(0x51,LANG_MENU_BACK,                           MENUITEM_UP, 0, 0 ),
442    {0}
443};
444static CMenu dof_submenu = {0x31,LANG_MENU_DOF_TITLE, /*cb_dof_menu_change*/ NULL, dof_submenu_items };
445
446static const char* gui_zoom_value_modes[] = { "X", "FL", "EFL" };
447static const char* gui_show_values_modes[] = { "Don't", "Always", "Shoot" };
448static CMenuItem values_submenu_items[] = {
449          MENU_ENUM2(0x5f,LANG_MENU_OSD_SHOW_MISC_VALUES,          &conf.show_values, gui_show_values_modes ),
450         // MENU_ITEM(0x43,LANG_MENU_VALUES_SHOW_IN_REVIEW,   MENUITEM_BOOL,      &conf.values_show_in_review, 0 ),
451          MENU_ITEM(0x5c,LANG_MENU_SHOW_VALUES_IN_VIDEO,           MENUITEM_BOOL,      &conf.show_values_in_video, 0 ),
452          MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_ZOOM,               MENUITEM_BOOL,      &conf.values_show_zoom, 0 ),
453          MENU_ENUM2(0x5f,LANG_MENU_OSD_ZOOM_VALUE,                &conf.zoom_value, gui_zoom_value_modes ),
454          MENU_ITEM(0x60,LANG_MENU_OSD_ZOOM_SCALE,                 MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.zoom_scale,   MENU_MINMAX(0, 1000) ),
455      MENU_ITEM(0x62,LANG_MENU_VALUES_SHOW_REAL_APERTURE,      MENUITEM_BOOL,      &conf.values_show_real_aperture, 0 ),
456      MENU_ITEM(0x74,LANG_MENU_VALUES_SHOW_REAL_ISO,           MENUITEM_BOOL,      &conf.values_show_real_iso, 0 ),
457      MENU_ITEM(0x74,LANG_MENU_VALUES_SHOW_MARKET_ISO,         MENUITEM_BOOL,      &conf.values_show_market_iso, 0 ),
458          MENU_ITEM(0x2d,LANG_MENU_SHOW_ISO_ONLY_IN_AUTOISO_MODE,  MENUITEM_BOOL,            &conf.values_show_iso_only_in_autoiso_mode, 0 ),
459      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_EV_SETED,                     MENUITEM_BOOL,      &conf.values_show_ev_seted, 0 ),
460      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_EV_MEASURED,        MENUITEM_BOOL,            &conf.values_show_ev_measured, 0 ),
461      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_BV_SETED,                     MENUITEM_BOOL,      &conf.values_show_bv_seted, 0 ),
462      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_BV_MEASURED,          MENUITEM_BOOL,      &conf.values_show_bv_measured, 0 ),
463      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_OVEREXPOSURE,             MENUITEM_BOOL,      &conf.values_show_overexposure, 0 ),
464      MENU_ITEM(0x5c,LANG_MENU_SHOW_CANON_OVEREXPOSURE,      MENUITEM_BOOL,      &conf.values_show_canon_overexposure, 0 ),
465      MENU_ITEM(0x5c,LANG_MENU_VALUES_SHOW_LUMINANCE,        MENUITEM_BOOL,      &conf.values_show_luminance, 0 ),
466          MENU_ITEM(0x51,LANG_MENU_BACK,                           MENUITEM_UP, 0, 0 ),
467    {0}
468};
469static CMenu values_submenu = {0x28,LANG_MENU_OSD_VALUES_TITLE, /*cb_values_menu_change*/ NULL, values_submenu_items };
470
471static const char* gui_show_clock_modes[]={ "Don't", "Normal", "Seconds"};
472static const char* gui_clock_format_modes[] = { "24h", "12h"};
473static const char* gui_clock_indicator_modes[] = { "PM", "P", "."};
474static const char* gui_clock_halfpress_modes[] = { "Full", "Seconds", "Don't"};
475static CMenuItem clock_submenu_items[] = {
476    MENU_ENUM2(0x5f,LANG_MENU_OSD_SHOW_CLOCK,           &conf.show_clock, gui_show_clock_modes ),
477    MENU_ENUM2(0x6d,LANG_MENU_OSD_CLOCK_FORMAT,         &conf.clock_format, gui_clock_format_modes ),
478    MENU_ENUM2(0x6c,LANG_MENU_OSD_CLOCK_INDICATOR,      &conf.clock_indicator, gui_clock_indicator_modes ),
479    MENU_ENUM2(0x6e,LANG_MENU_OSD_CLOCK_HALFPRESS,      &conf.clock_halfpress, gui_clock_halfpress_modes ),
480    MENU_ITEM(0x51,LANG_MENU_BACK, MENUITEM_UP, 0, 0 ),
481    {0}
482};
483static CMenu clock_submenu = {0x34,LANG_MENU_OSD_CLOCK_PARAMS_TITLE, NULL, clock_submenu_items };
484
485
486static const char* gui_show_movie_time_modes[] = { "Don't", "hh:mm:ss", "KB/s","both"};
487#if !CAM_VIDEO_QUALITY_ONLY
488    static const char* gui_video_mode_modes[] = { "Bitrate", "Quality"};
489#else
490    static const char* gui_video_mode_modes[] = { "Default", "Quality"};
491#endif
492static CMenuItem video_submenu_items[] = {
493#if CAM_CHDK_HAS_EXT_VIDEO_MENU
494        MENU_ENUM2(0x23,LANG_MENU_VIDEO_MODE,             &conf.video_mode, gui_video_mode_modes ),
495#if !CAM_VIDEO_QUALITY_ONLY
496      MENU_ITEM(0x5e,LANG_MENU_VIDEO_BITRATE,           MENUITEM_ENUM,    gui_video_bitrate_enum, 0 ),
497#endif
498    MENU_ITEM(0x60,LANG_MENU_VIDEO_QUALITY,           MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.video_quality, MENU_MINMAX(1, 99) ),
499    MENU_ITEM(0x5c,LANG_MENU_CLEAR_VIDEO_VALUES,    MENUITEM_BOOL,    &conf.clear_video, 0 ),
500#endif
501#if CAM_VIDEO_CONTROL
502    MENU_ITEM(0x5c,LANG_MENU_FAST_SWITCH_VIDEO,   MENUITEM_BOOL,  &conf.fast_movie_control, 0 ),
503#endif
504#if CAM_CHDK_HAS_EXT_VIDEO_MENU
505    MENU_ITEM(0x5c,LANG_MENU_FAST_SWITCH_QUALITY_VIDEO,   MENUITEM_BOOL,  &conf.fast_movie_quality_control, 0 ),
506#endif
507#if CAM_CAN_UNLOCK_OPTICAL_ZOOM_IN_VIDEO
508    MENU_ITEM(0x5c,LANG_MENU_OPTICAL_ZOOM_IN_VIDEO,   MENUITEM_BOOL,  &conf.unlock_optical_zoom_for_video, 0 ),
509#endif
510#if CAM_CAN_MUTE_MICROPHONE
511    MENU_ITEM(0x83,LANG_MENU_MUTE_ON_ZOOM,   MENUITEM_BOOL,  &conf.mute_on_zoom, 0 ),
512#endif
513#if CAM_AF_SCAN_DURING_VIDEO_RECORD
514    MENU_ITEM(0x82,LANG_MENU_VIDEO_AF_KEY,   MENUITEM_ENUM,    gui_video_af_key_enum, 0 ),
515#endif
516    MENU_ENUM2(0x5c,LANG_MENU_OSD_SHOW_VIDEO_TIME,         &conf.show_movie_time, gui_show_movie_time_modes ),
517    MENU_ITEM(0x60,LANG_MENU_OSD_SHOW_VIDEO_REFRESH,             MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.show_movie_refresh,   MENU_MINMAX(1, 20) ),
518    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
519    {0}
520};
521static CMenu video_submenu = {0x23,LANG_MENU_VIDEO_PARAM_TITLE, NULL, video_submenu_items };
522
523static const char* gui_bracket_values_modes[] = { "Off", "1/3 Ev","2/3 Ev", "1 Ev", "1 1/3Ev", "1 2/3Ev", "2 Ev", "2 1/3Ev", "2 2/3Ev", "3 Ev", "3 1/3Ev", "3 2/3Ev", "4 Ev"};
524static const char* gui_override_koef_modes[] = { "Off", "1", "10", "100", "1000" };
525static const char* gui_bracket_type_modes[] = { "+/-", "-","+"};
526static CMenuItem bracketing_in_continuous_submenu_items[] = {
527          MENU_ENUM2(0x63,LANG_MENU_TV_BRACKET_VALUE,            &conf.tv_bracket_value, gui_bracket_values_modes ),
528#if CAM_HAS_IRIS_DIAPHRAGM
529          MENU_ENUM2(0x62,LANG_MENU_AV_BRACKET_VALUE,            &conf.av_bracket_value, gui_bracket_values_modes ),
530#endif
531#if CAM_CAN_SD_OVERRIDE
532          MENU_ITEM(0x5e,LANG_MENU_SUBJ_DIST_BRACKET_VALUE,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.subj_dist_bracket_value, MENU_MINMAX(0, 100) ),
533          MENU_ENUM2(0x5f,LANG_MENU_SUBJ_DIST_BRACKET_KOEF,      &conf.subj_dist_bracket_koef, gui_override_koef_modes ),
534#endif
535          MENU_ITEM(0x74,LANG_MENU_ISO_BRACKET_VALUE,            MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.iso_bracket_value, MENU_MINMAX(0, 100) ),
536          MENU_ENUM2a(0x5f,LANG_MENU_ISO_BRACKET_KOEF,           &conf.iso_bracket_koef, gui_override_koef_modes, 4 ),
537          MENU_ENUM2(0x60,LANG_MENU_BRACKET_TYPE,                &conf.bracket_type, gui_bracket_type_modes ),
538          MENU_ITEM(0x5b,LANG_MENU_CLEAR_BRACKET_VALUES,        MENUITEM_BOOL,        &conf.clear_bracket, 0 ),
539     MENU_ITEM(0x5c,LANG_MENU_BRACKETING_ADD_RAW_SUFFIX,                MENUITEM_BOOL,      &conf.bracketing_add_raw_suffix, 0 ),
540      MENU_ITEM(0x51,LANG_MENU_BACK,                         MENUITEM_UP, 0, 0 ),
541      {0}
542};
543static CMenu bracketing_in_continuous_submenu = {0x2c,LANG_MENU_BRACKET_IN_CONTINUOUS_TITLE, NULL, bracketing_in_continuous_submenu_items };
544
545
546/*
547static CMenuItem exposure_submenu_items[] = {
548          MENU_ITEM(0x59,LANG_MENU_RECALC_EXPOSURE,         MENUITEM_BOOL,    &conf.recalc_exposure, 0),
549          MENU_ITEM(0x63,LANG_MENU_TV_EXPOSURE_ORDER,       MENUITEM_ENUM,    gui_tv_exposure_order_enum, 0),
550          MENU_ITEM(0x62,LANG_MENU_AV_EXPOSURE_ORDER,       MENUITEM_ENUM,    gui_av_exposure_order_enum, 0),
551          MENU_ITEM(0x74,LANG_MENU_ISO_EXPOSURE_ORDER,     MENUITEM_ENUM,    gui_iso_exposure_order_enum, 0),
552          MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
553      {0}
554};
555static CMenu exposure_submenu = {0x2a,LANG_MENU_EXPOSURE_TITLE, NULL, exposure_submenu_items };
556*/
557
558// "Extra Photo Operations" Menu
559static const char* gui_override_disable_modes[] = { "Off", "On", "Disabled"};
560static const char* gui_nd_filter_state_modes[] = { "Off", "In", "Out" };
561static const char* gui_fast_ev_step_modes[] = {"1/6 Ev","1/3 Ev","1/2 Ev", "2/3 Ev","5/6 Ev","1 Ev","1 1/6 Ev","1 1/3 Ev","1 1/2 Ev", "1 2/3 Ev","1 5/6 Ev","2 Ev","2 1/6 Ev","2 1/3 Ev","2 1/2 Ev", "2 2/3 Ev","2 5/6 Ev","3 Ev","3 1/6 Ev","3 1/3 Ev","3 1/2 Ev", "3 2/3 Ev","3 5/6 Ev","4 Ev"};
562static const char* gui_fast_image_quality_modes[] = { "sup.fine", "fine", "normal", "off" };
563static CMenuItem operation_submenu_items[] = {
564      MENU_ENUM2(0x5f,LANG_MENU_OVERRIDE_DISABLE,    &conf.override_disable, gui_override_disable_modes ),
565      MENU_ITEM(0x5c,LANG_MENU_OVERRIDE_DISABLE_ALL,     MENUITEM_BOOL,    &conf.override_disable_all, 0 ),
566          MENU_ITEM(0x61,LANG_MENU_OVERRIDE_TV_VALUE,        MENUITEM_ENUM,    gui_tv_override_value_enum, 0 ),
567          MENU_ITEM(0x5f,LANG_MENU_OVERRIDE_TV_KOEF,         MENUITEM_ENUM,    gui_tv_override_koef_enum, 0 ),
568          MENU_ITEM(0x59,LANG_MENU_TV_ENUM_TYPE,             MENUITEM_ENUM,    gui_tv_enum_type_enum, 0 ),
569#if CAM_HAS_IRIS_DIAPHRAGM
570          MENU_ITEM(0x62,LANG_MENU_OVERRIDE_AV_VALUE,        MENUITEM_ENUM,    gui_av_override_enum, 0 ),
571#endif
572#if CAM_HAS_ND_FILTER
573      MENU_ENUM2(0x5f,LANG_MENU_OVERRIDE_ND_FILTER,      &conf.nd_filter_state, gui_nd_filter_state_modes ),
574#endif
575#if CAM_CAN_SD_OVERRIDE
576      MENU_ITEM(0x5e,LANG_MENU_OVERRIDE_SUBJ_DIST_VALUE, MENUITEM_ENUM,    gui_subj_dist_override_value_enum, 0 ),
577          MENU_ITEM(0x5f,LANG_MENU_OVERRIDE_SUBJ_DIST_KOEF,  MENUITEM_ENUM,    gui_subj_dist_override_koef_enum, 0 ),
578#endif
579          MENU_ITEM(0x74,LANG_MENU_OVERRIDE_ISO_VALUE,     MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.iso_override_value, MENU_MINMAX(0, 800) ),
580          MENU_ENUM2a(0x5f,LANG_MENU_OVERRIDE_ISO_KOEF,       &conf.iso_override_koef, gui_override_koef_modes, 4 ),
581#if ZOOM_OVERRIDE
582    MENU_ITEM(0x5c,LANG_MENU_OVERRIDE_ZOOM,         MENUITEM_BOOL,    &conf.zoom_override, 0 ),
583    MENU_ITEM(0x5f,LANG_MENU_OVERRIDE_ZOOM_VALUE,         MENUITEM_ENUM,    gui_zoom_override_enum, 0 ),
584
585          MENU_ITEM(0x5c,LANG_MENU_CLEAR_ZOOM_OVERRIDE_VALUES,    MENUITEM_BOOL,    &conf.clear_zoom_override, 0 ),
586#endif
587          MENU_ITEM(0x2c,LANG_MENU_BRACKET_IN_CONTINUOUS,          MENUITEM_SUBMENU, &bracketing_in_continuous_submenu, 0 ),
588          MENU_ITEM(0x2d,LANG_MENU_AUTOISO,                  MENUITEM_SUBMENU, &autoiso_submenu, 0 ),
589      //{LANG_MENU_EXPOSURE,               MENUITEM_SUBMENU, &exposure_submenu, 0 ),
590          MENU_ITEM(0x5b,LANG_MENU_CLEAR_OVERRIDE_VALUES,    MENUITEM_BOOL,    &conf.clear_override, 0 ),
591
592      MENU_ITEM(0x5c,LANG_MENU_MISC_FAST_EV,         MENUITEM_BOOL,    &conf.fast_ev, 0 ),
593      MENU_ENUM2(0x5f,LANG_MENU_MISC_FAST_EV_STEP,   &conf.fast_ev_step, gui_fast_ev_step_modes ),
594#if CAM_REAR_CURTAIN
595      MENU_ITEM(0x5c, LANG_MENU_REAR_CURTAIN, MENUITEM_BOOL, &conf.flash_sync_curtain, 0 ),
596#endif
597          MENU_ITEM(0x5c, LANG_MENU_FLASH_MANUAL_OVERRIDE, MENUITEM_BOOL,   &conf.flash_manual_override, 0 ),
598    MENU_ITEM(0x5f, LANG_MENU_FLASH_VIDEO_OVERRIDE_POWER,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.flash_video_override_power, MENU_MINMAX(0, 2) ),
599#if CAM_HAS_VIDEO_BUTTON
600    MENU_ITEM(0x5c, LANG_MENU_FLASH_VIDEO_OVERRIDE, MENUITEM_BOOL,   &conf.flash_video_override, 0 ),
601#endif
602#if CAM_QUALITY_OVERRIDE
603    MENU_ENUM2(0x5c,LANG_MENU_MISC_IMAGE_QUALITY,   &conf.fast_image_quality, gui_fast_image_quality_modes ),
604#endif
605    MENU_ITEM(0x51,LANG_MENU_BACK,                     MENUITEM_UP, 0, 0 ),
606    {0}
607};
608static CMenu operation_submenu = {0x21,LANG_MENU_OPERATION_PARAM_TITLE, NULL, operation_submenu_items };
609
610#ifdef OPT_EDGEOVERLAY
611static const char* gui_edge_pano_modes[] = { "Off", "Right", "Down", "Left", "Up", "Free"};
612static CMenuItem edge_overlay_submenu_items[] = {
613    MENU_ITEM(0x5c,LANG_MENU_EDGE_OVERLAY_ENABLE,     MENUITEM_BOOL,          &conf.edge_overlay_enable, 0 ),
614    MENU_ITEM(0x5c,LANG_MENU_EDGE_FILTER,     MENUITEM_BOOL,          &conf.edge_overlay_filter, 0 ),
615    MENU_ENUM2(0x5f,LANG_MENU_EDGE_PANO,    &conf.edge_overlay_pano, gui_edge_pano_modes ),
616    MENU_ITEM(0x5e,LANG_MENU_EDGE_PANO_OVERLAP,   MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.edge_overlay_pano_overlap, MENU_MINMAX(0, 100) ),
617    MENU_ITEM(0x5c,LANG_MENU_EDGE_SHOW,     MENUITEM_BOOL,          &conf.edge_overlay_show, 0 ),
618    MENU_ITEM(0x5e,LANG_MENU_EDGE_OVERLAY_TRESH,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX, &conf.edge_overlay_thresh, MENU_MINMAX(0, 255) ),
619    MENU_ITEM(0x65,LANG_MENU_EDGE_OVERLAY_COLOR,      MENUITEM_COLOR_FG,      &conf.edge_overlay_color, 0 ),
620    MENU_ITEM(0x5c,LANG_MENU_EDGE_PLAY,                 MENUITEM_BOOL,          &conf.edge_overlay_play, 0 ), //does not work on cams like s-series, which dont have a real "hardware" play/rec switch, need a workaround, probably another button
621    MENU_ITEM(0x33,LANG_MENU_EDGE_SAVE,                 MENUITEM_PROC,          gui_menuproc_edge_save, 0 ),
622    MENU_ITEM(0x5c,LANG_MENU_EDGE_ZOOM,     MENUITEM_BOOL,          &conf.edge_overlay_zoom, 0 ),
623    MENU_ITEM(0x33,LANG_MENU_EDGE_LOAD,                 MENUITEM_PROC,          gui_menuproc_edge_load, 0 ),
624    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
625    {0}
626};
627static CMenu edge_overlay_submenu = {0x7f,LANG_MENU_EDGE_OVERLAY_TITLE, NULL, edge_overlay_submenu_items };
628#endif
629
630static CMenuItem grid_submenu_items[] = {
631    MENU_ITEM(0x2f,LANG_MENU_SHOW_GRID,               MENUITEM_BOOL,            &conf.show_grid_lines, 0 ),
632    MENU_ITEM(0x35,LANG_MENU_GRID_LOAD,               MENUITEM_PROC,            gui_grid_lines_load, 0 ),
633    MENU_ITEM(0x0,LANG_MENU_GRID_CURRENT,            MENUITEM_SEPARATOR, 0, 0 ),
634    MENU_ITEM(0x0,(int)grid_title,                   MENUITEM_TEXT, 0, 0 ),
635    MENU_ITEM(0x0,(int)"",                           MENUITEM_SEPARATOR, 0, 0 ),
636    MENU_ITEM(0x5c,LANG_MENU_GRID_FORCE_COLOR,        MENUITEM_BOOL,          &conf.grid_force_color, 0 ),
637    MENU_ITEM(0x65,LANG_MENU_GRID_COLOR_LINE,         MENUITEM_COLOR_FG,      &conf.grid_color, 0 ),
638    MENU_ITEM(0x65,LANG_MENU_GRID_COLOR_FILL,         MENUITEM_COLOR_BG,      &conf.grid_color, 0 ),
639    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
640    {0}
641};
642static CMenu grid_submenu = {0x2f,LANG_MENU_GRID_TITLE, NULL, grid_submenu_items };
643
644static CMenuItem visual_submenu_items[] = {
645    MENU_ITEM(0x35,LANG_MENU_VIS_LANG,                MENUITEM_PROC,      gui_draw_load_lang, 0 ),
646    MENU_ITEM(0x5f,LANG_MENU_VIS_OSD_FONT,            MENUITEM_ENUM,      gui_font_enum, 0 ),
647    MENU_ITEM(0x35,LANG_MENU_VIS_MENU_FONT,           MENUITEM_PROC,      gui_draw_load_menu_rbf, 0 ),
648    MENU_ITEM(0x35,LANG_MENU_VIS_MENU_SYMBOL_FONT,    MENUITEM_PROC,      gui_draw_load_symbol_rbf, 0 ),
649    MENU_ITEM(0x80,LANG_MENU_RESET_FILES                 ,         MENUITEM_PROC,          gui_menuproc_reset_files, 0 ),
650    MENU_ITEM(0x0,LANG_MENU_VIS_COLORS,              MENUITEM_SEPARATOR, 0, 0 ),
651    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_TEXT,            MENUITEM_COLOR_FG,  &conf.osd_color, 0 ),
652    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_BKG,             MENUITEM_COLOR_BG,  &conf.osd_color, 0 ),
653    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_WARNING,         MENUITEM_COLOR_FG,  &conf.osd_color_warn, 0 ),
654    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_WARNING_BKG,     MENUITEM_COLOR_BG,  &conf.osd_color_warn, 0 ),
655    MENU_ITEM(0x65,LANG_MENU_VIS_HISTO,               MENUITEM_COLOR_FG,  &conf.histo_color, 0 ),
656    MENU_ITEM(0x65,LANG_MENU_VIS_HISTO_BKG,           MENUITEM_COLOR_BG,  &conf.histo_color, 0 ),
657    MENU_ITEM(0x65,LANG_MENU_VIS_HISTO_BORDER,        MENUITEM_COLOR_FG,  &conf.histo_color2, 0 ),
658    MENU_ITEM(0x65,LANG_MENU_VIS_HISTO_MARKERS,       MENUITEM_COLOR_BG,  &conf.histo_color2, 0 ),
659    MENU_ITEM(0x65,LANG_MENU_VIS_ZEBRA_UNDER,         MENUITEM_COLOR_BG,  &conf.zebra_color, 0 ),
660    MENU_ITEM(0x65,LANG_MENU_VIS_ZEBRA_OVER,          MENUITEM_COLOR_FG,  &conf.zebra_color, 0 ),
661    MENU_ITEM(0x65,LANG_MENU_VIS_BATT_ICON,           MENUITEM_COLOR_FG,  &conf.batt_icon_color, 0 ),
662    MENU_ITEM(0x65,LANG_MENU_VIS_SPACE_ICON,          MENUITEM_COLOR_FG,  &conf.space_color, 0 ),
663    MENU_ITEM(0x65,LANG_MENU_VIS_SPACE_ICON_BKG,      MENUITEM_COLOR_BG,  &conf.space_color, 0 ),
664    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_TEXT,           MENUITEM_COLOR_FG,  &conf.menu_color, 0 ),
665    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_BKG,            MENUITEM_COLOR_BG,  &conf.menu_color, 0 ),
666    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_TITLE_TEXT,     MENUITEM_COLOR_FG,  &conf.menu_title_color, 0 ),
667    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_TITLE_BKG,      MENUITEM_COLOR_BG,  &conf.menu_title_color, 0 ),
668    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_CURSOR_TEXT,    MENUITEM_COLOR_FG,  &conf.menu_cursor_color, 0 ),
669    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_CURSOR_BKG,     MENUITEM_COLOR_BG,  &conf.menu_cursor_color, 0 ),
670    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_SYMBOL_TEXT,    MENUITEM_COLOR_FG,  &conf.menu_symbol_color, 0 ),
671    MENU_ITEM(0x65,LANG_MENU_VIS_MENU_SYMBOL_BKG,     MENUITEM_COLOR_BG,  &conf.menu_symbol_color, 0 ),
672    MENU_ITEM(0x65,LANG_MENU_VIS_READER_TEXT,         MENUITEM_COLOR_FG,  &conf.reader_color, 0 ),
673    MENU_ITEM(0x65,LANG_MENU_VIS_READER_BKG,          MENUITEM_COLOR_BG,  &conf.reader_color, 0 ),
674    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_OVERRIDE,         MENUITEM_COLOR_FG,  &conf.osd_color_override, 0 ),
675    MENU_ITEM(0x65,LANG_MENU_VIS_OSD_OVERRIDE_BKG,     MENUITEM_COLOR_BG,  &conf.osd_color_override, 0 ),
676    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
677    {0}
678};
679static CMenu visual_submenu = {0x28,LANG_MENU_VIS_TITLE, NULL, visual_submenu_items };
680
681/*
682 * 1 extra entry for the "Main menu" and 1 for null when the menu is full with user selections
683 * Compiler will zero init remaining portion of array so no there is no hidden relationship between
684 * this structure and the value of USER_MENU_ITEMS. The value of USER_MENU_ITEMS can be anything you
685 * wish and everything automagically works.
686*/
687
688static CMenuItem user_submenu_items[USER_MENU_ITEMS + 2] = {
689        MENU_ITEM(0x20,LANG_MENU_MAIN_TITLE,     MENUITEM_PROC,  rinit, 0 )
690};
691
692static CMenu user_submenu = {0x2e,LANG_MENU_USER_MENU, NULL, user_submenu_items };
693
694static CMenuItem raw_state_submenu_items[] = {
695    MENU_ITEM(0x5c,LANG_MENU_OSD_SHOW_RAW_STATE,      MENUITEM_BOOL,      &conf.show_raw_state, 0 ),
696    MENU_ITEM(0x5c,LANG_MENU_OSD_SHOW_REMAINING_RAW,  MENUITEM_BOOL,      &conf.show_remaining_raw, 0 ),
697    MENU_ITEM(0x60,LANG_MENU_OSD_RAW_TRESHOLD,        MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.remaining_raw_treshold,   MENU_MINMAX(0, 200) ),
698    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
699    {0}
700};
701
702static CMenu raw_state_submenu = {0x24,LANG_MENU_OSD_RAW_STATE_PARAMS_TITLE, NULL, raw_state_submenu_items };
703
704#ifdef  CAM_TOUCHSCREEN_UI
705static const char* gui_touchscreen_disable_modes[]={ "Enable", "Disable" };
706static CMenuItem touchscreen_submenu_items[] = {
707    MENU_ENUM2(0x5f,LANG_MENU_TS_VIDEO_AE_DISABLE,      &conf.touchscreen_disable_video_controls,    gui_touchscreen_disable_modes ),
708    MENU_ENUM2(0x5f,LANG_MENU_TS_ALT_SHORTCUTS_DISABLE, &conf.touchscreen_disable_shortcut_controls, gui_touchscreen_disable_modes ),
709    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
710    {0}
711};
712static CMenu touchscreen_submenu = {0x28,LANG_MENU_TOUCHSCREEN_VALUES, /*cb_values_menu_change*/ NULL, touchscreen_submenu_items };
713#endif
714
715static const char* gui_temp_mode_modes[] = { "Off", "Optical", "CCD", "Battery", "all" };
716static const char* gui_hide_osd_modes[] = { "Don't", "In Playback", "On Disp Press", "Both"};
717static const char* gui_show_usb_info_modes[] = { "Off", "Icon", "Text"};
718static CMenuItem osd_submenu_items[] = {
719    MENU_ITEM(0x5c,LANG_MENU_OSD_SHOW,                MENUITEM_BOOL,      &conf.show_osd, 0 ),
720    MENU_ENUM2(0x5c,LANG_MENU_OSD_HIDE_PLAYBACK,      &conf.hide_osd, gui_hide_osd_modes ),
721    MENU_ITEM(0x81,LANG_MENU_VIS_MENU_CENTER,         MENUITEM_BOOL,        &conf.menu_center, 0 ),
722    MENU_ITEM(0x81,LANG_MENU_SELECT_FIRST_ENTRY,         MENUITEM_BOOL,     &conf.menu_select_first_entry, 0 ),
723    MENU_ITEM(0x64,LANG_MENU_VIS_SYMBOL,             MENUITEM_BOOL,         &conf.menu_symbol_enable, 0 ),
724    MENU_ITEM(0x2e,LANG_MENU_USER_MENU,                         MENUITEM_SUBMENU,   &user_submenu, 0 ),
725    MENU_ITEM(0x5f,LANG_MENU_USER_MENU_ENABLE,          MENUITEM_ENUM,      gui_user_menu_show_enum, 0 ),
726    MENU_ITEM(0x5c,LANG_MENU_USER_MENU_AS_ROOT,       MENUITEM_BOOL,      &conf.user_menu_as_root, 0 ),
727    MENU_ITEM(0x5f,LANG_MENU_OSD_SHOW_STATES,         MENUITEM_BOOL,      &conf.show_state, 0 ),
728    MENU_ENUM2(0x5f,LANG_MENU_OSD_SHOW_TEMP,         &conf.show_temp, gui_temp_mode_modes ),
729    MENU_ITEM(0x59,LANG_MENU_OSD_TEMP_FAHRENHEIT,      MENUITEM_BOOL,      &conf.temperature_unit, 0 ),
730    MENU_ENUM2(0x71,LANG_MENU_USB_SHOW_INFO,         &conf.usb_info_enable, gui_show_usb_info_modes ),
731    MENU_ITEM(0x72,LANG_MENU_OSD_LAYOUT_EDITOR,       MENUITEM_PROC,      gui_draw_osd_le, 0 ),
732    MENU_ITEM(0x2f,LANG_MENU_OSD_GRID_PARAMS,         MENUITEM_SUBMENU,   &grid_submenu, 0 ),
733    MENU_ITEM(0x22,LANG_MENU_OSD_VALUES,                MENUITEM_SUBMENU,   &values_submenu, 0 ),
734    MENU_ITEM(0x31,LANG_MENU_OSD_DOF_CALC,            MENUITEM_SUBMENU,   &dof_submenu, 0 ),
735    MENU_ITEM(0x24,LANG_MENU_OSD_RAW_STATE_PARAMS,    MENUITEM_SUBMENU,   &raw_state_submenu, 0 ),
736    MENU_ITEM(0x32,LANG_MENU_OSD_BATT_PARAMS,         MENUITEM_SUBMENU,   &battery_submenu, 0 ),
737    MENU_ITEM(0x33,LANG_MENU_OSD_SPACE_PARAMS,        MENUITEM_SUBMENU,   &space_submenu, 0 ),
738    MENU_ITEM(0x34,LANG_MENU_OSD_CLOCK_PARAMS,          MENUITEM_SUBMENU,   &clock_submenu, 0 ),
739    MENU_ITEM(0x59,LANG_MENU_OSD_SHOW_IN_REVIEW,      MENUITEM_BOOL,      &conf.show_osd_in_review, 0 ),
740#ifndef OPTIONS_AUTOSAVE
741    MENU_ITEM(0x5c,LANG_MENU_MAIN_SAVE_OPTIONS,       MENUITEM_PROC,      gui_menuproc_save, 0 ),
742#endif
743#ifdef  CAM_TOUCHSCREEN_UI
744    MENU_ITEM(0x22,LANG_MENU_TOUCHSCREEN_VALUES,         MENUITEM_SUBMENU,   &touchscreen_submenu, 0 ),
745#endif
746    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
747    {0}
748};
749
750static CMenu osd_submenu = {0x22,LANG_MENU_OSD_TITLE, NULL, osd_submenu_items };
751
752static const char* gui_histo_show_modes[] = { "Don't", "Always", "Shoot" };
753static CMenuItem histo_submenu_items[] = {
754    MENU_ENUM2(0x5f,LANG_MENU_HISTO_SHOW,             &conf.show_histo, gui_histo_show_modes ),
755    MENU_ITEM(0x6f,LANG_MENU_HISTO_LAYOUT,            MENUITEM_ENUM,      gui_histo_layout_enum, 0 ),
756    MENU_ITEM(0x5f,LANG_MENU_HISTO_MODE,              MENUITEM_ENUM,      gui_histo_mode_enum, 0 ),
757    MENU_ITEM(0x5c,LANG_MENU_HISTO_EXP,               MENUITEM_BOOL,       &conf.show_overexp, 0 ),
758    MENU_ITEM(0x70,LANG_MENU_HISTO_IGNORE_PEAKS,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.histo_ignore_boundary,   MENU_MINMAX(0, 32) ),
759    MENU_ITEM(0x5c,LANG_MENU_HISTO_MAGNIFY,           MENUITEM_BOOL,       &conf.histo_auto_ajust, 0 ),
760    MENU_ITEM(0x5c,LANG_MENU_HISTO_SHOW_EV_GRID,      MENUITEM_BOOL,       &conf.histo_show_ev_grid, 0 ),
761    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
762    {0}
763};
764static CMenu histo_submenu = {0x25,LANG_MENU_HISTO_TITLE, NULL, histo_submenu_items };
765
766static CMenuItem raw_exceptions_submenu_items[] = {
767    #if defined CAM_HAS_VIDEO_BUTTON
768     MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_VIDEO,                MENUITEM_BOOL,      &conf.save_raw_in_video, 0 ),
769    #endif
770    #if defined(CAMERA_s3is)
771        MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_SPORTS,                MENUITEM_BOOL,      &conf.save_raw_in_sports, 0 ),
772    #endif
773    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_BURST,                MENUITEM_BOOL,      &conf.save_raw_in_burst, 0 ),
774    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_TIMER,                MENUITEM_BOOL,      &conf.save_raw_in_timer, 0 ),
775    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_EDGEOVERLAY,          MENUITEM_BOOL,      &conf.save_raw_in_edgeoverlay, 0 ),
776    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_AUTO,                 MENUITEM_BOOL,      &conf.save_raw_in_auto, 0 ),
777                #if CAM_BRACKETING
778        MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_EV_BRACKETING,                MENUITEM_BOOL,      &conf.save_raw_in_ev_bracketing, 0 ),
779                #endif
780    MENU_ITEM(0x5c,LANG_MENU_RAW_WARN,                MENUITEM_BOOL,      &conf.raw_exceptions_warn, 0 ),
781    MENU_ITEM(0x51,LANG_MENU_BACK,                           MENUITEM_UP, 0, 0 ),
782    {0}
783};
784static CMenu raw_exceptions_submenu = {0x59,LANG_MENU_OSD_RAW_EXCEPTIONS_PARAMS_TITLE, NULL, raw_exceptions_submenu_items };
785
786
787static const char* gui_raw_nr_modes[] = { "Auto", "Off", "On"};
788static CMenuItem raw_submenu_items[] = {
789    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE,                MENUITEM_BOOL,      &conf.save_raw, 0 ),
790    MENU_ITEM(0x59,LANG_MENU_OSD_RAW_EXCEPTIONS_PARAMS,         MENUITEM_SUBMENU,   &raw_exceptions_submenu, 0 ),
791    MENU_ENUM2(0x5f,LANG_MENU_RAW_NOISE_REDUCTION,    &conf.raw_nr, gui_raw_nr_modes ),
792    MENU_ITEM(0x5c,LANG_MENU_RAW_FIRST_ONLY,          MENUITEM_BOOL,      &conf.raw_save_first_only, 0 ),
793    MENU_ITEM(0x5c,LANG_MENU_RAW_SAVE_IN_DIR,         MENUITEM_BOOL,      &conf.raw_in_dir, 0 ),
794    MENU_ENUM2a(0x5f,LANG_MENU_RAW_PREFIX,            &conf.raw_prefix, img_prefixes, NUM_IMG_PREFIXES ),
795    MENU_ENUM2a(0x5f,LANG_MENU_RAW_EXTENSION,         &conf.raw_ext, img_exts, NUM_IMG_EXTS ),
796    MENU_ENUM2a(0x5f,LANG_MENU_SUB_PREFIX,            &conf.sub_batch_prefix, img_prefixes, NUM_IMG_PREFIXES ),
797    MENU_ENUM2a(0x5f,LANG_MENU_SUB_EXTENSION,         &conf.sub_batch_ext, img_exts, NUM_IMG_EXTS ),
798//  MENU_ITEM(0x60,LANG_MENU_SUB_IN_DARK_VALUE,       MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.sub_in_dark_value, MENU_MINMAX(0, 1023) ),
799//  MENU_ITEM(0x60,LANG_MENU_SUB_OUT_DARK_VALUE,      MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.sub_out_dark_value, MENU_MINMAX(0, 1023) ),
800    MENU_ITEM(0x2a,LANG_MENU_RAW_DEVELOP,             MENUITEM_PROC,      gui_raw_develop, 0 ),
801    MENU_ITEM(0x5c,LANG_MENU_BAD_PIXEL_REMOVAL,       MENUITEM_ENUM,      gui_bad_pixel_enum, 0 ),
802#if DNG_SUPPORT
803    MENU_ITEM(0x5c,LANG_MENU_DNG_FORMAT,              MENUITEM_BOOL | MENUITEM_ARG_CALLBACK, &conf.dng_raw , (int)cb_change_dng ),
804    MENU_ITEM(0x5c,LANG_MENU_RAW_DNG_EXT,             MENUITEM_BOOL,      &conf.raw_dng_ext, 0 ),
805    MENU_ITEM(0x2a,LANG_MENU_BADPIXEL_CREATE,         MENUITEM_PROC,      gui_menuproc_badpixel_create, 0 ),
806#endif
807    MENU_ITEM(0x5c,LANG_MENU_RAW_CACHED,              MENUITEM_BOOL,      &conf.raw_cache, 0 ),
808    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
809    {0}
810};
811static CMenu raw_submenu = {0x24,LANG_MENU_RAW_TITLE, NULL, raw_submenu_items };
812
813
814static const char* gui_zebra_mode_modes[] = { "Blink 1", "Blink 2", "Blink 3", "Solid", "Zebra 1", "Zebra 2" };
815static const char* gui_zebra_draw_osd_modes[] = { "Nothing", "Histo", "OSD" };
816static CMenuItem zebra_submenu_items[] = {
817    MENU_ITEM(0x5c,LANG_MENU_ZEBRA_DRAW,              MENUITEM_BOOL,                            &conf.zebra_draw, 0 ),
818    MENU_ENUM2(0x5f,LANG_MENU_ZEBRA_MODE,             &conf.zebra_mode, gui_zebra_mode_modes ),
819    MENU_ITEM(0x58,LANG_MENU_ZEBRA_UNDER,             MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.zebra_under,   MENU_MINMAX(0, 32) ),
820    MENU_ITEM(0x57,LANG_MENU_ZEBRA_OVER,              MENUITEM_INT|MENUITEM_F_UNSIGNED|MENUITEM_F_MINMAX,  &conf.zebra_over,    MENU_MINMAX(0, 32) ),
821    MENU_ITEM(0x28,LANG_MENU_ZEBRA_RESTORE_SCREEN,    MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,      &conf.zebra_restore_screen,     (int)cb_zebra_restore_screen ),
822    MENU_ITEM(0x5c,LANG_MENU_ZEBRA_RESTORE_OSD,       MENUITEM_BOOL|MENUITEM_ARG_CALLBACK,      &conf.zebra_restore_osd,        (int)cb_zebra_restore_osd ),
823    MENU_ENUM2(0x5f,LANG_MENU_ZEBRA_DRAW_OVER,        &conf.zebra_draw_osd, gui_zebra_draw_osd_modes ),
824    MENU_ITEM(0x5c,LANG_MENU_ZEBRA_MULTICHANNEL,      MENUITEM_BOOL,                            &conf.zebra_multichannel, 0 ),
825    MENU_ITEM(0x51,LANG_MENU_BACK,                    MENUITEM_UP, 0, 0 ),
826    {0}
827};
828static CMenu zebra_submenu = {0x26,LANG_MENU_ZEBRA_TITLE, NULL, zebra_submenu_items };
829
830#ifdef OPT_CURVES
831static CMenuItem curve_submenu_items[] = {
832    MENU_ITEM(0x5f,LANG_MENU_CURVE_ENABLE,        MENUITEM_ENUM,      gui_conf_curve_enum, 0 ),
833    MENU_ITEM(0x35,LANG_MENU_CURVE_LOAD,          MENUITEM_PROC,      gui_load_curve, 0 ),
834    MENU_ITEM(0x51,LANG_MENU_BACK,                MENUITEM_UP, 0, 0 ),
835    {0}
836};
837static CMenu curve_submenu = {0x85,LANG_MENU_CURVE_PARAM_TITLE, NULL, curve_submenu_items };
838#endif
839
840static CMenuItem root_menu_items[] = {
841    MENU_ITEM(0x21,LANG_MENU_OPERATION_PARAM,         MENUITEM_SUBMENU,   &operation_submenu, 0 ),
842    MENU_ITEM(0x23,LANG_MENU_VIDEO_PARAM,             MENUITEM_SUBMENU,   &video_submenu, 0 ),
843    MENU_ITEM(0x24,LANG_MENU_MAIN_RAW_PARAM,          MENUITEM_SUBMENU,   &raw_submenu, 0 ),
844#ifdef OPT_EDGEOVERLAY
845    MENU_ITEM(0x7f,LANG_MENU_EDGE_OVERLAY,         MENUITEM_SUBMENU,   &edge_overlay_submenu, 0 ),
846#endif
847#ifdef OPT_CURVES
848    MENU_ITEM(0x85,LANG_MENU_CURVE_PARAM,             MENUITEM_SUBMENU,   &curve_submenu, 0 ),
849#endif
850    MENU_ITEM(0x25,LANG_MENU_MAIN_HISTO_PARAM,        MENUITEM_SUBMENU,   &histo_submenu, 0 ),
851    MENU_ITEM(0x26,LANG_MENU_MAIN_ZEBRA_PARAM,        MENUITEM_SUBMENU,   &zebra_submenu, 0 ),
852    MENU_ITEM(0x22,LANG_MENU_MAIN_OSD_PARAM,          MENUITEM_SUBMENU,   &osd_submenu, 0 ),
853    MENU_ITEM(0x28,LANG_MENU_MAIN_VISUAL_PARAM,       MENUITEM_SUBMENU,   &visual_submenu, 0 ),
854#ifdef OPT_SCRIPTING
855    MENU_ITEM(0x27,LANG_MENU_MAIN_SCRIPT_PARAM,       MENUITEM_SUBMENU,   &script_submenu, 0 ),
856#endif
857    MENU_ITEM(0x29,LANG_MENU_MAIN_MISC,               MENUITEM_SUBMENU,   &misc_submenu, 0 ),
858#ifndef OPTIONS_AUTOSAVE
859    MENU_ITEM(0x33,LANG_MENU_MAIN_SAVE_OPTIONS,       MENUITEM_PROC,      gui_menuproc_save, 0 ),
860#endif
861    {0}
862};
863
864static CMenu root_menu = {0x20,LANG_MENU_MAIN_TITLE, NULL, root_menu_items };
865
866static int gui_user_menu_flag;
867
868void rinit(){
869        // Erase screen if switching from user menu to main menu
870        // in case the user menu is larger than the main menu
871        // otherwise it leaves remnants of the user menu above and below
872        // the main menu.
873    draw_restore();
874        gui_menu_init(&root_menu);
875}
876
877//-------------------------------------------------------------------
878void
879mod_user_menu(CMenuItem curr_menu_item, int* cur_memnu_item_indx, int mod) {
880int i;
881CMenuItem tmp_menu_item;
882        switch(mod) {
883
884                case 0:
885                        /*
886                         * Delete user menu entry by sliding all the lower valid/existing entries up.
887                         */
888
889                        if (*cur_memnu_item_indx == 0) /* don't allow deleting "user menu" */
890                                break;
891                        for(i = *cur_memnu_item_indx; user_submenu_items[i].text; i++) {
892                                user_submenu_items[i] = user_submenu_items[i+1];
893                        }
894
895                        /*
896                         * there were no valid entries below this one, so
897                         * the index pointer must be decremented.
898                         */
899                        if(!user_submenu_items[*cur_memnu_item_indx].text)
900                                *cur_memnu_item_indx -= 1;
901
902                        break;
903
904                case 1:
905                        /*
906                         * Insert new Item at end of existing entries
907                         */
908                        for(i = 1; i < USER_MENU_ITEMS + 1; i++) {
909                                if(!user_submenu_items[i].text) {
910                                        user_submenu_items[i] = curr_menu_item;
911                                        break;
912                                }
913                        }
914                        break;
915
916                case 2:
917                        /*
918                         * Move entry up
919                         */
920
921                        if((*cur_memnu_item_indx > 1)) {
922                                tmp_menu_item = user_submenu_items[*cur_memnu_item_indx -1];
923                                user_submenu_items[*cur_memnu_item_indx -1] = user_submenu_items[*cur_memnu_item_indx];
924                                user_submenu_items[*cur_memnu_item_indx] = tmp_menu_item;
925                                *cur_memnu_item_indx -=1;
926                        }
927                        break;
928
929                case 3:
930                        /*
931                         * Move entry down below next entry if next entry is not empty
932                         */
933                        if (*cur_memnu_item_indx == 0) /* don't allow moving "user menu" */
934                                break;
935                        if((*cur_memnu_item_indx < (USER_MENU_ITEMS)) && (user_submenu_items[*cur_memnu_item_indx +1].text)) {
936                                tmp_menu_item = user_submenu_items[*cur_memnu_item_indx +1];
937                                user_submenu_items[*cur_memnu_item_indx + 1] = user_submenu_items[*cur_memnu_item_indx];
938                                user_submenu_items[*cur_memnu_item_indx] = tmp_menu_item;
939                                *cur_memnu_item_indx +=1;
940                        }
941                        break;
942
943        }
944}
945
946//-------------------------------------------------------------------
947void cb_step_25() {
948    voltage_step = (conf.batt_step_25)?25:1;
949}
950
951void cb_perc() {
952    conf.batt_volts_show=0;
953}
954
955void cb_volts() {
956    conf.batt_perc_show=0;
957}
958
959void cb_space_perc() {
960    conf.space_mb_show=0;
961}
962
963void cb_space_mb() {
964    conf.space_perc_show=0;
965}
966
967void cb_battery_menu_change(unsigned int item) {
968    switch (item) {
969        case 0: //Voltage MAX
970            if (conf.batt_volts_max<conf.batt_volts_min+25) {
971                conf.batt_volts_min = conf.batt_volts_max-25;
972            }
973            break;
974        case 1: //Voltage MIN
975            if (conf.batt_volts_min>conf.batt_volts_max-25) {
976                conf.batt_volts_max = conf.batt_volts_min+25;
977            }
978            break;
979        default:
980            break;
981    }
982}
983
984void cb_zebra_restore_screen() {
985    if (!conf.zebra_restore_screen)
986        conf.zebra_restore_osd = 0;
987}
988
989void cb_zebra_restore_osd() {
990    if (conf.zebra_restore_osd)
991        conf.zebra_restore_screen = 1;
992}
993
994#if DNG_SUPPORT
995void cb_change_dng(){
996 int old=conf.dng_raw;
997 conf_change_dng();
998 if ((old==1) && (conf.dng_raw==0)) gui_mbox_init(LANG_ERROR, LANG_CANNOT_OPEN_BADPIXEL_FILE, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
999}
1000
1001void gui_menuproc_badpixel_create(int arg) {
1002        // After this action module will not be unloaded until reboot
1003        // because not clear when it finished
1004        if ( module_dng_load(LIBDNG_OWNED_BY_CREATEBADPIXEL) )
1005        libdng.create_badpixel_bin();
1006}
1007#endif
1008
1009#if defined (DNG_EXT_FROM)
1010void cb_change_dng_usb_ext(){
1011 if (conf.dng_usb_ext) change_ext_to_dng(); else change_ext_to_default();
1012}
1013#endif
1014
1015/*
1016common code for "enum" menu items that just take a list of string values and don't require any special setters
1017would be better to have another menu item type that does this by default
1018save memory by eliminating dupe code
1019*/
1020static void gui_enum_value_change(int *value, int change, unsigned num_items) {
1021    *value+=change;
1022    if (*value<0)
1023        *value = num_items-1;
1024    else if (*value>=num_items)
1025        *value = 0;
1026}
1027static const char* gui_change_simple_enum(int* value, int change, const char** items, unsigned num_items) {
1028        gui_enum_value_change(value, change, num_items);
1029    return items[*value];
1030}
1031const char* gui_change_enum2(const CMenuItem *menu_item, int change)
1032{
1033    const char** items = (const char**)menu_item->arg;
1034        gui_enum_value_change(menu_item->value, change, menu_item->opt_len);
1035    return items[*menu_item->value];
1036}
1037
1038//-------------------------------------------------------------------
1039#ifdef OPT_CURVES
1040const char* gui_conf_curve_enum(int change, int arg) {
1041    static const char* modes[]={ "None", "Custom", "+1EV", "+2EV", "Auto DR" };
1042
1043    gui_enum_value_change(&conf.curve_enable,change,sizeof(modes)/sizeof(modes[0]));
1044
1045        if(change && curve_init_mode)
1046                curve_init_mode();
1047    return modes[conf.curve_enable];
1048}
1049#endif
1050
1051#ifdef OPT_SCRIPTING
1052//-------------------------------------------------------------------
1053const char* gui_script_param_set_enum(int change, int arg) {
1054    static const char* modes[]={ "0", "1", "2", "3", "4", "5", "6", "7", "8", "9" };
1055
1056    if (change != 0) {
1057        if (conf.script_param_save) {
1058            save_params_values(0);
1059        }
1060                gui_enum_value_change(&conf.script_param_set,change,sizeof(modes)/sizeof(modes[0]));
1061
1062        if (!load_params_values(conf.script_file, 1, 0))
1063            script_load(conf.script_file, 0);
1064        gui_update_script_submenu();
1065    }
1066
1067    return modes[conf.script_param_set];
1068}
1069
1070//-------------------------------------------------------------------
1071void gui_update_script_submenu() {
1072    register int p=0, i;
1073
1074    for (i=0; i<sizeof(script_submenu_items_top)/sizeof(script_submenu_items_top[0]); ++p, ++i) {
1075        script_submenu_items[p]=script_submenu_items_top[i];
1076    }
1077    for (i=0; i<SCRIPT_NUM_PARAMS; ++i) {
1078        if (script_param_order[i]) {
1079            script_submenu_items[p].symbol=0x0;
1080            script_submenu_items[p].text=(int)script_params[script_param_order[i]-1];
1081            script_submenu_items[p].type=MENUITEM_INT;
1082            script_submenu_items[p].value=&conf.script_vars[script_param_order[i]-1];
1083            ++p;
1084        }
1085    }
1086    for (i=0; i<sizeof(script_submenu_items_bottom)/sizeof(script_submenu_items_bottom[0]); ++p, ++i) {
1087        script_submenu_items[p]=script_submenu_items_bottom[i];
1088    }
1089}
1090
1091//-------------------------------------------------------------------
1092static void gui_load_script_selected(const char *fn) {
1093    if (fn)
1094        script_load(fn, 1);
1095}
1096
1097void gui_load_script(int arg) {
1098    module_fselect_init(LANG_STR_SELECT_SCRIPT_FILE, conf.script_file, "A/CHDK/SCRIPTS", gui_load_script_selected);
1099}
1100
1101void gui_load_script_default(int arg) {
1102    script_load(conf.script_file, 0);
1103    if (conf.script_param_save) {
1104        save_params_values(1);
1105    }
1106}
1107#endif
1108
1109//-------------------------------------------------------------------
1110const char* gui_override_disable_enum(int change, int arg) {
1111        return gui_change_simple_enum(&conf.override_disable,change,gui_override_disable_modes,sizeof(gui_override_disable_modes)/sizeof(gui_override_disable_modes[0]));
1112}
1113
1114//-------------------------------------------------------------------
1115const char* gui_histo_mode_enum(int change, int arg) {
1116    static const char* modes[]={ "Linear", "Log" };
1117
1118        gui_enum_value_change(&conf.histo_mode,change,sizeof(modes)/sizeof(modes[0]));
1119
1120    histogram_set_mode(conf.histo_mode);
1121
1122    return modes[conf.histo_mode];
1123}
1124
1125//-------------------------------------------------------------------
1126const char* gui_histo_layout_enum(int change, int arg) {
1127    static const char* modes[]={ "RGB", "Y", "RGB Y",  "R G B", "RGB all", "Y all", "Blend", "Blend Y"};
1128
1129        gui_enum_value_change(&conf.histo_layout,change,sizeof(modes)/sizeof(modes[0]));
1130
1131    if (conf.histo_layout==OSD_HISTO_LAYOUT_Y || conf.histo_layout==OSD_HISTO_LAYOUT_Y_argb) {
1132        histogram_set_main(HISTO_Y);
1133    } else {
1134        histogram_set_main(HISTO_RGB);
1135    }
1136
1137    return modes[conf.histo_layout];
1138}
1139
1140//-------------------------------------------------------------------
1141const char* gui_font_enum(int change, int arg) {
1142    static const char* fonts[]={ "Win1250", "Win1251", "Win1252", "Win1253", "Win1254", "Win1257"};
1143
1144        gui_enum_value_change(&conf.font_cp,change,sizeof(fonts)/sizeof(fonts[0]));
1145
1146    if (change != 0) {
1147        font_set(conf.font_cp);
1148        if (!rbf_load(conf.menu_rbf_file))
1149            rbf_load_from_8x16(current_font);
1150        rbf_set_codepage(FONT_CP_WIN);
1151        gui_menu_init(NULL);
1152    }
1153
1154    return fonts[conf.font_cp];
1155}
1156
1157//-------------------------------------------------------------------
1158#ifdef  CAM_TOUCHSCREEN_UI
1159
1160const char* gui_on_off_enum(int change, int *conf_val)
1161{
1162    static const char* modes[]={ "Off", "On"};
1163        return gui_change_simple_enum(conf_val,change,modes,sizeof(modes)/sizeof(modes[0]));
1164}
1165
1166#endif
1167
1168//-------------------------------------------------------------------
1169const char* gui_nd_filter_state_enum(int change, int arg) {
1170        return gui_change_simple_enum(&conf.nd_filter_state,change,gui_nd_filter_state_modes,sizeof(gui_nd_filter_state_modes)/sizeof(gui_nd_filter_state_modes[0]));
1171}
1172
1173const char* gui_histo_show_enum(int change, int arg) {
1174        return gui_change_simple_enum(&conf.show_histo,change,gui_histo_show_modes,sizeof(gui_histo_show_modes)/sizeof(gui_histo_show_modes[0]));
1175}
1176
1177//-------------------------------------------------------------------
1178#if CAM_ADJUSTABLE_ALT_BUTTON
1179const char* gui_alt_mode_button_enum(int change, int arg) {
1180#if defined(CAMERA_s2is) || defined(CAMERA_s3is) || defined(CAMERA_s5is)
1181    static const char* names[]={ "Shrtcut", "Flash", "Timer", "ISO", "Video" };
1182    static const int keys[]={ KEY_PRINT, KEY_FLASH, KEY_TIMER, KEY_ISO, KEY_VIDEO };
1183#elif defined(CAMERA_g7) || defined(CAMERA_g9)
1184    static const char* names[]={ "Print", "FE"};
1185    static const int keys[]={ KEY_PRINT, KEY_MICROPHONE };
1186#elif defined(CAMERA_g10) || defined(CAMERA_g12) 
1187    static const char* names[]={ "Print", "Disp",  "AE Lock", "Jump" };
1188    static const int keys[]={ KEY_PRINT, KEY_DISPLAY, KEY_AE_LOCK, KEY_METERING};
1189#elif defined(CAMERA_g11)
1190    static const char* names[]={ "Print", "Disp",  "AE Lock", "Jump" };
1191    static const int keys[]={ KEY_PRINT, KEY_DISPLAY, KEY_MICROPHONE, KEY_METERING};   
1192#elif defined(CAMERA_ixus65_sd630)
1193    static const char* names[]={ "Print", "Disp"};
1194    static const int keys[]={ KEY_PRINT, KEY_DISPLAY };
1195#elif defined(CAMERA_a650)
1196    static const char* names[]={ "Print", "ISO"};
1197    static const int keys[]={ KEY_PRINT, KEY_ISO };
1198#elif defined(CAMERA_sx100is) || defined(CAMERA_sx110is)
1199    static const char* names[]={ "Print", "Face"};
1200    static const int keys[]={ KEY_PRINT, KEY_FACE };
1201#elif defined(CAMERA_sx10) || defined(CAMERA_sx1) || defined(CAMERA_sx20) || defined(CAMERA_sx30) || defined(CAMERA_sx40hs)
1202    static const char* names[]={ "Shrtcut", "Flash", "Video"};
1203    static const int keys[]={ KEY_PRINT, KEY_FLASH, KEY_VIDEO };
1204#elif defined(CAMERA_a570) || defined(CAMERA_a580) || defined(CAMERA_a590) || defined(CAMERA_a720)
1205    static const char* names[]={ "Print", "Display"};
1206    static const int keys[] = {KEY_PRINT, KEY_DISPLAY};
1207#elif defined(CAMERA_sx220hs) || defined(CAMERA_sx230hs)
1208    static const char* names[]={ "Disp+Set", "Display", "Playback", "Video"};
1209    static const int keys[] = {KEY_PRINT, KEY_DISPLAY, KEY_PLAYBACK, KEY_VIDEO};
1210#elif defined(CAMERA_ixus220_elph300hs)
1211    static const char* names[]={ "Video", "Display", "Playback", "Video"};
1212    static const int keys[] = {KEY_PRINT, KEY_DISPLAY, KEY_PLAYBACK, KEY_VIDEO};
1213#else
1214    #error camera alt-buttons not defined
1215#endif
1216    int i;
1217
1218    for (i=0; i<sizeof(names)/sizeof(names[0]); ++i) {
1219        if (conf.alt_mode_button==keys[i]) {
1220            break;
1221        }
1222    }
1223
1224    i+=change;
1225    if (i<0)
1226        i=(sizeof(names)/sizeof(names[0]))-1;
1227    else if (i>=(sizeof(names)/sizeof(names[0])))
1228        i=0;
1229
1230    conf.alt_mode_button = keys[i];
1231    kbd_set_alt_mode_key_mask(conf.alt_mode_button);
1232    return names[i];
1233}
1234#endif
1235
1236//-------------------------------------------------------------------
1237const char* gui_alt_power_enum(int change, int arg) {
1238// Script option is retained even if scripting is disabled, otherwise conf values will change
1239// Equivalent to ALT
1240    static const char* modes[]={ "Never", "Alt", "Script", "Always" };
1241        gui_enum_value_change(&conf.alt_prevent_shutdown,change,sizeof(modes)/sizeof(modes[0]));
1242
1243        conf_update_prevent_shutdown();
1244
1245    return modes[conf.alt_prevent_shutdown];
1246}
1247
1248//-------------------------------------------------------------------
1249const char* gui_video_bitrate_enum(int change, int arg) {
1250        gui_enum_value_change(&conf.video_bitrate,change,VIDEO_BITRATE_STEPS);
1251
1252    shooting_video_bitrate_change(conf.video_bitrate);
1253
1254    return video_bitrate_strings[conf.video_bitrate];
1255}
1256
1257
1258//-------------------------------------------------------------------
1259const char* gui_tv_override_koef_enum(int change, int arg) {
1260    static const char* modes[]={"Off", "1/100K", "1/10000", "1/1000","1/100","1/10", "1","10","100"};
1261
1262    conf.tv_override_koef+=change;
1263   if (conf.tv_enum_type) {
1264     if (conf.tv_override_koef<0)  conf.tv_override_koef=6;
1265     else if (conf.tv_override_koef>6) conf.tv_override_koef=0;
1266     else if (conf.tv_override_koef==1)  conf.tv_override_koef=6;
1267     else if (conf.tv_override_koef==5)  conf.tv_override_koef=0;
1268     else if (conf.tv_override_koef!=0 && conf.tv_override_koef!=6) conf.tv_override_koef=6;
1269     }
1270   else {
1271    if (conf.tv_override_koef<0)
1272        conf.tv_override_koef=sizeof(modes)/sizeof(modes[0])-1;
1273    else if (conf.tv_override_koef>=(sizeof(modes)/sizeof(modes[0])))
1274        conf.tv_override_koef=0;
1275    }
1276
1277    return modes[conf.tv_override_koef];
1278}
1279
1280const char* gui_tv_override_value_enum(int change, int arg) {
1281        /*
1282    static const char* modes[]={
1283    // add very long time exposures as approximately powers of 2, adding 15 exposures
1284    "2048","1625","1290","1024","812","645","512","406","322","256","203","161","128","101","80",
1285                "64","50.8", "40.3", "32", "25.4","20","16", "12.7", "10","8", "6.3","5","4","3.2", "2.5","2", "1.6", "1.3", "1", "0.8", "0.6", "0.5", "0.4", "0.3", "1/4", "1/5", "1/6", "1/8", "1/10", "1/13", "1/15", "1/20", "1/25", "1/30", "1/40", "1/50", "1/60", "1/80", "1/100", "1/125", "1/160", "1/200", "1/250", "1/320", "1/400", "1/500", "1/640","1/800", "1/1000", "1/1250", "1/1600","1/2000","1/2500","1/3200","1/4000", "1/5000", "1/6400", "1/8000", "1/10000", "1/12500", "1/16000", "1/20000", "1/25000", "1/32000", "1/40000", "1/50000", "1/64000","1/80000", "1/100k"};
1286                */
1287    static char buf[4];
1288
1289        // XXX This array above is redundant with platform/generic/shooting.c, this should be avoided!
1290    conf.tv_override_value+=change;
1291    if (conf.tv_enum_type) {
1292       if (conf.tv_override_value<0) {
1293          conf.tv_override_value=tv_override_amount-1;
1294        }
1295       else if ((unsigned)conf.tv_override_value>=(tv_override_amount))
1296         conf.tv_override_value=0;
1297       return tv_override[conf.tv_override_value];
1298     }
1299     else
1300      {
1301       if (conf.tv_override_value<0) {
1302          conf.tv_override_value=100;
1303        }
1304       else if (conf.tv_override_value>100)  conf.tv_override_value=0;
1305       sprintf(buf, "%d",  conf.tv_override_value);
1306       return buf;
1307      }
1308}
1309
1310const char* gui_tv_enum_type_enum(int change, int arg) {
1311    static const char* modes[]={"Factor", "Ev Step"};
1312
1313    gui_enum_value_change(&conf.tv_enum_type,change,sizeof(modes)/sizeof(modes[0]));
1314    if (change) {
1315        conf.tv_override_koef=6;
1316        if (conf.tv_enum_type)
1317            conf.tv_override_value=tv_override_zero_shift;
1318        else conf.tv_override_value=1;
1319    }
1320    return modes[conf.tv_enum_type];
1321}
1322
1323const char* gui_subj_dist_override_value_enum(int change, int arg) {
1324        static const int koef[] = {0, 1,10,100,1000};
1325    static char buf[8];
1326    conf.subj_dist_override_value+=(change*koef[conf.subj_dist_override_koef]);
1327    if (conf.subj_dist_override_value<0)
1328        conf.subj_dist_override_value=MAX_DIST;
1329    else if (conf.subj_dist_override_value>MAX_DIST)
1330        conf.subj_dist_override_value=0;
1331    sprintf(buf, "%d", (int)conf.subj_dist_override_value);
1332    return buf;
1333}
1334
1335
1336const char* gui_subj_dist_override_koef_enum(int change, int arg) {
1337        return gui_change_simple_enum(&conf.subj_dist_override_koef,change,gui_override_koef_modes,sizeof(gui_override_koef_modes)/sizeof(gui_override_koef_modes[0]));
1338}
1339
1340/*
1341const char* gui_tv_exposure_order_enum(int change, int arg) {
1342    static const char* modes[]={ "Off", "1","2", "3"};
1343
1344    conf.tv_exposure_order+=change;
1345    if (conf.tv_exposure_order<0)
1346        conf.tv_exposure_order=0;
1347    else if (conf.tv_exposure_order>=(sizeof(modes)/sizeof(modes[0])))
1348        conf.tv_exposure_order=sizeof(modes)/sizeof(modes[0])-1;
1349    if((conf.tv_exposure_order>0) && (conf.av_exposure_order==conf.tv_exposure_order))
1350     {
1351       conf.av_exposure_order=0;
1352     }
1353    if((conf.tv_exposure_order>0) && (conf.iso_exposure_order==conf.tv_exposure_order))
1354     {
1355       conf.iso_exposure_order=0;
1356     }
1357
1358    return modes[conf.tv_exposure_order];
1359}
1360
1361const char* gui_av_exposure_order_enum(int change, int arg) {
1362    static const char* modes[]={ "Off", "1","2", "3"};
1363
1364    conf.av_exposure_order+=change;
1365    if (conf.av_exposure_order<0)
1366        conf.av_exposure_order=0;
1367    else if (conf.av_exposure_order>=(sizeof(modes)/sizeof(modes[0])))
1368        conf.av_exposure_order=sizeof(modes)/sizeof(modes[0])-1;
1369    if((conf.av_exposure_order>0) && (conf.tv_exposure_order==conf.av_exposure_order))
1370     {
1371       conf.tv_exposure_order=0;
1372     }
1373    if((conf.av_exposure_order>0) && (conf.iso_exposure_order==conf.av_exposure_order))
1374     {
1375       conf.iso_exposure_order=0;
1376     }
1377    return modes[conf.av_exposure_order];
1378}
1379
1380const char* gui_iso_exposure_order_enum(int change, int arg) {
1381    static const char* modes[]={ "Off", "1","2", "3"};
1382
1383    conf.iso_exposure_order+=change;
1384    if (conf.iso_exposure_order<0)
1385        conf.iso_exposure_order=0;
1386    else if (conf.iso_exposure_order>=(sizeof(modes)/sizeof(modes[0])))
1387        conf.iso_exposure_order=sizeof(modes)/sizeof(modes[0])-1;
1388    if((conf.iso_exposure_order>0) && (conf.tv_exposure_order==conf.iso_exposure_order))
1389     {
1390       conf.tv_exposure_order=0;
1391     }
1392    if((conf.iso_exposure_order>0) && (conf.av_exposure_order==conf.iso_exposure_order))
1393     {
1394       conf.av_exposure_order=0;
1395     }
1396
1397    return modes[conf.iso_exposure_order];
1398}
1399*/
1400const char* gui_av_override_enum(int change, int arg) {
1401    static char buf[8];
1402    short prop_id;
1403    conf.av_override_value+=change;
1404    if (conf.av_override_value<0) conf.av_override_value=shooting_get_aperture_sizes_table_size()+6;
1405    else if (conf.av_override_value>shooting_get_aperture_sizes_table_size()+6) conf.av_override_value=0;
1406    if (conf.av_override_value == 0)  return "Off";
1407    else {
1408     short prop_id=shooting_get_aperture_from_av96(shooting_get_av96_override_value());
1409         sprintf(buf, "%d.%02d", (int)prop_id/100, (int)prop_id%100 );
1410         return buf;
1411        }
1412}
1413
1414#if ZOOM_OVERRIDE
1415const char* gui_zoom_override_enum(int change, int arg) {
1416    static char buf[3];
1417    conf.zoom_override_value+=change;
1418    if (conf.zoom_override_value<0) conf.zoom_override_value=zoom_points-1;
1419    else if (conf.zoom_override_value>zoom_points-1) conf.zoom_override_value=0;
1420                sprintf(buf,"%i",conf.zoom_override_value);
1421                return buf;
1422}
1423#endif
1424
1425const char* gui_user_menu_show_enum(int change, int arg) {
1426    static const char* modes[]={ "Off", "On","On Direct", "Edit" };
1427
1428        if (conf.user_menu_enable == 3) user_menu_save();
1429        return gui_change_simple_enum(&conf.user_menu_enable,change,modes,sizeof(modes)/sizeof(modes[0]));
1430}
1431
1432const char* gui_video_af_key_enum(int change, int arg){
1433#if CAMERA_g12
1434    static const char* names[]={ "", "Shutter", "Set", "AE Lock"};
1435    static const int keys[]={0, KEY_SHOOT_HALF, KEY_SET, KEY_AE_LOCK };
1436#else
1437    static const char* names[]={ "", "Shutter", "Set"};
1438    static const int keys[]={0, KEY_SHOOT_HALF, KEY_SET };
1439#endif
1440    int i;
1441
1442    for (i=0; i<sizeof(names)/sizeof(names[0]); ++i) {
1443        if (conf.video_af_key==keys[i]) {
1444            break;
1445        }
1446    }
1447
1448    i+=change;
1449    if (i<0)
1450        i=(sizeof(names)/sizeof(names[0]))-1;
1451    else if (i>=(sizeof(names)/sizeof(names[0])))
1452        i=0;
1453
1454    conf.video_af_key = keys[i];
1455    return names[i];
1456}
1457
1458const char* gui_bad_pixel_enum(int change, int arg) {
1459    int modes[]={LANG_MENU_BAD_PIXEL_OFF, LANG_MENU_BAD_PIXEL_INTERPOLATION, LANG_MENU_BAD_PIXEL_RAW_CONVERTER};
1460        return lang_str((int)gui_change_simple_enum(&conf.bad_pixel_removal,change,(const char **)modes,sizeof(modes)/sizeof(modes[0])));
1461}
1462
1463//-------------------------------------------------------------------
1464
1465void raw_fselect_cb(const char * filename){
1466 struct stat st;
1467 if (!filename) return;
1468 stat((char*)filename,&st);
1469 if (st.st_size!=hook_raw_size()) return;
1470 gui_mbox_init((int)"", LANG_RAW_DEVELOP_MESSAGE, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
1471 raw_prepare_develop((char*)filename);
1472}
1473
1474//-------------------------------------------------------------------
1475void gui_raw_develop(int arg){
1476 int m=mode_get();
1477 module_fselect_init(LANG_RAW_DEVELOP_SELECT_FILE, "A/DCIM", "A", raw_fselect_cb);
1478}
1479
1480//-------------------------------------------------------------------
1481
1482static void gui_menuproc_reset_files(int arg){
1483conf.lang_file[0] = 0;
1484conf.menu_symbol_rbf_file[0] = 0;
1485conf.menu_rbf_file[0] = 0;
1486conf_save();
1487gui_mbox_init(LANG_INFORMATION, LANG_MENU_RESTART_CAMERA, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
1488
1489}
1490
1491//-------------------------------------------------------------------
1492#ifdef OPT_DEBUGGING
1493#define TASKLIST_MAX_LINES 12 // probably as much as will fit on screen
1494#define TASKLIST_NUM_TASKS 64 // should be enough ?
1495static void gui_debug_draw_tasklist(void) {
1496#ifndef CAM_DRYOS
1497    int tasklist[TASKLIST_NUM_TASKS]; // max number of tasks we will look at
1498    char buf[40]; // a single line of the list
1499    int n_tasks,n_show_tasks,show_start;
1500    const char *name;
1501    int i;
1502    n_tasks = task_id_list_get(tasklist,sizeof(tasklist)/sizeof(tasklist[0]));
1503    show_start = debug_tasklist_start;
1504    n_show_tasks = n_tasks - show_start;
1505    // auto adjust to show the last N tasks
1506    if(n_show_tasks < TASKLIST_MAX_LINES) {
1507        show_start = n_tasks - TASKLIST_MAX_LINES;
1508        if(show_start<0)
1509            show_start = 0;
1510         n_show_tasks = n_tasks - show_start;
1511    }
1512    else if( n_show_tasks > TASKLIST_MAX_LINES ) {
1513        n_show_tasks = TASKLIST_MAX_LINES;
1514    }
1515    sprintf(buf,"%d-%d of %d tasks %c",show_start,show_start+n_show_tasks,n_tasks,debug_display_direction > 0?'+':'-');
1516    draw_string(64,0,buf, conf.osd_color);
1517    for( i = 0;  i < n_show_tasks; i++ ) {
1518        // TODO get full task info
1519        name = task_name(tasklist[show_start+i]);
1520        if ( !name || !*name ) {
1521            name = "(unknown)";
1522        }
1523        sprintf(buf,"%10s %8X",name,tasklist[show_start+i]);
1524        draw_string(64,16+16*i,buf, conf.osd_color);
1525    }
1526#endif //CAM_DRYOS
1527}
1528
1529#define DEBUG_DISPLAY_NONE 0
1530#define DEBUG_DISPLAY_PROPS 1
1531#define DEBUG_DISPLAY_PARAMS 2
1532#define DEBUG_DISPLAY_TASKS 3
1533
1534static void gui_debug_shortcut(void) {
1535    static int lastcall = -1;
1536    int t=get_tick_count();
1537    if ( lastcall != -1) {
1538        if (t-lastcall <= 400)
1539            debug_display_direction = -debug_display_direction;
1540    }
1541    lastcall=t;
1542    switch(conf.debug_shortcut_action) {
1543        case 1:
1544            dump_memory();
1545        break;
1546        case 2:
1547            if(conf.debug_display == DEBUG_DISPLAY_TASKS) {
1548                debug_tasklist_start += debug_display_direction*(TASKLIST_MAX_LINES-2); // a little intentional overlap
1549                if(debug_tasklist_start >= TASKLIST_NUM_TASKS || debug_tasklist_start < 0)
1550                    debug_tasklist_start = 0;
1551            }
1552            else if (conf.debug_display == DEBUG_DISPLAY_PROPS || conf.debug_display == DEBUG_DISPLAY_PARAMS) {
1553                conf.debug_propcase_page += debug_display_direction*1;
1554                if(conf.debug_propcase_page > 128 || conf.debug_propcase_page < 0)
1555                    conf.debug_propcase_page = 0;
1556            }
1557        break;
1558        case 3:
1559            gui_compare_props(1);
1560        break;
1561    }
1562}
1563
1564//-------------------------------------------------------------------
1565#endif
1566
1567#if CAM_MULTIPART
1568void card_break_proc(unsigned int btn){
1569 if (btn==MBOX_BTN_YES) create_partitions();
1570}
1571
1572
1573#ifdef OPT_DEBUGGING
1574static void gui_menuproc_break_card(int arg){
1575 gui_mbox_init(LANG_WARNING, LANG_PARTITIONS_CREATE_WARNING, MBOX_BTN_YES_NO|MBOX_DEF_BTN2|MBOX_TEXT_CENTER, card_break_proc);
1576}
1577#endif
1578
1579static void gui_menuproc_swap_partitions(int arg){
1580 if (get_part_count()<2) gui_mbox_init(LANG_ERROR, LANG_ONLY_ONE_PARTITION, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
1581 else
1582        {
1583                swap_partitions();
1584                gui_mbox_init(LANG_INFORMATION, LANG_SOKOBAN_MSG_FINISH_TITLE, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
1585        }
1586}
1587#endif
1588
1589//-------------------------------------------------------------------
1590static volatile gui_mode_t gui_mode;    // current gui mode. if <GUI_MODE_LASTIDX - idx in guiHandlers (core modes), otherwise pointer to gui_handler object (module modes)
1591
1592static volatile int gui_restore;
1593static volatile int gui_in_redraw;
1594static int gui_splash, gui_splash_mode;
1595static char osd_buf[32];
1596#ifdef OPTIONS_AUTOSAVE
1597static Conf old_conf;
1598#endif
1599
1600extern gui_handler guiHandlers[];
1601
1602//-------------------------------------------------------------------
1603void gui_init()
1604{
1605    gui_set_mode(GUI_MODE_NONE);
1606    gui_restore = 0;
1607    gui_in_redraw = 0;
1608    if (conf.start_sound>0)
1609    {
1610        play_sound(4);
1611    }
1612    gui_splash = (conf.splash_show)?SPLASH_TIME:0;
1613
1614        gui_modules_menu_load();
1615    user_menu_restore();
1616    gui_lang_init();
1617    draw_init();
1618
1619    exposition_thresh = screen_size/500;
1620    voltage_step = (conf.batt_step_25)?25:1;
1621    load_from_file( "A/CHDK/badpixel", make_pixel_list );
1622    load_from_file( "A/CHDK/badpixel.txt", make_pixel_list );
1623#ifdef OPT_CURVES
1624        // initialize curves, loading files if required by current mode
1625        //curve_init_mode();    // @tsv it will be initialize on first load
1626#endif
1627#if ZOOM_OVERRIDE
1628// reyalp - need to do this in capt_seq
1629//              if (conf.zoom_override) shooting_set_zoom(conf.zoom_override_value);
1630#endif
1631}
1632
1633
1634//-------------------------------------------------------------------
1635void gui_modules_menu_load(int arg){
1636
1637        misc_submenu_items[1].type=MENUITEM_TEXT;
1638
1639        unsigned int argv[] ={  (unsigned int)MODULES_PATH,
1640                                                        (unsigned int)(&misc_submenu_items[1])
1641                                                 };
1642        module_run("modmenu.flt", 0, 2,argv, UNLOAD_IF_ERR );
1643}
1644
1645//-------------------------------------------------------------------
1646#ifdef OPT_CURVES
1647static void gui_load_curve_selected(const char *fn) {
1648        if (fn) {
1649                // TODO we could sanity check here, but curve_set_type should fail gracefullish
1650                strcpy(conf.curve_file,fn);
1651                if(conf.curve_enable == 1 && curve_init_mode)
1652                        curve_init_mode();
1653        }
1654}
1655
1656//-------------------------------------------------------------------
1657void gui_load_curve(int arg) {
1658    module_fselect_init(LANG_STR_SELECT_CURVE_FILE, conf.curve_file, CURVE_DIR, gui_load_curve_selected);
1659}
1660
1661#endif
1662
1663
1664// Small hack: use understandable name to reused data member
1665#define binded_gui_mode_ptr kbd_process
1666
1667//-------------------------------------------------------------------
1668gui_mode_t gui_get_mode() {
1669    if ( gui_mode >= GUI_MODE_COUNT )
1670        {
1671                int mode;
1672                for (mode=0;mode<GUI_MODE_COUNT;mode++)
1673                {
1674                        if ( (guiHandlers[mode].flags & GUI_MODE_FLAG_ALIAS) &&
1675                                        guiHandlers[mode].binded_gui_mode_ptr == (void*)gui_mode )
1676                                return mode;
1677                }
1678        }
1679    return gui_mode;
1680}
1681
1682//-------------------------------------------------------------------
1683void gui_set_mode(gui_mode_t mode)
1684{
1685        if ( gui_mode == mode )
1686                return;
1687
1688        if (  mode < GUI_MODE_COUNT &&
1689                  (guiHandlers[mode].flags & GUI_MODE_FLAG_ALIAS) )
1690        {
1691                mode = (unsigned int)guiHandlers[mode].binded_gui_mode_ptr;
1692        }
1693
1694        // Sanity check for case module pointer - is this really gui_handler
1695    if ( mode >= GUI_MODE_COUNT && ((gui_handler*)mode)->magicnum != GUI_MODE_MAGICNUM ) {
1696                // If sanity failed (module is unload) - set to default mode
1697        gui_mode = GUI_MODE_NONE;
1698                draw_restore();
1699                return;
1700        }
1701       
1702#ifdef CAM_TOUCHSCREEN_UI
1703    if (((gui_mode == 0) != (mode == 0)) ||                         // Change from GUI_MODE_NONE to any other or vice-versa
1704        ((gui_mode > GUI_MODE_MENU) != (mode > GUI_MODE_MENU)))     // Switch in & out of menu mode
1705        redraw_buttons = 1;
1706#endif
1707    gui_mode = mode;
1708}
1709
1710//-------------------------------------------------------------------
1711// PURPOSE: bind module struct to
1712// RETUN: 0 - fail, 1 - ok
1713int gui_bind_mode(int core_mode, gui_handler* handler) {
1714
1715        // sanity checks
1716    if ( core_mode >= GUI_MODE_COUNT ||
1717                (guiHandlers[core_mode].flags & GUI_MODE_FLAG_ALIAS)==0
1718           )
1719                return 0;
1720
1721        if ( handler && handler->magicnum != GUI_MODE_MAGICNUM )
1722                return 0;
1723
1724        // check is this module is already binded (loaded with different name)
1725        gui_handler* bind_gui_handler = (gui_handler*)guiHandlers[core_mode].binded_gui_mode_ptr;
1726        if ( bind_gui_handler && bind_gui_handler->magicnum == GUI_MODE_MAGICNUM )
1727                return 0;
1728
1729        guiHandlers[core_mode].binded_gui_mode_ptr = (void*)handler;
1730        return 1;
1731}
1732
1733#undef binded_gui_mode_ptr
1734
1735
1736//-------------------------------------------------------------------
1737void gui_force_restore() {
1738    gui_restore = gui_in_redraw;
1739}
1740
1741static void gui_handle_splash(void) {
1742        static char *logo = NULL;
1743    static int logo_size;
1744    if (gui_splash) {
1745                static int need_logo=1; // don't use logo ptr, since we don't want to keep re-trying
1746                if(need_logo) {
1747                const char *logo_name="A/CHDK/DATA/logo.dat";
1748            FILE *fd;
1749            struct stat st;
1750                        need_logo=0;
1751            if (stat(logo_name,&st) == 0) {
1752                                logo_size=st.st_size;
1753                                logo=malloc(logo_size);
1754                                if(logo) {
1755                                        fd = fopen(logo_name, "rb");
1756                                        if(fd){
1757                                                fread(logo,1,logo_size,fd);
1758                                                fclose(fd);
1759                                        }
1760                                        else {
1761                                                free(logo);
1762                                                logo=NULL;
1763                                        }
1764                }
1765                        }
1766                }
1767        if (gui_splash>(SPLASH_TIME-4)) {
1768            gui_draw_splash(logo,logo_size);
1769           //   conf.show_osd = 0;
1770        } else if (gui_splash==1 && (mode_get()&MODE_MASK) == gui_splash_mode && (gui_mode==GUI_MODE_NONE || gui_mode==GUI_MODE_ALT)) {
1771            draw_restore();
1772           // conf.show_osd = 1; //had to uncomment in order to fix a bug with disappearing osd...
1773        }
1774        --gui_splash;
1775                if(!gui_splash) {
1776                        free(logo);
1777                }
1778    }
1779}
1780
1781//-------------------------------------------------------------------
1782#ifdef OPTIONS_AUTOSAVE
1783
1784static void conf_store_old_settings() {
1785    old_conf=conf;
1786}
1787
1788static int conf_save_new_settings_if_changed() {
1789    if (memcmp(&old_conf, &conf, sizeof(Conf)) != 0) {
1790                user_menu_save();
1791        conf_save();
1792        conf_store_old_settings();
1793        return 1;
1794    }
1795    return 0;
1796}
1797
1798#endif
1799
1800//-------------------------------------------------------------------
1801void gui_chdk_draw()
1802{
1803    static int show_md_grid=0;
1804
1805    gui_draw_osd();
1806
1807#ifdef CAM_DISP_ALT_TEXT
1808    draw_txt_string(20, 14, "<ALT>", MAKE_COLOR(COLOR_ALT_BG, COLOR_FG));
1809#endif
1810
1811#ifdef OPT_SCRIPTING
1812    if ((mode_get()&MODE_MASK) == MODE_REC)
1813    {
1814        draw_txt_string(0, 14, script_title, MAKE_COLOR(COLOR_ALT_BG, COLOR_FG));
1815        if (state_kbd_script_run) show_md_grid=5;
1816        if (show_md_grid)
1817        {
1818            --show_md_grid;
1819            md_draw_grid();
1820        }
1821    }
1822#endif
1823
1824    console_draw();
1825}
1826
1827//-------------------------------------------------------------------
1828// Handler for Menu button press default - enter Menu mode
1829void gui_default_kbd_process_menu_btn()
1830{
1831    gui_set_mode(GUI_MODE_MENU);
1832    draw_restore();
1833}
1834
1835// Change SD override factor, direction = 1 to increase, -1 to decrease
1836// Only applies if camera has a Zoom lever
1837#if CAM_HAS_ZOOM_LEVER
1838static void sd_override_koef(int direction)
1839{
1840    gui_subj_dist_override_koef_enum(direction,0);
1841#if !CAM_HAS_MANUAL_FOCUS
1842    if (conf.subj_dist_override_koef==0) conf.subj_dist_override_koef=1;
1843#endif
1844    shooting_set_focus(shooting_get_subject_distance_override_value(), SET_NOW);
1845}
1846#endif
1847
1848// Change SD override by factor amount, direction = 1 to increase (zoom in), -1 to decrease (zoom out)
1849static void sd_override(int direction)
1850{
1851    gui_subj_dist_override_value_enum(direction,0);
1852    shooting_set_focus(shooting_get_subject_distance_override_value(),SET_NOW);
1853}
1854
1855// Main button processing for CHDK Alt mode (not in MENU mode)
1856// This needs to be cleaned up, re-organised and commented !!!!
1857void gui_chdk_kbd_process()
1858{
1859#if !CAM_HAS_ERASE_BUTTON && CAM_CAN_SD_OVERRIDE        // ALT RAW toggle kbd processing if camera has SD override but no erase button
1860    if (kbd_is_key_clicked(SHORTCUT_TOGGLE_RAW))
1861    {
1862        if (conf.debug_shortcut_action > 0)
1863        {
1864#ifdef OPT_DEBUGGING
1865            gui_debug_shortcut();
1866#endif
1867        }
1868        // Check in manual focus mode
1869        else if (!shooting_get_common_focus_mode())
1870        {
1871            // Not manual focus mode so just update RAW save setting
1872            conf.save_raw = !conf.save_raw;
1873            draw_restore();
1874        }
1875        else
1876        {
1877            // In manual focus mode so update shooting distance
1878#if CAM_HAS_ZOOM_LEVER
1879            conf.subj_dist_override_value=MAX_DIST;
1880            shooting_set_focus(shooting_get_subject_distance_override_value(), SET_NOW);
1881#else
1882            if (conf.subj_dist_override_koef==4)
1883                gui_subj_dist_override_koef_enum(-3,0);
1884            else
1885                gui_subj_dist_override_koef_enum(1,0);
1886#endif
1887        }
1888    }
1889#else                                                   // ALT RAW toggle kbd processing if can't SD override or has erase button
1890    if (kbd_is_key_clicked(SHORTCUT_TOGGLE_RAW))
1891    {
1892        if (conf.debug_shortcut_action > 0)
1893        {
1894#ifdef OPT_DEBUGGING
1895            gui_debug_shortcut();
1896#endif
1897        }
1898        else
1899        {
1900            // Change RAW save state
1901            conf.save_raw = !conf.save_raw;
1902            draw_restore();
1903        }
1904    }
1905#endif
1906#ifdef OPT_SCRIPTING                                    // ALT Set button processing if scripting enabled - open script menu
1907    else if (kbd_is_key_clicked(KEY_SET))
1908    {
1909        gui_menu_init(&script_submenu);
1910        gui_default_kbd_process_menu_btn();
1911    }
1912#endif
1913#if CAM_CAN_SD_OVERRIDE                                 // ALT button processing if camera has SD override
1914    else
1915    {
1916#if !CAM_HAS_MANUAL_FOCUS
1917        if (kbd_is_key_clicked(SHORTCUT_MF_TOGGLE))     // Camera does not have manual focus
1918        {
1919            if (conf.subj_dist_override_koef>0)
1920                conf.subj_dist_override_koef=0;
1921            else conf.subj_dist_override_koef=1;
1922            draw_restore();
1923        }
1924        else
1925#endif
1926        if (shooting_get_common_focus_mode())           // Check in manual focus mode
1927        {
1928#if CAM_HAS_ZOOM_LEVER                                  // Camera has zoom lever, use left & right to change factor,up to set infinity
1929            if (kbd_is_key_clicked(KEY_RIGHT))
1930            {
1931                sd_override_koef(1);
1932            }
1933            else if (kbd_is_key_clicked(KEY_LEFT))
1934            {
1935                sd_override_koef(-1);
1936            }
1937            else if (kbd_is_key_clicked(SHORTCUT_SET_INFINITY))
1938            {
1939                conf.subj_dist_override_value=MAX_DIST;
1940                shooting_set_focus(shooting_get_subject_distance_override_value(), SET_NOW);
1941            }
1942            else
1943#endif
1944            if (kbd_is_key_clicked(SHORTCUT_SET_HYPERFOCAL))    // Set hyperfocal distance if down pressed
1945            {
1946                int m=mode_get()&MODE_SHOOTING_MASK;
1947                if ((m==MODE_M) || (m==MODE_AV))
1948                     conf.subj_dist_override_value=(int)shooting_get_hyperfocal_distance_f(shooting_get_aperture_from_av96(shooting_get_user_av96()),get_focal_length(lens_get_zoom_point()));
1949                else conf.subj_dist_override_value=(int)shooting_get_hyperfocal_distance();
1950                shooting_set_focus(shooting_get_subject_distance_override_value(), SET_NOW);
1951            }
1952            else
1953            {
1954                switch (kbd_get_autoclicked_key())
1955                {
1956#if CAM_HAS_ZOOM_LEVER
1957                case KEY_ZOOM_IN:
1958#else
1959                case KEY_RIGHT:
1960#endif
1961                    sd_override(1);
1962                    break;
1963#if CAM_HAS_ZOOM_LEVER
1964                case KEY_ZOOM_OUT:
1965#else
1966                case KEY_LEFT:
1967#endif
1968                    sd_override(-1);
1969                    break;
1970                }
1971            }
1972        }
1973    }
1974#endif
1975}
1976
1977//-------------------------------------------------------------------
1978// Handler for Menu button press in CHDK Alt mode (not in Menu mode)
1979// Enter main menu or user menu based on configuration
1980void gui_chdk_kbd_process_menu_btn()
1981{
1982    if (conf.user_menu_as_root && (conf.user_menu_enable != 0)) {
1983        if (kbd_is_key_pressed(KEY_SHOOT_HALF))
1984            gui_menu_init(&root_menu);
1985        else
1986            gui_menu_init(&user_submenu);
1987    }
1988    else {
1989        if ((conf.user_menu_enable != 0) && kbd_is_key_pressed(KEY_SHOOT_HALF))
1990            gui_menu_init(&user_submenu);
1991        else
1992            gui_menu_init(&root_menu);
1993    }
1994    gui_default_kbd_process_menu_btn();
1995}
1996
1997// Menu button handled for Menu mode
1998void gui_menu_kbd_process_menu_btn()
1999{
2000#ifdef OPTIONS_AUTOSAVE
2001    conf_save_new_settings_if_changed();
2002#endif
2003    if (gui_user_menu_flag)
2004    {
2005        gui_set_mode(GUI_MODE_MENU);
2006        gui_user_menu_flag = 0;
2007        gui_menu_init(&root_menu);
2008    }
2009    else
2010        gui_set_mode(GUI_MODE_ALT);
2011    draw_restore();
2012}
2013
2014//-------------------------------------------------------------------
2015// GUI handler table (entries must be in the same order and have the same number of entries as Gui_Mode enum)
2016gui_handler guiHandlers[GUI_MODE_COUNT] =
2017{
2018    /*GUI_MODE_NONE*/           { gui_draw_osd,         0,                          0,                                                          0,                                                                      GUI_MODE_MAGICNUM },
2019    /*GUI_MODE_ALT*/            { gui_chdk_draw,        gui_chdk_kbd_process,       gui_chdk_kbd_process_menu_btn,      0,                                                                      GUI_MODE_MAGICNUM },           
2020    /*GUI_MODE_MENU*/           { gui_menu_draw,        gui_menu_kbd_process,       gui_menu_kbd_process_menu_btn,      0,                                                                      GUI_MODE_MAGICNUM },
2021    /*GUI_MODE_ALIAS_PALETTE*/  { 0,                                    0,                                              0,                                                              GUI_MODE_FLAG_ALIAS,                            GUI_MODE_MAGICNUM },
2022    /*GUI_MODE_MBOX*/           { gui_mbox_draw,        gui_mbox_kbd_process,       0,                                                          GUI_MODE_FLAG_NORESTORE_ON_SWITCH,      GUI_MODE_MAGICNUM },
2023    /*GUI_MODE_ALIAS_FSELECT*/  { 0,                                    0,                                              0,                                                              GUI_MODE_FLAG_ALIAS,                            GUI_MODE_MAGICNUM },
2024    /*GUI_MODE_OSD*/            { gui_osd_draw,         gui_osd_kbd_process,        gui_default_kbd_process_menu_btn, 0,                                                                 GUI_MODE_MAGICNUM },           // THIS IS OSD LAYOUT EDITOR
2025    /*GUI_MODE_ALIAS_MPOPUP*/   { 0,                                    0,                                              0,                                                              GUI_MODE_FLAG_ALIAS,                            GUI_MODE_MAGICNUM },
2026};
2027
2028
2029//-------------------------------------------------------------------
2030// Main GUI redraw function, perform common initialisation then calls the redraw handler for the mode
2031void gui_redraw()
2032{
2033    static gui_mode_t gui_mode_prev_tick = GUI_MODE_NONE;
2034    gui_mode_t gui_mode_old;
2035
2036    static int flag_gui_enforce_redraw = 0;
2037
2038#ifdef CAM_DETECT_SCREEN_ERASE
2039    if (!draw_test_guard() && gui_mode)     // Attempt to detect screen erase in <Alt> mode, redraw if needed
2040    {
2041        draw_set_guard();
2042
2043                flag_gui_enforce_redraw |= GUI_REDRAWFLAG_ERASEGUARD;
2044        //gui_menu_force_redraw();
2045        //gui_fselect_force_redraw();   //@tsv
2046#ifdef CAM_TOUCHSCREEN_UI
2047        extern int redraw_buttons;
2048        redraw_buttons = 1;
2049#endif
2050    }
2051#endif
2052
2053        gui_handle_splash();
2054
2055    gui_in_redraw = 1;
2056    gui_mode_old = gui_mode;
2057
2058#ifdef CAM_TOUCHSCREEN_UI
2059    extern void virtual_buttons();
2060    virtual_buttons();
2061#endif
2062
2063    // Call redraw handler
2064        gui_handler* cur_gui_handler = (gui_mode<GUI_MODE_COUNT)? (&guiHandlers[gui_mode]) : (gui_handler*)gui_mode;
2065    if (cur_gui_handler->redraw) cur_gui_handler->redraw(flag_gui_enforce_redraw);
2066        flag_gui_enforce_redraw=0;
2067
2068    // Forced redraw if needed
2069    gui_in_redraw = 0;
2070        cur_gui_handler = (gui_mode<GUI_MODE_COUNT)? (&guiHandlers[gui_mode]) : (gui_handler*)gui_mode;
2071    if ((gui_mode_old != gui_mode
2072                        && (gui_mode_old != GUI_MODE_NONE && gui_mode_old != GUI_MODE_ALT)
2073                        && !(cur_gui_handler->flags & GUI_MODE_FLAG_NORESTORE_ON_SWITCH))
2074            || gui_restore )
2075        {
2076
2077        if (gui_restore)
2078                        flag_gui_enforce_redraw |= GUI_REDRAWFLAG_DRAW_RESTORED;
2079        gui_restore = 0;
2080
2081        if ( !( cur_gui_handler->flags & GUI_MODE_FLAG_NODRAWRESTORE) )
2082            draw_restore();
2083    }
2084
2085        if ( gui_mode_prev_tick != gui_mode ) {
2086                flag_gui_enforce_redraw |= GUI_REDRAWFLAG_MODE_WAS_CHANGED;
2087                gui_mode_prev_tick = gui_mode;
2088        }
2089}
2090
2091//-------------------------------------------------------------------
2092// Main kbd processing for GUI modes
2093void gui_kbd_process()
2094{
2095        gui_handler* cur_gui_handler = (gui_mode<GUI_MODE_COUNT)? (&guiHandlers[gui_mode]) : (gui_handler*)gui_mode;   
2096
2097    // Call menu button handler if menu button pressed
2098    if (kbd_is_key_clicked(KEY_MENU))
2099    {
2100        if (cur_gui_handler->kbd_process_menu_btn) cur_gui_handler->kbd_process_menu_btn();
2101        return;
2102    }
2103
2104    // Call mode handler for other buttons
2105    if (cur_gui_handler->kbd_process) cur_gui_handler->kbd_process();
2106}
2107
2108//-------------------------------------------------------------------
2109void gui_kbd_enter()
2110{
2111    // XXX set custom palette
2112#ifdef OPTIONS_AUTOSAVE
2113    conf_store_old_settings();
2114#endif
2115    gui_set_mode(GUI_MODE_ALT);
2116
2117        conf_update_prevent_shutdown();
2118
2119    vid_turn_off_updates();
2120
2121    // If user menu set to start automatically when <ALT> mode entered
2122    // then enter user menu mode, unless a script was paused by exiting
2123    // <ALT> mode when the script was running.
2124        gui_user_menu_flag = 0;
2125        if ((conf.user_menu_enable == 2) && !state_kbd_script_run) {
2126                gui_menu_init(&user_submenu);
2127                gui_set_mode(GUI_MODE_MENU);
2128                draw_restore();
2129                gui_user_menu_flag = 1;
2130        }
2131
2132}
2133
2134//-------------------------------------------------------------------
2135void gui_kbd_leave()
2136{
2137    // XXX restore palette
2138#ifdef OPTIONS_AUTOSAVE
2139    conf_save_new_settings_if_changed();
2140#endif
2141#ifdef OPT_UBASIC
2142    ubasic_error = UBASIC_E_NONE;
2143#endif
2144    draw_restore();
2145    rbf_set_codepage(FONT_CP_WIN);
2146    vid_turn_on_updates();
2147    gui_set_mode(GUI_MODE_NONE);
2148
2149        // Unload all modules which are marked as safe to unload
2150        module_async_unload_allrunned(0);
2151
2152        conf_update_prevent_shutdown();
2153}
2154//-------------------------------------------------------------------
2155
2156void other_kbd_process(){
2157 int key;
2158#if CAM_AF_SCAN_DURING_VIDEO_RECORD
2159
2160 if (movie_status==VIDEO_RECORD_IN_PROGRESS) {
2161  if (kbd_is_key_clicked(conf.video_af_key)) MakeAFScan();
2162 }
2163
2164#endif
2165
2166#if CAM_CAN_UNLOCK_OPTICAL_ZOOM_IN_VIDEO
2167 // return from digital to optical zoom in video
2168#if CAM_HAS_ZOOM_LEVER
2169   key=KEY_ZOOM_OUT;
2170#else
2171   key=KEY_DOWN;
2172#endif
2173    if (conf.unlock_optical_zoom_for_video && (movie_status==VIDEO_RECORD_IN_PROGRESS) &&  kbd_is_key_clicked(key)){
2174     short x;
2175     get_property_case(PROPCASE_DIGITAL_ZOOM_STATE, &x, sizeof(x));
2176     if (x) {
2177      get_property_case(PROPCASE_DIGITAL_ZOOM_POSITION, &x, sizeof(x));
2178#if defined (CAMERA_s90) || defined (CAMERA_s95) || defined (CAMERA_g12) || defined (CAMERA_a3000)
2179          if (x==0) zoom_status=ZOOM_OPTICAL_MAX; //ERR99: No zoom back from digital to optical zoom possible if set to medium
2180#else
2181          if (x==0) zoom_status=ZOOM_OPTICAL_MEDIUM;
2182#endif
2183
2184     }
2185    }
2186#endif
2187
2188#if CAM_EV_IN_VIDEO
2189    if ((movie_status==VIDEO_RECORD_IN_PROGRESS) && !kbd_is_key_pressed(KEY_SHOOT_HALF)){
2190#if CAM_HAS_ERASE_BUTTON
2191        if (kbd_is_key_clicked(KEY_ERASE)){
2192#else
2193#if !defined (CAMERA_a480)
2194        if (kbd_is_key_clicked(KEY_DISPLAY)){
2195#else
2196        if (kbd_is_key_clicked(KEY_MENU)){
2197#endif
2198#endif
2199            set_ev_video_avail(!get_ev_video_avail());
2200#ifdef CAM_TOUCHSCREEN_UI
2201            redraw_buttons = 1;
2202#endif
2203        }
2204        if (get_ev_video_avail()) {
2205            if (kbd_is_key_clicked(KEY_LEFT)) {
2206                set_ev_video(get_ev_video()-1);
2207            }
2208            if (kbd_is_key_clicked(KEY_RIGHT)){
2209                set_ev_video(get_ev_video()+1);
2210            }
2211        }
2212    }
2213#endif
2214}
2215
2216void gui_draw_debug_vals_osd() {
2217#ifdef OPT_DEBUGGING
2218
2219#if defined(OPT_EXMEM_TESTING)
2220    // Only do memory corruption testing if not recording video
2221    if (!MODE_IS_VIDEO(mode_get()))
2222    {
2223            // If defined the exmem memory is allocated; but not used for CHDK.
2224            // It is filled with a guard value (see wrappers.c) which is checked here
2225        // Any corruption is reported, otherwise 'OK' is displayed on screen (along with the exmem memory start address).
2226            extern void *exmem_start, *exmem_end;
2227            // check exmem allocated memory for corruption
2228            unsigned long* p = (unsigned long*)exmem_start;
2229            unsigned long *f = 0, *l = 0;
2230            long cnt = 0;
2231            while (p < (unsigned long*)exmem_end)
2232            {
2233                    if (p[0] != 0xDEADBEEF)
2234                    {
2235                            l = p;
2236                            if (f == 0) f = p;
2237                            cnt++;
2238                    }
2239                    p++;
2240            }
2241            if (cnt != 0)
2242            {
2243                    sprintf(osd_buf, "s:%8x e:%8x", exmem_start, exmem_end);
2244                    draw_txt_string(2, 12, osd_buf, conf.osd_color);
2245                    sprintf(osd_buf, "f:%8x l:%8x c:%d", f, l, cnt);
2246            }
2247            else
2248            {
2249                    sprintf(osd_buf, "OK 0x%x", exmem_start);
2250            }
2251            draw_txt_string(2, 13, osd_buf, conf.osd_color);
2252            // end of check     
2253    }
2254#endif
2255
2256    // DEBUG: "Show misc. values"
2257    // change ROW to fit values on screen in draw_txt_string(COLUMN, ROW, ...)
2258    // uncomment gui_draw_debug_vals_osd() below if you want debug values always on top
2259    if (conf.debug_misc_vals_show) {
2260        // show value of Memory Address selected with Memory Browser
2261        sprintf(osd_buf, "MEM: %#8x", (void*) (*(int*)conf.mem_view_addr_init));    // show value in Hexadecimal integer
2262        //sprintf(osd_buf, "MEM: %8u", (void*) (*(int*)conf.mem_view_addr_init));    // show value in Decimal integer
2263        draw_txt_string(28,  9, osd_buf, conf.osd_color);
2264
2265        // show Autofocus status (if AF is working)
2266        extern volatile long focus_busy;
2267        sprintf(osd_buf, "FB:  %8u", focus_busy);
2268        draw_txt_string(28, 10, osd_buf, conf.osd_color);
2269
2270        // show Zoom status (if Lens is moving)
2271        extern volatile long zoom_busy;
2272        sprintf(osd_buf, "ZB:  %8u", zoom_busy);
2273        draw_txt_string(28, 11, osd_buf, conf.osd_color);
2274
2275        // show USB-Power status to debug remote / sync
2276        sprintf(osd_buf, "USB: %8u", get_usb_power(1));
2277        draw_txt_string(28, 12, osd_buf, conf.osd_color);
2278
2279        /*
2280        // some cameras missing zoom_status
2281        sprintf(osd_buf, "ZS:  %#8x", zoom_status);
2282        draw_txt_string(28, 13, osd_buf, conf.osd_color);
2283        */
2284
2285        /*
2286        sprintf(osd_buf, "VP:  %#8x", vid_get_viewport_fb_d());
2287        draw_txt_string(28, 14, osd_buf, conf.osd_color);
2288        */
2289
2290        /*
2291        // debug keymap, KEYS_MASKx, SD_READONLY_FLAG, USB_MASK
2292        extern long physw_status[3];
2293        sprintf(osd_buf, "PS1: %#8x", physw_status[0]);
2294        draw_txt_string(28, 10, osd_buf, conf.osd_color);
2295
2296        sprintf(osd_buf, "PS2: %#8x", physw_status[1]);
2297        draw_txt_string(28, 11, osd_buf, conf.osd_color);
2298
2299        sprintf(osd_buf, "PS3: %#8x", physw_status[2]);
2300        draw_txt_string(28, 12, osd_buf, conf.osd_color);
2301        */
2302
2303        /*
2304        long v=get_file_counter();
2305        sprintf(osd_buf, "1:%03d-%04d", (v>>18)&0x3FF, (v>>4)&0x3FFF);
2306        sprintf(osd_buf, "1:%d, %08X", xxxx, eeee);
2307        */
2308    }
2309    {
2310        static char sbuf[100];
2311        int r,i, p, len;
2312        if (conf.debug_display == DEBUG_DISPLAY_PROPS){
2313
2314            for (i=0;i<10;i++){
2315                r = 0;
2316                p = conf.debug_propcase_page*10+i;
2317                get_property_case(p, &r, 4);
2318                sprintf(sbuf, "%3d: %d              ", p, r);
2319                sbuf[20]=0;
2320                draw_string(64,16+16*i,sbuf, conf.osd_color);
2321            }
2322        }
2323
2324        if (conf.debug_display == DEBUG_DISPLAY_PARAMS){
2325            extern long* FlashParamsTable[];
2326            char s[30];
2327            int count;
2328
2329            for (i=0;i<10;i++){
2330                r = 0;
2331                p = conf.debug_propcase_page*10+i;
2332                if (p>=get_flash_params_count()) {
2333                    sprintf(sbuf, "%3d: This parameter does not exists", p);
2334                } else  {
2335                    len=FlashParamsTable[p][1]>>16;
2336                    if ((len==1)||(len==2)||(len==4)){
2337                        get_parameter_data(p, &r, len);
2338                        sprintf(sbuf, "%3d: %30d :%2d ", p, r,len);
2339                    }
2340                    else {
2341                        if (len>=sizeof(s)) count=sizeof(s)-1; else count=len;
2342                        get_parameter_data(p, &s, count);
2343                        s[count]=0;
2344                        sprintf(sbuf, "%3d: %30s :%2d ", p, s,len);
2345                    }
2346                }
2347                draw_string(16,16+16*i,sbuf, conf.osd_color);
2348            }
2349        }
2350    }
2351
2352    if(conf.debug_display == DEBUG_DISPLAY_TASKS) {
2353            gui_debug_draw_tasklist();
2354    }
2355#endif
2356}
2357
2358//-------------------------------------------------------------------
2359// int osd_visible( uint playmode )             // playmode = m&MODE_MASK from gui_draw_osd()
2360//                                                                                      // hide_osd =  0=Don't, 1=In Playback, 2=On Disp Press, 3=Both
2361//-------------------------------------------------------------------
2362int osd_visible(unsigned int playmode)         
2363{
2364        if ( conf.hide_osd == 0 ) return(1) ;
2365       
2366        if( !kbd_is_key_pressed(KEY_SHOOT_HALF))
2367        {       
2368                if (playmode == MODE_REC)
2369                {       
2370                        if ( conf.hide_osd < 2 ) return( 1 ) ;
2371                       
2372#if defined(PARAM_DISPLAY_MODE1) && defined(PARAM_DISPLAY_MODE2)
2373
2374                        short disp_key_mode ;
2375                        if (recreview_hold==0)
2376                        {       
2377                                if ( shooting_get_prop(PROPCASE_DISPLAY_MODE) == 0) return( 1 );                       
2378                        }
2379                        else
2380                        {
2381                                if (conf.show_osd_in_review )
2382                                {
2383                                        get_parameter_data(PARAM_DISPLAY_MODE2, &disp_key_mode, 2);             
2384                                        if (disp_key_mode == 0 ) return( 1 ) ;
2385                                }
2386                        }
2387                }
2388                else
2389                {
2390                        if (conf.hide_osd == 2 )
2391                        {       
2392                                short disp_key_mode ;
2393
2394                                get_parameter_data(PARAM_DISPLAY_MODE1, &disp_key_mode, 2);
2395                                if (disp_key_mode == 1 ) return( 1 ) ;
2396                        }
2397                }
2398        }
2399#else
2400                        if ( shooting_get_prop(PROPCASE_DISPLAY_MODE) == 0) return( 1 );
2401                }
2402        }
2403#endif         
2404
2405        return( 0 ) ;
2406       
2407}
2408
2409//-------------------------------------------------------------------
2410// void gui_draw_osd()
2411//-------------------------------------------------------------------
2412void gui_draw_osd() {
2413    unsigned int m, /*n = 0,*/ mode_photo, mode_video;
2414    coord x;
2415#if CAM_SWIVEL_SCREEN
2416    static int flashlight = 0;
2417#endif
2418    static int pressed = 0;
2419    static int half_disp_press_old=0;
2420    int half_disp_press;
2421    int need_restore = 0;
2422    m = mode_get();
2423
2424// DEBUG: uncomment if you want debug values always on top
2425//gui_draw_debug_vals_osd();
2426
2427#if CAM_SWIVEL_SCREEN
2428    if (conf.flashlight && (m&MODE_SCREEN_OPENED) && (m&MODE_SCREEN_ROTATED) && (gui_mode==GUI_MODE_NONE /* || gui_mode==GUI_MODE_ALT */)) {
2429        draw_filled_rect(0, 0, screen_width-1, screen_height-1, MAKE_COLOR(COLOR_WHITE, COLOR_WHITE));
2430        flashlight = 1;
2431    }
2432    if (flashlight) {
2433        if ((!((m&MODE_SCREEN_OPENED) && (m&MODE_SCREEN_ROTATED))) || (gui_mode!=GUI_MODE_NONE /* && gui_mode!=GUI_MODE_ALT */)) {
2434            flashlight = 0;
2435                        need_restore = 1;
2436        } else {
2437                        return;
2438                }
2439    }
2440#endif
2441
2442    if (kbd_is_key_pressed(KEY_SHOOT_HALF)) {
2443        if (kbd_is_key_pressed(SHORTCUT_TOGGLE_ZEBRA)) {
2444            if (!pressed) {
2445                conf.zebra_draw = !conf.zebra_draw;
2446                if (!conf.zebra_draw) {
2447                                        need_restore = 1;
2448                }
2449                pressed = 1;
2450            }
2451        } else if (kbd_is_key_pressed(SHORTCUT_TOGGLE_HISTO)) {
2452            if (!pressed) {
2453                if (++conf.show_histo>SHOW_HALF) conf.show_histo=0;
2454                if (!conf.show_histo) {
2455                                        need_restore = 1;
2456                }
2457                pressed = 1;
2458            }
2459        } else if (kbd_is_key_pressed(SHORTCUT_TOGGLE_OSD)) {
2460            if (!pressed) {
2461                conf.show_osd = !conf.show_osd;
2462                if (!conf.show_osd) {
2463                                        need_restore = 1;
2464                }
2465                pressed = 1;
2466            }
2467        } else if (kbd_is_key_pressed(SHORTCUT_DISABLE_OVERRIDES)) {
2468             if (!pressed) {
2469                 if (conf.override_disable < 2) conf.override_disable = !conf.override_disable;
2470                 if (!conf.show_osd) {
2471                                        need_restore = 1;
2472                 }
2473                 pressed = 1;
2474             }
2475        } else {
2476            pressed = 0;
2477        }
2478    } else {
2479        pressed = 0;
2480    }
2481
2482        // TODO some of the ifs below should probably use this
2483        mode_video = MODE_IS_VIDEO(m);
2484
2485    mode_photo = (m&MODE_MASK) == MODE_PLAY ||
2486                 !( mode_video ||
2487                                 (m&MODE_SHOOTING_MASK)==MODE_STITCH);
2488
2489    half_disp_press=mode_photo && kbd_is_key_pressed(KEY_SHOOT_HALF) && kbd_is_key_pressed(KEY_DISPLAY);
2490    if (half_disp_press && ! half_disp_press_old)
2491                need_restore = 1;
2492    half_disp_press_old=half_disp_press;
2493
2494        if (need_restore)
2495                draw_restore();
2496
2497    if (half_disp_press)
2498                return;
2499
2500        if (gui_osd_draw_zebra(conf.zebra_draw && gui_mode==GUI_MODE_NONE &&
2501                                                        kbd_is_key_pressed(KEY_SHOOT_HALF) && mode_photo &&
2502                                                        !state_kbd_script_run)) {// no zebra when script running, to save mem
2503                return; // if zebra drawn, we're done
2504        }
2505#if !CAM_SHOW_OSD_IN_SHOOT_MENU
2506      if (!(conf.show_osd && (canon_menu_active==(int)&canon_menu_active-4) && (canon_shoot_menu_active==0)))  return;
2507#else
2508      if (!(conf.show_osd && (canon_menu_active==(int)&canon_menu_active-4) /*&& (canon_shoot_menu_active==0)*/ ))  return;
2509#endif
2510
2511
2512    if ((gui_mode==GUI_MODE_NONE || gui_mode==GUI_MODE_ALT) && (
2513     (kbd_is_key_pressed(KEY_SHOOT_HALF) && ((conf.show_histo==SHOW_HALF)/* || (m&MODE_MASK) == MODE_PLAY*/)) ||
2514     ((conf.show_histo==SHOW_ALWAYS)  &&  !((m&MODE_MASK) == MODE_PLAY) && (recreview_hold==0))
2515    ) &&
2516    (mode_photo || (m&MODE_SHOOTING_MASK)==MODE_STITCH)) {
2517        gui_osd_draw_histo();
2518    }
2519
2520    if ((m&MODE_MASK) == MODE_REC && (recreview_hold==0 || conf.show_osd_in_review) ) {
2521        if (conf.show_grid_lines) {
2522            gui_grid_draw_osd(1);
2523        }
2524        if ((gui_mode==GUI_MODE_NONE || gui_mode==GUI_MODE_ALT) && (((kbd_is_key_pressed(KEY_SHOOT_HALF) || (state_kbd_script_run) || (shooting_get_common_focus_mode())) && (mode_photo || (m&MODE_SHOOTING_MASK)==MODE_STITCH )) || ((mode_video || movie_status > 1) && conf.show_values_in_video) )) {
2525
2526           if (conf.show_dof!=DOF_DONT_SHOW) gui_osd_calc_dof();
2527
2528           if (conf.show_dof==DOF_SHOW_IN_DOF) gui_osd_draw_dof();
2529
2530           if (conf.values_show_real_iso || conf.values_show_market_iso || conf.values_show_ev_seted || conf.values_show_ev_measured || conf.values_show_bv_measured || conf.values_show_bv_seted || conf.values_show_overexposure || conf.values_show_canon_overexposure || conf.values_show_luminance) gui_osd_calc_expo_param();
2531        }
2532        if (conf.show_state) gui_osd_draw_state();
2533        if (conf.save_raw && conf.show_raw_state && !mode_video && (!kbd_is_key_pressed(KEY_SHOOT_HALF))) gui_osd_draw_raw_info();
2534
2535            if ((conf.show_values==SHOW_ALWAYS && mode_photo) || ((mode_video || movie_status > 1)&& conf.show_values_in_video) || ((kbd_is_key_pressed(KEY_SHOOT_HALF) || (recreview_hold==1)) && (conf.show_values==SHOW_HALF)))
2536                   gui_osd_draw_values(1);
2537        else if  (shooting_get_common_focus_mode() && mode_photo && conf.show_values && !(conf.show_dof==DOF_SHOW_IN_DOF) )
2538           gui_osd_draw_values(2);
2539            else if  (conf.show_values==SHOW_HALF)
2540                   gui_osd_draw_values(0);
2541    }
2542
2543    if ( osd_visible(m&MODE_MASK) ) 
2544    {
2545        gui_batt_draw_osd();
2546        gui_space_draw_osd();
2547        gui_usb_draw_osd();
2548        if(conf.show_temp>0) gui_osd_draw_temp();
2549        if (conf.fast_ev && !mode_video && (m&MODE_MASK) == MODE_REC ) gui_osd_draw_ev();
2550    }
2551
2552    if ( conf.show_clock )
2553        {
2554                if ( osd_visible(m&MODE_MASK) || ( kbd_is_key_pressed(KEY_SHOOT_HALF) && conf.clock_halfpress==0) ) gui_osd_draw_clock(0,0,0);
2555                else if ( kbd_is_key_pressed(KEY_SHOOT_HALF) && conf.clock_halfpress==1 ) gui_osd_draw_seconds();
2556        }
2557
2558    if ( conf.show_movie_time > 0 && (mode_video || movie_status > 1)) gui_osd_draw_movie_time_left();
2559#if CAM_DRAW_EXPOSITION
2560    if (gui_mode==GUI_MODE_NONE && kbd_is_key_pressed(KEY_SHOOT_HALF) && ((m&MODE_MASK)==MODE_REC) && ((m&MODE_SHOOTING_MASK))!=MODE_VIDEO_STD && (m&MODE_SHOOTING_MASK)!=MODE_VIDEO_COMPACT) {
2561     strcpy(osd_buf,shooting_get_tv_str());
2562     strcat(osd_buf,"\"  F");
2563     strcat(osd_buf,shooting_get_av_str());
2564     draw_txt_string(22-strlen(osd_buf)/2, 14, osd_buf, conf.osd_color);
2565    }
2566#endif
2567
2568#if CAM_EV_IN_VIDEO
2569    if (movie_status==VIDEO_RECORD_IN_PROGRESS) gui_osd_draw_ev_video(get_ev_video_avail());
2570#endif
2571
2572        gui_draw_debug_vals_osd();
2573
2574#ifdef OPT_UBASIC
2575    if (ubasic_error){
2576        const char *msg;
2577        if (ubasic_error >= UBASIC_E_ENDMARK) {
2578            msg = ubasic_errstrings[UBASIC_E_UNKNOWN_ERROR];
2579        } else {
2580            msg = ubasic_errstrings[ubasic_error];
2581        }
2582        sprintf(osd_buf, "uBASIC:%d %s ", ubasic_linenumber(), msg);
2583        draw_txt_string(0, 0, osd_buf, MAKE_COLOR(COLOR_RED, COLOR_YELLOW));
2584    }
2585#endif
2586}
2587
2588#ifndef OPTIONS_AUTOSAVE
2589//-------------------------------------------------------------------
2590void gui_menuproc_save(int arg)
2591{
2592    conf_save();
2593}
2594#endif
2595
2596//-------------------------------------------------------------------
2597static void gui_menuproc_reset_selected(unsigned int btn) {
2598    if (btn==MBOX_BTN_YES)
2599        conf_load_defaults();
2600}
2601
2602void gui_menuproc_reset(int arg)
2603{
2604    gui_mbox_init(LANG_MSG_RESET_OPTIONS_TITLE,
2605                  LANG_MSG_RESET_OPTIONS_TEXT,
2606                  MBOX_FUNC_RESTORE|MBOX_TEXT_CENTER|MBOX_BTN_YES_NO|MBOX_DEF_BTN2, gui_menuproc_reset_selected);
2607}
2608
2609//-------------------------------------------------------------------
2610void gui_show_build_info(int arg) {
2611    static char buf[192];
2612    static char comp[64];
2613
2614#ifdef __GNUC__
2615# ifndef __GNUC_PATCHLEVEL__
2616# define __GNUC_PATCHLEVEL 0
2617# endif
2618    sprintf(comp, "GCC %d.%d.%d", __GNUC__ ,__GNUC_MINOR__,__GNUC_PATCHLEVEL__ );
2619#else
2620    sprintf(comp, "UNKNOWN" );
2621#endif
2622    sprintf(buf, lang_str(LANG_MSG_BUILD_INFO_TEXT), HDK_VERSION, BUILD_NUMBER, __DATE__, __TIME__, PLATFORM, PLATFORMSUB, comp);
2623gui_mbox_init(LANG_MSG_BUILD_INFO_TITLE, (int)buf, MBOX_FUNC_RESTORE|MBOX_TEXT_LEFT, NULL);
2624}
2625
2626//-------------------------------------------------------------------
2627void gui_show_memory_info(int arg) {
2628    static char buf[96];    // buffer size was 64, size increased for none english language
2629
2630    sprintf(buf, lang_str(LANG_MSG_MEMORY_INFO_TEXT), core_get_free_memory(), MEMISOSIZE, &_start, &_end);
2631    gui_mbox_init(LANG_MSG_MEMORY_INFO_TITLE, (int)buf, MBOX_FUNC_RESTORE|MBOX_TEXT_CENTER, NULL);
2632}
2633
2634//-------------------------------------------------------------------
2635void gui_menu_run_fltmodule(int arg) {
2636    module_run((char*)arg, 0, 0,0, UNLOAD_IF_ERR);
2637}
2638
2639//-------------------------------------------------------------------
2640void gui_draw_splash(char* logo, int logo_size) {
2641    coord w, h, x, y;
2642    static const char *text[] = {
2643        "CHDK Firmware '" HDK_VERSION " " BUILD_NUMBER "'" ,
2644        "Build: " __DATE__ " " __TIME__ ,
2645        "Camera: " PLATFORM " - " PLATFORMSUB };
2646    int i, l;
2647    color cl = MAKE_COLOR(COLOR_RED, COLOR_WHITE);
2648
2649    gui_splash_mode = (mode_get()&MODE_MASK);
2650
2651    h=sizeof(text)/sizeof(text[0])*FONT_HEIGHT+8;
2652    w=0;
2653    for (i=0; i<sizeof(text)/sizeof(text[0]); ++i) {
2654        l=strlen(text[i]);
2655        if (l>w) w=l;
2656    }
2657    w=w*FONT_WIDTH+10;
2658
2659    x = (screen_width-w)>>1; y = ((screen_height-h)>>1) + 20;
2660    draw_filled_round_rect(x, y, x+w, y+h, MAKE_COLOR(COLOR_RED, COLOR_RED));
2661    for (i=0; i<sizeof(text)/sizeof(text[0]); ++i) {
2662        draw_string(x+((w-strlen(text[i])*FONT_WIDTH)>>1), y+i*FONT_HEIGHT+4, text[i], cl);
2663    }
2664    if(logo){
2665      int pos;
2666      int mx=0;
2667      int my=0;
2668      int offset_x = (screen_width-150)>>1;
2669      int offset_y = ((screen_height-84)>>1) - 42;
2670      const color color_lookup[8] = {COLOR_BLACK,
2671                                                                        COLOR_SPLASH_RED/*0x2E redish*/,
2672                                                                        COLOR_RED,
2673                                                                        COLOR_GREY /*0x3D*/,
2674                                                                        COLOR_SPLASH_GREY /*0x1F*/,
2675                                                                        COLOR_SPLASH_PINK /*0x21 pinkish*/,
2676                                                                        COLOR_TRANSPARENT /*0x00*/,
2677                                                                        COLOR_WHITE /*0x11*/};
2678      for(pos=0; pos<logo_size; pos++){
2679          char data = logo[pos];
2680          color c = color_lookup[(data>>5) & 0x07];
2681          for(i=0; i<(data&0x1F)+1; i++){
2682              if (c!=0x00){
2683                  draw_pixel(offset_x+mx,offset_y+my,c);
2684              }
2685              if (mx==149){
2686                  mx=0;
2687                  my++;
2688              }else{
2689                  mx++;
2690              }
2691          }
2692      }
2693    }
2694}
2695
2696//-------------------------------------------------------------------
2697void gui_draw_fselect(int arg) {
2698    module_fselect_init(LANG_STR_FILE_BROWSER, "A", "A", NULL);
2699}
2700
2701//-------------------------------------------------------------------
2702static void gui_grid_lines_load_selected(const char *fn) {
2703    if (fn)
2704        grid_lines_load(fn);
2705}
2706void gui_grid_lines_load(int arg) {
2707    module_fselect_init(LANG_STR_SELECT_GRID_FILE, conf.grid_lines_file, "A/CHDK/GRIDS", gui_grid_lines_load_selected);
2708}
2709
2710//-------------------------------------------------------------------
2711void gui_draw_osd_le(int arg) {
2712    gui_set_mode(GUI_MODE_OSD);
2713    gui_osd_init();
2714}
2715
2716//-------------------------------------------------------------------
2717#ifdef OPT_TEXTREADER
2718static void gui_draw_read_selected(const char *fn) {
2719    if (fn) {
2720        if (!rbf_load(conf.reader_rbf_file))
2721            rbf_load_from_8x16(current_font);
2722        rbf_set_codepage(conf.reader_codepage);
2723
2724                unsigned int argv[] ={ (unsigned int)fn };
2725                module_run("txtread.flt", 0, sizeof(argv)/sizeof(argv[0]), argv, UNLOAD_IF_ERR);
2726    }
2727}
2728
2729void gui_draw_read(int arg) {
2730    module_fselect_init_w_mode(LANG_STR_SELECT_TEXT_FILE, conf.reader_file, "A/CHDK/BOOKS", gui_draw_read_selected, 1);
2731    void gui_fselect_set_key_redraw(int n);
2732    //gui_fselect_set_key_redraw(1);    @tsv
2733}
2734
2735void gui_draw_read_last(int arg) {
2736    struct stat st;
2737    if (stat(conf.reader_file,&st) == 0) {
2738        gui_draw_read_selected(conf.reader_file);
2739    } else {
2740        gui_draw_read(arg);
2741    }
2742}
2743#endif
2744
2745//-------------------------------------------------------------------
2746void gui_menuproc_mkbootdisk(int arg) {
2747    mark_filesystem_bootable();
2748    gui_mbox_init(LANG_INFORMATION, LANG_CONSOLE_TEXT_FINISHED, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
2749}
2750
2751#ifdef OPT_EDGEOVERLAY
2752static void gui_load_edge_selected( const char* fn ) {
2753    if( fn && module_edgeovr_load())
2754                load_edge_overlay(fn);
2755}
2756
2757void gui_menuproc_edge_save(int arg) {
2758        if ( module_edgeovr_load() )
2759        save_edge_overlay();
2760}
2761
2762void gui_menuproc_edge_load(int arg) {
2763    module_fselect_init(LANG_MENU_EDGE_LOAD, EDGE_SAVE_DIR, EDGE_SAVE_DIR, gui_load_edge_selected);
2764}
2765#endif
2766
2767//-------------------------------------------------------------------
2768#ifdef OPT_TEXTREADER
2769static void gui_draw_rbf_selected(const char *fn) {
2770    if (fn) {
2771        strcpy(conf.reader_rbf_file, fn);
2772    }
2773}
2774void gui_draw_load_rbf(int arg) {
2775    module_fselect_init(LANG_STR_SELECT_FONT_FILE, conf.reader_rbf_file, "A/CHDK/FONTS", gui_draw_rbf_selected);
2776}
2777#endif
2778//-------------------------------------------------------------------
2779static void gui_draw_menu_rbf_selected(const char *fn) {
2780    if (fn) {
2781        strcpy(conf.menu_rbf_file, fn);
2782        if (!rbf_load(conf.menu_rbf_file))
2783            rbf_load_from_8x16(current_font);
2784        rbf_set_codepage(FONT_CP_WIN);
2785        gui_menu_init(NULL);
2786    }
2787}
2788void gui_draw_load_menu_rbf(int arg) {
2789    module_fselect_init(LANG_STR_SELECT_FONT_FILE, conf.menu_rbf_file, "A/CHDK/FONTS", gui_draw_menu_rbf_selected);
2790}
2791
2792//-------------------------------------------------------------------
2793static void gui_draw_symbol_rbf_selected(const char *fn) {
2794    if (fn) {
2795        strcpy(conf.menu_symbol_rbf_file, fn);
2796        if(!rbf_load_symbol(conf.menu_symbol_rbf_file)) conf.menu_symbol_enable=0;              //AKA
2797        gui_menu_init(NULL);
2798    }
2799}
2800void gui_draw_load_symbol_rbf(int arg) {
2801    module_fselect_init(LANG_STR_SELECT_SYMBOL_FILE, conf.menu_symbol_rbf_file, "A/CHDK/SYMBOLS", gui_draw_symbol_rbf_selected);
2802}
2803
2804//-------------------------------------------------------------------
2805static void gui_draw_lang_selected(const char *fn) {
2806    if (fn) {
2807        strcpy(conf.lang_file, fn);
2808        lang_load_from_file(conf.lang_file);
2809        gui_menu_init(NULL);
2810    }
2811}
2812void gui_draw_load_lang(int arg) {
2813    module_fselect_init(LANG_STR_SELECT_LANG_FILE, conf.lang_file, "A/CHDK/LANG", gui_draw_lang_selected);
2814}
2815
2816CMenuItem* find_mnu(CMenu *curr_menu, int itemid )
2817{
2818        int gui_menu_curr_item;
2819        CMenuItem* rv=0;
2820
2821        if ( itemid==0 )
2822                return 0;               
2823
2824        gui_menu_curr_item = 0;
2825        while(curr_menu->menu[gui_menu_curr_item].text) {
2826                if ( lang_strhash31(curr_menu->menu[gui_menu_curr_item].text) == itemid){
2827                        return (CMenuItem*) &(curr_menu->menu[gui_menu_curr_item]);
2828                }
2829                if ((curr_menu->menu[gui_menu_curr_item].type & MENUITEM_MASK) == MENUITEM_SUBMENU)
2830                        if (curr_menu->menu[gui_menu_curr_item].text != LANG_MENU_USER_MENU) {
2831                                rv = find_mnu((CMenu*)(curr_menu->menu[gui_menu_curr_item].value), itemid);
2832                                if ( rv )
2833                                        return rv;
2834                        }
2835                gui_menu_curr_item++;
2836        }
2837        return 0;
2838}
2839
2840void user_menu_save() {
2841    int x;
2842        for (x=0; x<USER_MENU_ITEMS; x++) {
2843                /*
2844                 * First entry in user_submenu_items is reserved for the "Main Menu"
2845                 * conf.user_menu_vars only traks/saves the real user entries.
2846                 */
2847                conf.user_menu_vars[x] = lang_strhash31(user_submenu_items[x+1].text);
2848        }
2849}
2850
2851void user_menu_restore() {
2852    int x;
2853        CMenuItem* item=0;
2854
2855        for (x=0; x<USER_MENU_ITEMS; x++) {
2856                /*
2857                 * First entry in user_submenu_items is reserved for the "Main Menu"
2858                 * conf.user_menu_vars only traks/saves the real user entries.
2859                 */
2860                 item = find_mnu(&root_menu, conf.user_menu_vars[x]);
2861                 if ( item )
2862                        user_submenu_items[x+1] = *item;
2863        }
2864}
2865
2866#ifdef OPT_DEBUGGING
2867
2868void gui_compare_props(int arg)
2869{
2870        #define NUM_PROPS 512
2871        // never freed, but not allocated unless prop compare is used once
2872        static int *props = NULL;
2873        char buf[64];
2874        int i;
2875        int p;
2876        int c;
2877
2878        if( props )
2879        { // we have previous data set! do a comparison
2880                c = 0;
2881                for( i = 0; i < NUM_PROPS; ++i )
2882                {
2883                        p = shooting_get_prop(i);
2884                        if( props[i] != p )
2885                        {
2886                                ++c;
2887                                sprintf(buf,"%4d is %8d was %8d",i,p,props[i]);
2888                                draw_string(16,16*c,buf,MAKE_COLOR(COLOR_BLACK,COLOR_YELLOW));
2889                        }
2890                        props[i] = p;
2891                        if( c == 12 )
2892                        {
2893                                ++c;
2894                                sprintf(buf,"%s","Waiting 15 Seconds");
2895                                draw_string(16,16*c,buf,MAKE_COLOR(COLOR_BLACK,COLOR_YELLOW));
2896                                msleep(15000);
2897                                c = 0;
2898                        }
2899                }
2900                ++c;
2901                sprintf(buf,"%s","Press <ALT> to leave");
2902                draw_string(16,16*c,buf,MAKE_COLOR(COLOR_BLACK,COLOR_YELLOW));
2903        }
2904        else
2905        {
2906        // no previous data was set so we save the data initially
2907                props = (int *)malloc(NUM_PROPS*sizeof(int));
2908                if(props) {
2909                        for( i = 0; i < NUM_PROPS; ++i )
2910                        {
2911                                props[i] = shooting_get_prop(i);
2912                        }
2913                }
2914        }
2915}
2916
2917// Save camera romlog to A/ROMLOG.LOG file
2918void save_romlog(int arg)
2919{
2920    extern unsigned _ExecuteEventProcedure(const char *name,...);
2921
2922    struct stat st;
2923    if (stat("A/ROMLOG.LOG",&st)    == 0) remove("A/ROMLOG.LOG");
2924    if (stat("A/RomLogErr.txt",&st) == 0) remove("A/RomLogErr.txt");
2925
2926    unsigned args[3];
2927    args[0] = (unsigned)"SystemEventInit";
2928    if (call_func_ptr(_ExecuteEventProcedure,args,1) == -1)
2929    {
2930        args[0] = (unsigned)"System.Create";
2931        if (call_func_ptr(_ExecuteEventProcedure,args,1) == -1)
2932        {
2933            gui_mbox_init(LANG_ERROR, LANG_SAVE_ROMLOG_INIT_ERROR, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
2934            return;
2935        }
2936    }
2937
2938    args[0] = (unsigned)"GetLogToFile";
2939    args[1] = (unsigned)"A/ROMLOG.LOG";
2940    args[2] = 1;
2941    if (call_func_ptr(_ExecuteEventProcedure,args,3) == -1)
2942    {
2943        gui_mbox_init(LANG_ERROR, LANG_SAVE_ROMLOG_FAIL, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
2944    }
2945    else
2946    {
2947        gui_mbox_init(LANG_INFORMATION, LANG_SAVE_ROMLOG_OK, MBOX_BTN_OK|MBOX_TEXT_CENTER, NULL);
2948    }
2949}
2950
2951#endif
Note: See TracBrowser for help on using the repository browser.