summaryrefslogtreecommitdiff
path: root/apps/gui
diff options
context:
space:
mode:
authorMichael Sevakis <jethead71@rockbox.org>2006-10-11 20:34:25 +0000
committerMichael Sevakis <jethead71@rockbox.org>2006-10-11 20:34:25 +0000
commitcc66aea55d5ed6298d8b8cc724b5fd7d9073e2db (patch)
tree1bec795a0a2c879d17ac43d69a2e9e12bf5e0f5b /apps/gui
parent504dae291c73d394a5103074b71d0c170138c10e (diff)
downloadrockbox-cc66aea55d5ed6298d8b8cc724b5fd7d9073e2db.tar.gz
rockbox-cc66aea55d5ed6298d8b8cc724b5fd7d9073e2db.zip
Made color picker work on x5 remote and display nicely when using backdrops. Also tweaked the appearance in general. Keymap still does not entirely function however (no inc/dec yet).
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@11193 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/gui')
-rw-r--r--apps/gui/color_picker.c386
1 files changed, 273 insertions, 113 deletions
diff --git a/apps/gui/color_picker.c b/apps/gui/color_picker.c
index 1217fcd08c..06653976a6 100644
--- a/apps/gui/color_picker.c
+++ b/apps/gui/color_picker.c
@@ -23,6 +23,7 @@
23#include "kernel.h" 23#include "kernel.h"
24#include "system.h" 24#include "system.h"
25#include "screen_access.h" 25#include "screen_access.h"
26#include "font.h"
26#include "debug.h" 27#include "debug.h"
27#include "misc.h" 28#include "misc.h"
28#include "settings.h" 29#include "settings.h"
@@ -31,115 +32,291 @@
31#include "splash.h" 32#include "splash.h"
32#include "action.h" 33#include "action.h"
33 34
34#define TEXT_MARGIN display->char_width+2 35/* structure for color info */
35#define SLIDER_START 20 36struct rgb_pick
37{
38 unsigned color; /* native color value */
39 union
40 {
41 unsigned char rgb_val[6]; /* access to components as array */
42 struct
43 {
44 unsigned char r; /* native red value */
45 unsigned char g; /* native green value */
46 unsigned char b; /* native blue value */
47 unsigned char red; /* 8 bit red value */
48 unsigned char green; /* 8 bit green value */
49 unsigned char blue; /* 8 bit blue value */
50 } __attribute__ ((__packed__)); /* assume byte packing */
51 };
52};
53
54/* maximum values for components */
55static const unsigned char max_val[3] =
56{
57 LCD_MAX_RED,
58 LCD_MAX_GREEN,
59 LCD_MAX_BLUE
60};
61
62/* list of primary colors */
63static const unsigned prim_rgb[3] =
64{
65 LCD_RGBPACK(255, 0, 0),
66 LCD_RGBPACK(0, 255, 0),
67 LCD_RGBPACK(0, 0 ,255),
68};
69
70/* Unpacks the color value into native rgb values and 24 bit rgb values */
71static void unpack_rgb(struct rgb_pick *rgb)
72{
73 unsigned color = rgb->color;
74#if LCD_PIXELFORMAT == RGB565SWAPPED
75 swap16(color);
76#endif
77 rgb->r = (color & 0xf800) >> 11;
78 rgb->g = (color & 0x07e0) >> 5;
79 rgb->b = (color & 0x001f);
80 rgb->red = _RGB_UNPACK_RED(color);
81 rgb->green = _RGB_UNPACK_GREEN(color);
82 rgb->blue = _RGB_UNPACK_BLUE(color);
83}
36 84
37static const int max_val[3] = {LCD_MAX_RED,LCD_MAX_GREEN,LCD_MAX_BLUE}; 85/* Packs the native rgb colors into a color value */
86static void pack_rgb(struct rgb_pick *rgb)
87{
88 unsigned color = (rgb->r & 0x1f) << 11 |
89 (rgb->g & 0x3f) << 5 |
90 (rgb->b & 0x1f);
91#if LCD_PIXELFORMAT == RGB565SWAPPED
92 swap16(color);
93#endif
94 rgb->color = color;
95}
96
97/* Returns LCD_BLACK if the color is above a threshold brightness
98 else return LCD_WHITE */
99static inline unsigned get_black_or_white(const struct rgb_pick *rgb)
100{
101 return (4*rgb->r + 5*rgb->g + 2*rgb->b) >= 256 ?
102 LCD_BLACK : LCD_WHITE;
103}
104
105#define MARGIN_LEFT 2 /* Left margin of screen */
106#define MARGIN_TOP 4 /* Top margin of screen */
107#define MARGIN_RIGHT 2 /* Right margin of screen */
108#define MARGIN_BOTTOM 4 /* Bottom margin of screen */
109#define SLIDER_MARGIN_LEFT 2 /* Gap to left of sliders */
110#define SLIDER_MARGIN_RIGHT 2 /* Gap to right of sliders */
111#define TITLE_MARGIN_BOTTOM 4 /* Space below title bar */
112#define SELECTOR_LR_MARGIN 1 /* Margin between ">" and text */
113#define SELECTOR_TB_MARGIN 1 /* Margin on top and bottom of selector */
114#define SWATCH_TOP_MARGIN 4 /* Space between last slider and swatch */
115
116/* dunno why lcd_set_drawinfo should be left out of struct screen */
117static void set_drawinfo(struct screen *display, int mode,
118 unsigned foreground, unsigned background)
119{
120 display->set_drawmode(mode);
121 if (display->depth > 1)
122 {
123 display->set_foreground(foreground);
124 display->set_background(background);
125 }
126}
38 127
39static void draw_screen(struct screen *display, char *title, 128static void draw_screen(struct screen *display, char *title,
40 int *rgb_val, int color, int row) 129 struct rgb_pick *rgb, int row)
41{ 130{
42 int i; 131 unsigned text_color = LCD_BLACK;
43 char *textrgb = str(LANG_COLOR_RGB_LABELS), rgb_dummy[2] = {0,0}; 132 unsigned background_color = LCD_WHITE;
44 int text_top; 133 char buf[32];
45 int text_centre, bg_col; 134 int i, x, y;
46 char buf[32]; 135 int text_top;
47 int slider_width = (display->width-SLIDER_START-(display->char_width*5)); 136 int slider_left, slider_width;
48 int background_color = global_settings.bg_color; 137 bool display_three_rows;
49 int text_color = global_settings.fg_color; 138 int max_label_width;
50 bool display_three_rows = (display->height/6) > display->char_height;
51 139
52 display->clear_display(); 140 display->clear_display();
53 141
54 if (display->depth > 1) { 142 if (display->depth > 1)
55 display->set_foreground(text_color); 143 {
144 text_color = display->get_foreground();
145 background_color = display->get_background();
56 } 146 }
57 147
58 i = display->getstringsize(title,0,0); 148 /* Find out if there's enought room for three slider or just
59 display->putsxy((display->width-i)/2,6,title ); 149 enought to display the selected slider */
150 display_three_rows = display->height >= display->char_height*4 +
151 MARGIN_TOP +
152 TITLE_MARGIN_BOTTOM +
153 MARGIN_BOTTOM;
60 154
61 text_top = display->char_height*2; 155 /* Figure out widest label character in case they vary */
62 bg_col = background_color; 156 for (i = 0, max_label_width = 0; i < 3; i++)
63 for (i=0; i<3 ;i++)
64 { 157 {
158 buf[0] = str(LANG_COLOR_RGB_LABELS)[i];
159 buf[1] = '\0';
160 x = display->getstringsize(buf, NULL, NULL);
161 if (x > max_label_width)
162 max_label_width = x;
163 }
164
165 /* Draw title string */
166 set_drawinfo(display, DRMODE_SOLID, text_color, background_color);
167 display->getstringsize(title, &x, &y);
168 display->putsxy((display->width - x) / 2, MARGIN_TOP, title);
169
170 /* Get slider positions and top starting position */
171 text_top = MARGIN_TOP + y + TITLE_MARGIN_BOTTOM + SELECTOR_TB_MARGIN;
172 slider_left = MARGIN_LEFT + SELECTOR_LR_MARGIN + display->char_width +
173 max_label_width + SLIDER_MARGIN_LEFT;
174 slider_width = display->width - slider_left - SLIDER_MARGIN_RIGHT -
175 SELECTOR_LR_MARGIN - display->char_width*3 - MARGIN_RIGHT;
176
177 for (i = 0; i < 3; i++)
178 {
179 int mode = DRMODE_SOLID;
180 unsigned fg = text_color;
181 unsigned bg = background_color;
182
65 if (!display_three_rows) 183 if (!display_three_rows)
66 i = row; 184 i = row;
67 185
68 if (i==row) 186 if (i == row)
69 { 187 {
70 if ((global_settings.invert_cursor) && (display->depth >2)) 188 set_drawinfo(display, DRMODE_SOLID, text_color,
189 background_color);
190
191 if (global_settings.invert_cursor)
71 { 192 {
72 display->fillrect(0,text_top-1,display->width,display->char_height+2); 193 /* Draw solid bar selection bar */
73 bg_col = text_color; 194 display->fillrect(0,
195 text_top - SELECTOR_TB_MARGIN,
196 display->width,
197 display->char_height +
198 SELECTOR_TB_MARGIN*2);
199
200 if (display->depth == 1)
201 {
202 /* Just invert for low mono display */
203 mode |= DRMODE_INVERSEVID;
204 }
205 else
206 {
207 if (display->depth >= 16)
208 {
209 /* Backdrops will show through text in
210 DRMODE_SOLID */
211 mode = DRMODE_FG;
212 fg = prim_rgb[i];
213 }
214 else
215 {
216 fg = background_color;
217 }
218
219 bg = text_color;
220 }
74 } 221 }
75 else if (display_three_rows) 222 else if (display_three_rows)
76 { 223 {
77 display->putsxy(0,text_top,">"); 224 /* Draw "> <" around sliders */
78 display->putsxy(display->width-display->char_width-2,text_top,"<"); 225 display->putsxy(MARGIN_LEFT, text_top, ">");
79 bg_col = background_color; 226 display->putsxy(display->width-display->char_width -
80 } 227 MARGIN_RIGHT, text_top, "<");
81 if (display->depth > 1) 228 if (display->depth >= 16)
82 { 229 fg = prim_rgb[i];
83 if (i==0)
84 display->set_foreground(LCD_RGBPACK(255, 0, 0));
85 else if (i==1)
86 display->set_foreground(LCD_RGBPACK(0, 255, 0));
87 else if (i==2)
88 display->set_foreground(LCD_RGBPACK(0 ,0 ,255));
89 } 230 }
90 } 231 }
91 else 232
92 { 233 set_drawinfo(display, mode, fg, bg);
93 if (display->depth > 1) 234
94 display->set_foreground(text_color); 235 /* Draw label - assumes labels are one character */
95 bg_col = background_color; 236 buf[0] = str(LANG_COLOR_RGB_LABELS)[i];
96 } 237 buf[1] = '\0';
238 display->putsxy(slider_left - display->char_width -
239 SLIDER_MARGIN_LEFT, text_top, buf);
97 240
98 if (display->depth > 1) 241 /* Draw color value */
99 display->set_background(bg_col); 242 snprintf(buf, 3, "%02d", rgb->rgb_val[i]);
243 display->putsxy(slider_left + slider_width + SLIDER_MARGIN_RIGHT,
244 text_top, buf);
100 245
101 text_centre = text_top+(display->char_height/2); 246 /* Draw scrollbar */
102 rgb_dummy[0] = textrgb[i]; 247 gui_scrollbar_draw(display,
103 display->putsxy(TEXT_MARGIN,text_top,rgb_dummy); 248 slider_left,
104 snprintf(buf,3,"%02d",rgb_val[i]); 249 text_top + display->char_height / 4,
105 display->putsxy(display->width-(display->char_width*4),text_top,buf); 250 slider_width,
251 display->char_height / 2,
252 max_val[i],
253 0,
254 rgb->rgb_val[i],
255 HORIZONTAL);
106 256
107 text_top += display->char_height/4; 257 /* Advance to next line */
258 text_top += display->char_height + 2*SELECTOR_TB_MARGIN;
108 259
109 gui_scrollbar_draw(display,SLIDER_START,text_top,slider_width,
110 display->char_height/2,
111 max_val[i],0,rgb_val[i],HORIZONTAL);
112 if (!display_three_rows) 260 if (!display_three_rows)
113 break; 261 break;
114 text_top += display->char_height;
115 } 262 }
116 263
117 if (display->depth > 1) { 264 /* Format RGB: #rrggbb */
118 display->set_background(background_color); 265 snprintf(buf, sizeof(buf), str(LANG_COLOR_RGB_VALUE),
119 display->set_foreground(text_color); 266 rgb->red, rgb->green, rgb->blue);
120 } 267
268 if (display->depth >= 16)
269 {
270 /* Display color swatch on color screens only */
271 int left = slider_left;
272 int top = text_top + SWATCH_TOP_MARGIN;
273 int width = display->width - slider_left - left;
274 int height = display->height - top - MARGIN_BOTTOM;
121 275
122 if (text_top + (display->char_height*2) < (display->height-40-display->char_height)) 276 display->setfont(FONT_SYSFIXED);
123 text_top += (display->char_height*2);
124 else text_top += (display->char_height);
125 277
126 /* Display RGB: #rrggbb */ 278 /* Only draw if room */
127 snprintf(buf,sizeof(buf),str(LANG_COLOR_RGB_VALUE), 279 if (height >= display->char_height + 2)
128 RGB_UNPACK_RED(color), 280 {
129 RGB_UNPACK_GREEN(color), 281 display->set_foreground(rgb->color);
130 RGB_UNPACK_BLUE(color)); 282 display->fillrect(left, top, width, height);
131 283
132 display->putsxy((display->width-(display->char_width*11))/2,text_top,buf); 284 /* Draw RGB: #rrggbb in middle of swatch */
285 display->set_drawmode(DRMODE_FG);
286 display->getstringsize(buf, &x, &y);
287 display->set_foreground(get_black_or_white(rgb));
133 288
134 if (display->depth > 1) { 289 x = left + (width - x) / 2;
135 display->set_foreground(color); 290 y = top + (height - y) / 2;
136 display->fillrect(SLIDER_START,LCD_HEIGHT-40,slider_width,35);
137 291
138 display->set_foreground(LCD_BLACK); 292 display->putsxy(x, y, buf);
139 display->drawrect(SLIDER_START-1,LCD_HEIGHT-41,slider_width+2,37); 293 display->set_drawmode(DRMODE_SOLID);
294
295 /* Draw border */
296 display->set_foreground(text_color);
297 display->drawrect(left - 1, top - 1, width + 2, height + 2);
298 }
299
300 display->setfont(FONT_UI);
301 }
302 else
303 {
304 /* Display RGB value only centered on remaining display if room */
305 display->getstringsize(buf, &x, &y);
306 i = text_top + SWATCH_TOP_MARGIN;
307
308 if (i + y <= display->height - MARGIN_BOTTOM)
309 {
310 set_drawinfo(display, DRMODE_SOLID, text_color, background_color);
311 x = (display->width - x) / 2;
312 y = (i + display->height - MARGIN_BOTTOM - y) / 2;
313 display->putsxy(x, y, buf);
314 }
140 } 315 }
141 316
142 display->update(); 317 display->update();
318 /* Be sure screen mode is reset */
319 set_drawinfo(display, DRMODE_SOLID, text_color, background_color);
143} 320}
144 321
145/*********** 322/***********
@@ -148,74 +325,59 @@ static void draw_screen(struct screen *display, char *title,
148 color is a pointer to the colour (in native format) to modify 325 color is a pointer to the colour (in native format) to modify
149 set banned_color to -1 to allow all 326 set banned_color to -1 to allow all
150 ***********/ 327 ***********/
151bool set_color(struct screen *display,char *title, int* color, int banned_color) 328bool set_color(struct screen *display, char *title, int* color, int banned_color)
152{ 329{
153 int exit = 0, button, slider=0; 330 int exit = 0, button, slider = 0;
154 int rgb_val[3]; /* native depth r,g,b*/;
155 int fgcolor = display->get_foreground();
156 int newcolor = *color;
157 int i; 331 int i;
332 struct rgb_pick rgb;
333 (void)display;
158 334
159#if LCD_PIXELFORMAT == RGB565 335 rgb.color = *color;
160 rgb_val[0] = ((*color)&0xf800) >> 11;
161 rgb_val[1] = ((*color)&0x07e0) >> 5;
162 rgb_val[2] = ((*color)&0x001f);
163#elif LCD_PIXELFORMAT == RGB565SWAPPED
164 rgb_val[0] = ((swap16(*color))&0xf800) >> 11;
165 rgb_val[1] = ((swap16(*color))&0x07e0) >> 5;
166 rgb_val[2] = ((swap16(*color))&0x001f);
167#endif
168 336
169 while (!exit) 337 while (!exit)
170 { 338 {
171 /* We need to maintain three versions of the colour: 339 unpack_rgb(&rgb);
172
173 rgb_val[3] - the native depth RGB values
174 newcolor - the native format packed colour
175 */
176 340
177#if LCD_PIXELFORMAT == RGB565
178 newcolor = (rgb_val[0] << 11) | (rgb_val[1] << 5) | (rgb_val[2]);
179#elif LCD_PIXELFORMAT == RGB565SWAPPED
180 newcolor = swap16((rgb_val[0] << 11) | (rgb_val[1] << 5) | (rgb_val[2]));
181#endif
182 FOR_NB_SCREENS(i) 341 FOR_NB_SCREENS(i)
183 { 342 {
184 draw_screen(&screens[i], title, rgb_val, newcolor, slider); 343 draw_screen(&screens[i], title, &rgb, slider);
185 } 344 }
186 345
187 button = get_action(CONTEXT_SETTINGS_COLOURCHOOSER,TIMEOUT_BLOCK); 346 button = get_action(CONTEXT_SETTINGS_COLOURCHOOSER, TIMEOUT_BLOCK);
347
188 switch (button) 348 switch (button)
189 { 349 {
190 case ACTION_STD_PREV: 350 case ACTION_STD_PREV:
191 case ACTION_STD_PREVREPEAT: 351 case ACTION_STD_PREVREPEAT:
192 slider = (slider+2)%3; 352 slider = (slider + 2) % 3;
193 break; 353 break;
194 354
195 case ACTION_STD_NEXT: 355 case ACTION_STD_NEXT:
196 case ACTION_STD_NEXTREPEAT: 356 case ACTION_STD_NEXTREPEAT:
197 slider = (slider+1)%3; 357 slider = (slider + 1) % 3;
198 break; 358 break;
199 359
200 case ACTION_SETTINGS_INC: 360 case ACTION_SETTINGS_INC:
201 case ACTION_SETTINGS_INCREPEAT: 361 case ACTION_SETTINGS_INCREPEAT:
202 if (rgb_val[slider] < max_val[slider]) 362 if (rgb.rgb_val[slider] < max_val[slider])
203 rgb_val[slider]++; 363 rgb.rgb_val[slider]++;
364 pack_rgb(&rgb);
204 break; 365 break;
205 366
206 case ACTION_SETTINGS_DEC: 367 case ACTION_SETTINGS_DEC:
207 case ACTION_SETTINGS_DECREPEAT: 368 case ACTION_SETTINGS_DECREPEAT:
208 if (rgb_val[slider] > 0) 369 if (rgb.rgb_val[slider] > 0)
209 rgb_val[slider]--; 370 rgb.rgb_val[slider]--;
371 pack_rgb(&rgb);
210 break; 372 break;
211 373
212 case ACTION_STD_OK: 374 case ACTION_STD_OK:
213 if ((banned_color!=-1) && (banned_color == newcolor)) 375 if (banned_color != -1 && (unsigned)banned_color == rgb.color)
214 { 376 {
215 gui_syncsplash(HZ*2,true,str(LANG_COLOR_UNACCEPTABLE)); 377 gui_syncsplash(HZ*2, true, str(LANG_COLOR_UNACCEPTABLE));
216 break; 378 break;
217 } 379 }
218 *color = newcolor; 380 *color = rgb.color;
219 exit = 1; 381 exit = 1;
220 break; 382 break;
221 383
@@ -224,14 +386,12 @@ bool set_color(struct screen *display,char *title, int* color, int banned_color)
224 break; 386 break;
225 387
226 default: 388 default:
227 if(default_event_handler(button) == SYS_USB_CONNECTED) { 389 if (default_event_handler(button) == SYS_USB_CONNECTED)
228 display->set_foreground(fgcolor);
229 return true; 390 return true;
230 }
231 break; 391 break;
232 } 392 }
233 } 393 }
234 display->set_foreground(fgcolor); 394
235 action_signalscreenchange(); 395 action_signalscreenchange();
236 return false; 396 return false;
237} 397}