1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2006 Jonathan Gordon
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
18 ****************************************************************************/
21 #include "oldmenuapi.h"
23 #if PLUGIN_BUFFER_SIZE > 0x45000
24 #define MAX_CHARS 0x40000 /* 128 kiB */
26 #define MAX_CHARS 0x6000 /* 24 kiB */
28 #define MAX_LINE_LEN 2048
30 static struct plugin_api
* rb
;
32 static char buffer
[MAX_CHARS
];
34 static int char_count
= 0;
35 static int line_count
= 0;
36 static int last_action_line
= 0;
37 static int last_char_index
= 0;
39 #define ACTION_INSERT 0
41 #define ACTION_REMOVE 2
42 #define ACTION_UPDATE 3
43 #define ACTION_CONCAT 4
45 int _do_action(int action
, char* str
, int line
);
46 #ifndef HAVE_ADJUSTABLE_CPU_FREQ
47 #define do_action _do_action
49 int do_action(int action
, char* str
, int line
)
53 r
= _do_action(action
,str
,line
);
59 int _do_action(int action
, char* str
, int line
)
63 if (line
>=last_action_line
)
68 while (i
<line
&& i
<line_count
)
70 c
+= rb
->strlen(&buffer
[c
])+1;
76 len
= rb
->strlen(str
)+1;
77 if ( char_count
+ len
> MAX_CHARS
)
79 rb
->memmove(&buffer
[c
+len
],&buffer
[c
],char_count
);
80 rb
->strcpy(&buffer
[c
],str
);
85 if (line
> line_count
)
92 if (line
> line_count
)
94 len
= rb
->strlen(&buffer
[c
])+1;
96 rb
->memmove(&buffer
[c
],&buffer
[c
+len
],char_count
);
100 if (line
> line_count
)
102 len
= rb
->strlen(&buffer
[c
])+1;
103 rb
->memmove(&buffer
[c
+rb
->strlen(str
)+1],&buffer
[c
+len
],char_count
);
104 rb
->strcpy(&buffer
[c
],str
);
105 char_count
+= rb
->strlen(str
)+1-len
;
108 if (line
> line_count
)
110 rb
->memmove(&buffer
[c
-1],&buffer
[c
],char_count
);
115 last_action_line
= i
;
119 char *list_get_name_cb(int selected_item
,void* data
,char* buf
)
121 char *b
= &buffer
[do_action(ACTION_GET
,0,selected_item
)];
123 if (rb
->strlen(b
) >= MAX_PATH
)
125 char t
= b
[MAX_PATH
-10];
126 b
[MAX_PATH
-10] = '\0';
127 rb
->snprintf(buf
,MAX_PATH
,"%s ...",b
);
130 else rb
->strcpy(buf
,b
);
133 char filename
[MAX_PATH
];
134 int get_eol_string(char* fn
)
142 fd
= rb
->PREFIX(open(fn
,O_RDONLY
));
148 if (!rb
->read(fd
,&t
,1))
150 rb
->strcpy(eol
,"\n");
155 if (rb
->read(fd
,&t
,1) && t
=='\n')
156 rb
->strcpy(eol
,"\r\n");
157 else rb
->strcpy(eol
,"\r");
161 rb
->strcpy(eol
,"\n");
168 void save_changes(int overwrite
)
173 if (!filename
[0] || !overwrite
)
175 rb
->strcpy(filename
,"/");
176 rb
->kbd_input(filename
,MAX_PATH
);
179 fd
= rb
->open(filename
,O_WRONLY
|O_CREAT
|O_TRUNC
);
182 rb
->splash(HZ
*2, "Changes NOT saved");
187 /* current directory may have changed */
188 rb
->reload_directory();
190 rb
->lcd_clear_display();
191 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
194 for (i
=0;i
<line_count
;i
++)
196 rb
->fdprintf(fd
,"%s%s",&buffer
[do_action(ACTION_GET
,0,i
)],eol
);
198 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
204 void setup_lists(struct gui_synclist
*lists
, int sel
)
206 rb
->gui_synclist_init(lists
,list_get_name_cb
,0, false, 1);
207 rb
->gui_synclist_set_icon_callback(lists
,NULL
);
208 rb
->gui_synclist_set_nb_items(lists
,line_count
);
209 rb
->gui_synclist_limit_scroll(lists
,true);
210 rb
->gui_synclist_select_item(lists
, sel
);
211 rb
->gui_synclist_draw(lists
);
218 int do_item_menu(int cur_sel
, char* copy_buffer
)
221 static const struct menu_item items
[] = {
225 { "Insert Above", NULL
},
226 { "Insert Below", NULL
},
228 { "Cat To Above",NULL
},
232 m
= menu_init(rb
, items
, sizeof(items
) / sizeof(*items
),
233 NULL
, NULL
, NULL
, NULL
);
235 switch (menu_show(m
))
238 rb
->strcpy(copy_buffer
,&buffer
[do_action(ACTION_GET
,0,cur_sel
)]);
239 do_action(ACTION_REMOVE
,0,cur_sel
);
240 ret
= MENU_RET_UPDATE
;
243 rb
->strcpy(copy_buffer
,&buffer
[do_action(ACTION_GET
,0,cur_sel
)]);
244 ret
= MENU_RET_NO_UPDATE
;
247 ret
= MENU_RET_NO_UPDATE
;
250 case 3: /* insert above */
251 if (!rb
->kbd_input(copy_buffer
,MAX_LINE_LEN
))
253 do_action(ACTION_INSERT
,copy_buffer
,cur_sel
);
255 ret
= MENU_RET_UPDATE
;
258 case 4: /* insert below */
259 if (!rb
->kbd_input(copy_buffer
,MAX_LINE_LEN
))
261 do_action(ACTION_INSERT
,copy_buffer
,cur_sel
+1);
263 ret
= MENU_RET_UPDATE
;
267 ret
= MENU_RET_NO_UPDATE
;
269 case 6: /* cat to above */
272 do_action(ACTION_CONCAT
,0,cur_sel
);
273 ret
= MENU_RET_UPDATE
;
280 ret
= MENU_RET_NO_UPDATE
;
287 #ifdef HAVE_LCD_COLOR
288 /* in misc.h but no need to polute the api */
289 #define toupper(c) (((c >= 'a') && (c <= 'z'))?c+'A':c)
290 #define isxdigit(c) ((c>='a' && c<= 'f') || (c>='A' && c<= 'F') \
291 || (c>='0' && c<= '9'))
292 #define hex2dec(c) (((c) >= '0' && ((c) <= '9')) ? (toupper(c)) - '0' : \
293 (toupper(c)) - 'A' + 10)
294 int hex_to_rgb(const char* hex
)
297 int red
, green
, blue
;
299 if (rb
->strlen(hex
) == 6) {
300 for (i
=0; i
< 6; i
++ ) {
301 if (!isxdigit(hex
[i
])) {
308 red
= (hex2dec(hex
[0]) << 4) | hex2dec(hex
[1]);
309 green
= (hex2dec(hex
[2]) << 4) | hex2dec(hex
[3]);
310 blue
= (hex2dec(hex
[4]) << 4) | hex2dec(hex
[5]);
311 return LCD_RGBPACK(red
,green
,blue
);
317 #endif /* HAVE_LCD_COLOR */
319 /* this is the plugin entry point */
320 enum plugin_status
plugin_start(struct plugin_api
* api
, void* parameter
)
323 static char temp_line
[MAX_LINE_LEN
];
325 struct gui_synclist lists
;
328 bool changed
= false;
330 static char copy_buffer
[MAX_LINE_LEN
];
331 bool prev_show_statusbar
;
332 #ifdef HAVE_LCD_COLOR
333 bool edit_icons_file
= false;
339 prev_show_statusbar
= rb
->global_settings
->statusbar
;
340 rb
->global_settings
->statusbar
= false;
342 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
347 #ifdef HAVE_LCD_COLOR
350 rb
->strcpy(filename
,(char*)parameter
);
351 if (!get_eol_string(filename
))
353 rb
->strcpy(eol
,"\n");
355 fd
= rb
->open(filename
,O_RDONLY
);
358 rb
->splash(HZ
*2,"Couldnt open file: %s",(char*)parameter
);
361 #ifdef HAVE_LCD_COLOR
362 c
= rb
->strchr(filename
, '.');
363 if (c
&& rb
->strcmp(c
, ".icons"))
364 edit_icons_file
= true;
366 /* read in the file */
367 while (rb
->read_line(fd
,temp_line
,MAX_LINE_LEN
))
369 if (!do_action(ACTION_INSERT
,temp_line
,line_count
))
371 rb
->splash(HZ
*2,"Error reading file: %s",(char*)parameter
);
381 rb
->strcpy(eol
,"\n");
383 #ifdef HAVE_ADJUSTABLE_CPU_FREQ
386 /* now dump it in the list */
387 setup_lists(&lists
,0);
391 rb
->gui_synclist_draw(&lists
);
392 cur_sel
= rb
->gui_synclist_get_sel_pos(&lists
);
393 button
= rb
->get_action(CONTEXT_LIST
,TIMEOUT_BLOCK
);
394 if (rb
->gui_synclist_do_button(&lists
,button
,LIST_WRAP_UNLESS_HELD
))
400 bool edit_text
= true;
401 #ifdef HAVE_LCD_COLOR
405 rb
->strcpy(temp_line
,&buffer
[do_action(ACTION_GET
,0,cur_sel
)]);
406 #ifdef HAVE_LCD_COLOR
409 char *name
= temp_line
, *value
= NULL
;
410 char extension
[MAX_LINE_LEN
];
411 rb
->settings_parseline(temp_line
, &name
, &value
);
414 MENUITEM_STRINGLIST(menu
, "Edit What?", NULL
,
415 "Extension", "Color",);
416 switch (rb
->do_menu(&menu
, NULL
))
424 color
= hex_to_rgb(value
);
426 rb
->strcpy(extension
, name
);
427 rb
->set_color(rb
->screens
[SCREEN_MAIN
], name
, &color
, -1);
428 rb
->snprintf(temp_line
, MAX_LINE_LEN
, "%s: %02X%02X%02X",
429 extension
, RGB_UNPACK_RED(color
),
430 RGB_UNPACK_GREEN(color
),
431 RGB_UNPACK_BLUE(color
));
434 do_action(ACTION_UPDATE
,temp_line
,cur_sel
);
436 else do_action(ACTION_INSERT
,temp_line
,cur_sel
);
443 if (edit_text
&&!rb
->kbd_input(temp_line
,MAX_LINE_LEN
))
447 do_action(ACTION_UPDATE
,temp_line
,cur_sel
);
449 else do_action(ACTION_INSERT
,temp_line
,cur_sel
);
454 #ifdef TEXT_EDITOR_DELETE
455 case TEXT_EDITOR_DELETE
:
456 #ifdef TEXT_EDITOR_DELETE_PRE
457 if (last_button
!= TEXT_EDITOR_DELETE_PRE
)
460 if (!line_count
) break;
461 rb
->strcpy(copy_buffer
,&buffer
[do_action(ACTION_GET
,0,cur_sel
)]);
462 do_action(ACTION_REMOVE
,0,cur_sel
);
466 case ACTION_STD_MENU
:
467 { /* do the item menu */
468 switch (do_item_menu(cur_sel
, copy_buffer
))
474 case MENU_RET_UPDATE
:
477 case MENU_RET_NO_UPDATE
:
482 case ACTION_STD_CANCEL
:
488 static const struct menu_item items
[] = {
491 { "Save Changes", NULL
},
492 { "Save As...", NULL
},
494 { "Save and Exit", NULL
},
495 { "Ignore Changes and Exit", NULL
},
498 m
= menu_init(rb
, items
, sizeof(items
) / sizeof(*items
),
499 NULL
, NULL
, NULL
, NULL
);
507 case 2: //save to disk
529 rb
->gui_synclist_set_nb_items(&lists
,line_count
);
531 rb
->global_settings
->statusbar
= prev_show_statusbar
;