when resolving filenames also take system and hidden files into account.
[Rockbox.git] / uisimulator / sdl / lcd-bitmap.c
blobbc9e56732f0d1d415780ffea897f3c4ee5b77435
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2006 Dan Everton
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 ****************************************************************************/
20 #include "debug.h"
21 #include "uisdl.h"
22 #include "lcd-sdl.h"
24 SDL_Surface* lcd_surface;
25 int lcd_backlight_val;
27 #if LCD_DEPTH <= 8
28 #ifdef HAVE_BACKLIGHT
29 SDL_Color lcd_backlight_color_zero = {UI_LCD_BGCOLORLIGHT, 0};
30 SDL_Color lcd_backlight_color_max = {UI_LCD_FGCOLORLIGHT, 0};
31 #endif
32 SDL_Color lcd_color_zero = {UI_LCD_BGCOLOR, 0};
33 SDL_Color lcd_color_max = {UI_LCD_FGCOLOR, 0};
34 #endif
36 #if LCD_DEPTH < 8
37 int lcd_ex_shades = 0;
38 unsigned long (*lcd_ex_getpixel)(int, int) = NULL;
39 #endif
41 static unsigned long get_lcd_pixel(int x, int y)
43 #if LCD_DEPTH == 1
44 return ((lcd_framebuffer[y/8][x] >> (y & 7)) & 1);
45 #elif LCD_DEPTH == 2
46 #if LCD_PIXELFORMAT == HORIZONTAL_PACKING
47 return ((lcd_framebuffer[y][x/4] >> (2 * (~x & 3))) & 3);
48 #elif LCD_PIXELFORMAT == VERTICAL_PACKING
49 return ((lcd_framebuffer[y/4][x] >> (2 * (y & 3))) & 3);
50 #elif LCD_PIXELFORMAT == VERTICAL_INTERLEAVED
51 unsigned bits = (lcd_framebuffer[y/8][x] >> (y & 7)) & 0x0101;
52 return (bits | (bits >> 7)) & 3;
53 #endif
54 #elif LCD_DEPTH == 16
55 #if LCD_PIXELFORMAT == RGB565SWAPPED
56 unsigned bits = lcd_framebuffer[y][x];
57 return (bits >> 8) | (bits << 8);
58 #else
59 return lcd_framebuffer[y][x];
60 #endif
61 #endif
64 void lcd_update(void)
66 /* update a full screen rect */
67 lcd_update_rect(0, 0, LCD_WIDTH, LCD_HEIGHT);
70 void lcd_update_rect(int x_start, int y_start, int width, int height)
72 sdl_update_rect(lcd_surface, x_start, y_start, width, height, LCD_WIDTH,
73 LCD_HEIGHT, get_lcd_pixel);
74 sdl_gui_update(lcd_surface, x_start, y_start, width, height, LCD_WIDTH,
75 LCD_HEIGHT, background ? UI_LCD_POSX : 0, background? UI_LCD_POSY : 0);
78 #ifdef HAVE_BACKLIGHT
79 void sim_backlight(int value)
81 lcd_backlight_val = value;
83 #if LCD_DEPTH <= 8
84 if (value > 0) {
85 sdl_set_gradient(lcd_surface, &lcd_backlight_color_zero,
86 &lcd_backlight_color_max, 0, (1<<LCD_DEPTH));
87 } else {
88 sdl_set_gradient(lcd_surface, &lcd_color_zero, &lcd_color_max,
89 0, (1<<LCD_DEPTH));
91 #if LCD_DEPTH < 8
92 if (lcd_ex_shades) {
93 if (value > 0) {
94 sdl_set_gradient(lcd_surface, &lcd_backlight_color_max,
95 &lcd_backlight_color_zero, (1<<LCD_DEPTH),
96 lcd_ex_shades);
97 } else {
98 sdl_set_gradient(lcd_surface, &lcd_color_max, &lcd_color_zero,
99 (1<<LCD_DEPTH), lcd_ex_shades);
102 #endif
104 sdl_gui_update(lcd_surface, 0, 0, LCD_WIDTH, LCD_HEIGHT, LCD_WIDTH,
105 LCD_HEIGHT, background ? UI_LCD_POSX : 0, background? UI_LCD_POSY : 0);
107 #endif
109 #endif
111 /* initialise simulator lcd driver */
112 void sim_lcd_init(void)
114 #if LCD_DEPTH == 16
115 lcd_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, LCD_WIDTH * display_zoom,
116 LCD_HEIGHT * display_zoom, LCD_DEPTH, 0, 0, 0, 0);
117 #else
118 lcd_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, LCD_WIDTH * display_zoom,
119 LCD_HEIGHT * display_zoom, 8, 0, 0, 0, 0);
120 #endif
122 #if LCD_DEPTH <= 8
123 #ifdef HAVE_BACKLIGHT
124 sdl_set_gradient(lcd_surface, &lcd_backlight_color_zero, &lcd_color_max,
125 0, (1<<LCD_DEPTH));
126 #else
127 sdl_set_gradient(lcd_surface, &lcd_color_zero, &lcd_color_max, 0,
128 (1<<LCD_DEPTH));
129 #endif
130 #endif
133 #if LCD_DEPTH < 8
134 void sim_lcd_ex_init(int shades, unsigned long (*getpixel)(int, int))
136 lcd_ex_shades = shades;
137 lcd_ex_getpixel = getpixel;
138 if (shades) {
139 #ifdef HAVE_BACKLIGHT
140 if (lcd_backlight_val > 0) {
141 sdl_set_gradient(lcd_surface, &lcd_color_max,
142 &lcd_backlight_color_zero, (1<<LCD_DEPTH),
143 shades);
145 else
146 #endif
148 sdl_set_gradient(lcd_surface, &lcd_color_max, &lcd_color_zero,
149 (1<<LCD_DEPTH), shades);
154 void sim_lcd_ex_update_rect(int x_start, int y_start, int width, int height)
156 if (lcd_ex_getpixel) {
157 sdl_update_rect(lcd_surface, x_start, y_start, width, height,
158 LCD_WIDTH, LCD_HEIGHT, lcd_ex_getpixel);
159 sdl_gui_update(lcd_surface, x_start, y_start, width, height, LCD_WIDTH,
160 LCD_HEIGHT, background ? UI_LCD_POSX : 0,
161 background? UI_LCD_POSY : 0);
164 #endif
166 #ifdef HAVE_LCD_COLOR
168 * |R| |1.000000 -0.000001 1.402000| |Y'|
169 * |G| = |1.000000 -0.334136 -0.714136| |Pb|
170 * |B| |1.000000 1.772000 0.000000| |Pr|
171 * Scaled, normalized, rounded and tweaked to yield RGB 565:
172 * |R| |74 0 101| |Y' - 16| >> 9
173 * |G| = |74 -24 -51| |Cb - 128| >> 8
174 * |B| |74 128 0| |Cr - 128| >> 9
176 #define YFAC (74)
177 #define RVFAC (101)
178 #define GUFAC (-24)
179 #define GVFAC (-51)
180 #define BUFAC (128)
182 static inline int clamp(int val, int min, int max)
184 if (val < min)
185 val = min;
186 else if (val > max)
187 val = max;
188 return val;
191 void lcd_yuv_set_options(unsigned options)
193 (void)options;
196 /* Draw a partial YUV colour bitmap - similiar behavior to lcd_blit_yuv
197 in the core */
198 void lcd_blit_yuv(unsigned char * const src[3],
199 int src_x, int src_y, int stride,
200 int x, int y, int width, int height)
202 const unsigned char *ysrc, *usrc, *vsrc;
203 int linecounter;
204 fb_data *dst, *row_end;
205 long z;
207 /* width and height must be >= 2 and an even number */
208 width &= ~1;
209 linecounter = height >> 1;
211 #if LCD_WIDTH >= LCD_HEIGHT
212 dst = &lcd_framebuffer[y][x];
213 row_end = dst + width;
214 #else
215 dst = &lcd_framebuffer[x][LCD_WIDTH - y - 1];
216 row_end = dst + LCD_WIDTH * width;
217 #endif
219 z = stride * src_y;
220 ysrc = src[0] + z + src_x;
221 usrc = src[1] + (z >> 2) + (src_x >> 1);
222 vsrc = src[2] + (usrc - src[1]);
224 /* stride => amount to jump from end of last row to start of next */
225 stride -= width;
227 /* upsampling, YUV->RGB conversion and reduction to RGB565 in one go */
233 int y, cb, cr, rv, guv, bu, r, g, b;
235 y = YFAC*(*ysrc++ - 16);
236 cb = *usrc++ - 128;
237 cr = *vsrc++ - 128;
239 rv = RVFAC*cr;
240 guv = GUFAC*cb + GVFAC*cr;
241 bu = BUFAC*cb;
243 r = y + rv;
244 g = y + guv;
245 b = y + bu;
247 if ((unsigned)(r | g | b) > 64*256-1)
249 r = clamp(r, 0, 64*256-1);
250 g = clamp(g, 0, 64*256-1);
251 b = clamp(b, 0, 64*256-1);
254 *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9);
256 #if LCD_WIDTH >= LCD_HEIGHT
257 dst++;
258 #else
259 dst += LCD_WIDTH;
260 #endif
262 y = YFAC*(*ysrc++ - 16);
263 r = y + rv;
264 g = y + guv;
265 b = y + bu;
267 if ((unsigned)(r | g | b) > 64*256-1)
269 r = clamp(r, 0, 64*256-1);
270 g = clamp(g, 0, 64*256-1);
271 b = clamp(b, 0, 64*256-1);
274 *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9);
276 #if LCD_WIDTH >= LCD_HEIGHT
277 dst++;
278 #else
279 dst += LCD_WIDTH;
280 #endif
282 while (dst < row_end);
284 ysrc += stride;
285 usrc -= width >> 1;
286 vsrc -= width >> 1;
288 #if LCD_WIDTH >= LCD_HEIGHT
289 row_end += LCD_WIDTH;
290 dst += LCD_WIDTH - width;
291 #else
292 row_end -= 1;
293 dst -= LCD_WIDTH*width + 1;
294 #endif
298 int y, cb, cr, rv, guv, bu, r, g, b;
300 y = YFAC*(*ysrc++ - 16);
301 cb = *usrc++ - 128;
302 cr = *vsrc++ - 128;
304 rv = RVFAC*cr;
305 guv = GUFAC*cb + GVFAC*cr;
306 bu = BUFAC*cb;
308 r = y + rv;
309 g = y + guv;
310 b = y + bu;
312 if ((unsigned)(r | g | b) > 64*256-1)
314 r = clamp(r, 0, 64*256-1);
315 g = clamp(g, 0, 64*256-1);
316 b = clamp(b, 0, 64*256-1);
319 *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9);
321 #if LCD_WIDTH >= LCD_HEIGHT
322 dst++;
323 #else
324 dst += LCD_WIDTH;
325 #endif
327 y = YFAC*(*ysrc++ - 16);
328 r = y + rv;
329 g = y + guv;
330 b = y + bu;
332 if ((unsigned)(r | g | b) > 64*256-1)
334 r = clamp(r, 0, 64*256-1);
335 g = clamp(g, 0, 64*256-1);
336 b = clamp(b, 0, 64*256-1);
339 *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9);
341 #if LCD_WIDTH >= LCD_HEIGHT
342 dst++;
343 #else
344 dst += LCD_WIDTH;
345 #endif
347 while (dst < row_end);
349 ysrc += stride;
350 usrc += stride >> 1;
351 vsrc += stride >> 1;
353 #if LCD_WIDTH >= LCD_HEIGHT
354 row_end += LCD_WIDTH;
355 dst += LCD_WIDTH - width;
356 #else
357 row_end -= 1;
358 dst -= LCD_WIDTH*width + 1;
359 #endif
361 while (--linecounter > 0);
363 #if LCD_WIDTH >= LCD_HEIGHT
364 lcd_update_rect(x, y, width, height);
365 #else
366 lcd_update_rect(LCD_WIDTH - y - height, x, height, width);
367 #endif
369 #endif /* HAVE_LCD_COLOR */