diff options
Diffstat (limited to 'firmware/target/hosted')
-rw-r--r-- | firmware/target/hosted/sdl/button-sdl.c | 2018 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/button-sdl.h | 32 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/kernel-sdl.c | 162 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-bitmap.c | 416 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-bitmap.h | 35 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-charcells.c | 198 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-charcells.h | 34 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-remote-bitmap.c | 111 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-remote-bitmap.h | 32 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-sdl.c | 113 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/lcd-sdl.h | 43 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/pcm-sdl.c | 373 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/sim-ui-defines.h | 405 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/system-sdl.c | 236 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/system-sdl.h | 52 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/thread-sdl.c | 610 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/thread-sdl.h | 32 | ||||
-rw-r--r-- | firmware/target/hosted/sdl/timer-sdl.c | 61 |
18 files changed, 4963 insertions, 0 deletions
diff --git a/firmware/target/hosted/sdl/button-sdl.c b/firmware/target/hosted/sdl/button-sdl.c new file mode 100644 index 0000000000..51ba8cff92 --- /dev/null +++ b/firmware/target/hosted/sdl/button-sdl.c | |||
@@ -0,0 +1,2018 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2002 by Felix Arends | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <math.h> | ||
23 | #include "sim-ui-defines.h" | ||
24 | #include "lcd-charcells.h" | ||
25 | #include "lcd-remote.h" | ||
26 | #include "config.h" | ||
27 | #include "button.h" | ||
28 | #include "kernel.h" | ||
29 | #include "backlight.h" | ||
30 | #include "misc.h" | ||
31 | #include "sim_tasks.h" | ||
32 | #include "button-sdl.h" | ||
33 | #include "backlight.h" | ||
34 | |||
35 | #include "debug.h" | ||
36 | |||
37 | #ifdef HAVE_TOUCHSCREEN | ||
38 | #include "touchscreen.h" | ||
39 | static int mouse_coords = 0; | ||
40 | #endif | ||
41 | /* how long until repeat kicks in */ | ||
42 | #define REPEAT_START 6 | ||
43 | |||
44 | /* the speed repeat starts at */ | ||
45 | #define REPEAT_INTERVAL_START 4 | ||
46 | |||
47 | /* speed repeat finishes at */ | ||
48 | #define REPEAT_INTERVAL_FINISH 2 | ||
49 | |||
50 | #ifdef HAVE_TOUCHSCREEN | ||
51 | #define USB_KEY SDLK_c /* SDLK_u is taken by BUTTON_MIDLEFT */ | ||
52 | #else | ||
53 | #define USB_KEY SDLK_u | ||
54 | #endif | ||
55 | |||
56 | #if defined(IRIVER_H100_SERIES) || defined (IRIVER_H300_SERIES) | ||
57 | int _remote_type=REMOTETYPE_H100_LCD; | ||
58 | |||
59 | int remote_type(void) | ||
60 | { | ||
61 | return _remote_type; | ||
62 | } | ||
63 | #endif | ||
64 | |||
65 | static int xy2button(int x, int y); | ||
66 | |||
67 | struct event_queue button_queue; | ||
68 | |||
69 | static int btn = 0; /* Hopefully keeps track of currently pressed keys... */ | ||
70 | |||
71 | #ifdef HAS_BUTTON_HOLD | ||
72 | bool hold_button_state = false; | ||
73 | bool button_hold(void) { | ||
74 | return hold_button_state; | ||
75 | } | ||
76 | #endif | ||
77 | |||
78 | #ifdef HAS_REMOTE_BUTTON_HOLD | ||
79 | bool remote_hold_button_state = false; | ||
80 | bool remote_button_hold(void) { | ||
81 | return remote_hold_button_state; | ||
82 | } | ||
83 | #endif | ||
84 | static void button_event(int key, bool pressed); | ||
85 | extern bool debug_wps; | ||
86 | extern bool mapping; | ||
87 | static void gui_message_loop(void) | ||
88 | { | ||
89 | SDL_Event event; | ||
90 | static int x,y,xybutton = 0; | ||
91 | |||
92 | if (SDL_PollEvent(&event)) | ||
93 | { | ||
94 | switch(event.type) | ||
95 | { | ||
96 | case SDL_KEYDOWN: | ||
97 | button_event(event.key.keysym.sym, true); | ||
98 | break; | ||
99 | case SDL_KEYUP: | ||
100 | button_event(event.key.keysym.sym, false); | ||
101 | case SDL_MOUSEBUTTONDOWN: | ||
102 | switch ( event.button.button ) { | ||
103 | #ifdef HAVE_SCROLLWHEEL | ||
104 | case SDL_BUTTON_WHEELUP: | ||
105 | button_event( SDLK_UP, true ); | ||
106 | break; | ||
107 | case SDL_BUTTON_WHEELDOWN: | ||
108 | button_event( SDLK_DOWN, true ); | ||
109 | break; | ||
110 | #endif | ||
111 | case SDL_BUTTON_LEFT: | ||
112 | case SDL_BUTTON_MIDDLE: | ||
113 | if ( mapping && background ) { | ||
114 | x = event.button.x; | ||
115 | y = event.button.y; | ||
116 | } | ||
117 | if ( background ) { | ||
118 | xybutton = xy2button( event.button.x, event.button.y ); | ||
119 | if( xybutton ) | ||
120 | button_event( xybutton, true ); | ||
121 | } | ||
122 | break; | ||
123 | default: | ||
124 | break; | ||
125 | } | ||
126 | |||
127 | if (debug_wps && event.button.button == 1) | ||
128 | { | ||
129 | if ( background ) | ||
130 | #ifdef HAVE_REMOTE | ||
131 | if ( event.button.y < UI_REMOTE_POSY ) /* Main Screen */ | ||
132 | printf("Mouse at: (%d, %d)\n", event.button.x - UI_LCD_POSX -1 , event.button.y - UI_LCD_POSY - 1 ); | ||
133 | else | ||
134 | printf("Mouse at: (%d, %d)\n", event.button.x - UI_REMOTE_POSX -1 , event.button.y - UI_REMOTE_POSY - 1 ); | ||
135 | #else | ||
136 | printf("Mouse at: (%d, %d)\n", event.button.x - UI_LCD_POSX -1 , event.button.y - UI_LCD_POSY - 1 ); | ||
137 | #endif | ||
138 | else | ||
139 | if ( event.button.y/display_zoom < LCD_HEIGHT ) /* Main Screen */ | ||
140 | printf("Mouse at: (%d, %d)\n", event.button.x/display_zoom, event.button.y/display_zoom ); | ||
141 | #ifdef HAVE_REMOTE | ||
142 | else | ||
143 | printf("Mouse at: (%d, %d)\n", event.button.x/display_zoom, event.button.y/display_zoom - LCD_HEIGHT ); | ||
144 | #endif | ||
145 | } | ||
146 | break; | ||
147 | case SDL_MOUSEBUTTONUP: | ||
148 | switch ( event.button.button ) { | ||
149 | /* The scrollwheel button up events are ignored as they are queued immediately */ | ||
150 | case SDL_BUTTON_LEFT: | ||
151 | case SDL_BUTTON_MIDDLE: | ||
152 | if ( mapping && background ) { | ||
153 | printf(" { SDLK_, %d, %d, %d, \"\" },\n", x, | ||
154 | #define SQUARE(x) ((x)*(x)) | ||
155 | y, (int)sqrt( SQUARE(x-(int)event.button.x) | ||
156 | + SQUARE(y-(int)event.button.y)) ); | ||
157 | } | ||
158 | if ( background && xybutton ) { | ||
159 | button_event( xybutton, false ); | ||
160 | xybutton = 0; | ||
161 | } | ||
162 | #ifdef HAVE_TOUCHSCREEN | ||
163 | else { | ||
164 | button_event(BUTTON_TOUCHSCREEN, false); | ||
165 | } | ||
166 | #endif | ||
167 | break; | ||
168 | default: | ||
169 | break; | ||
170 | } | ||
171 | break; | ||
172 | |||
173 | |||
174 | case SDL_QUIT: | ||
175 | { | ||
176 | exit(EXIT_SUCCESS); | ||
177 | break; | ||
178 | } | ||
179 | default: | ||
180 | /*printf("Unhandled event\n"); */ | ||
181 | break; | ||
182 | } | ||
183 | } | ||
184 | } | ||
185 | |||
186 | static void button_event(int key, bool pressed) | ||
187 | { | ||
188 | int new_btn = 0; | ||
189 | static bool usb_connected = false; | ||
190 | if (usb_connected && key != USB_KEY) | ||
191 | return; | ||
192 | switch (key) | ||
193 | { | ||
194 | |||
195 | #ifdef HAVE_TOUCHSCREEN | ||
196 | case BUTTON_TOUCHSCREEN: | ||
197 | switch (touchscreen_get_mode()) | ||
198 | { | ||
199 | case TOUCHSCREEN_POINT: | ||
200 | new_btn = BUTTON_TOUCHSCREEN; | ||
201 | break; | ||
202 | case TOUCHSCREEN_BUTTON: | ||
203 | { | ||
204 | static int touchscreen_buttons[3][3] = { | ||
205 | {BUTTON_TOPLEFT, BUTTON_TOPMIDDLE, BUTTON_TOPRIGHT}, | ||
206 | {BUTTON_MIDLEFT, BUTTON_CENTER, BUTTON_MIDRIGHT}, | ||
207 | {BUTTON_BOTTOMLEFT, BUTTON_BOTTOMMIDDLE, BUTTON_BOTTOMRIGHT}, | ||
208 | }; | ||
209 | int px_x = ((mouse_coords&0xffff0000)>>16); | ||
210 | int px_y = ((mouse_coords&0x0000ffff)); | ||
211 | new_btn = touchscreen_buttons[px_y/(LCD_HEIGHT/3)][px_x/(LCD_WIDTH/3)]; | ||
212 | break; | ||
213 | } | ||
214 | } | ||
215 | break; | ||
216 | case SDLK_KP7: | ||
217 | case SDLK_7: | ||
218 | new_btn = BUTTON_TOPLEFT; | ||
219 | break; | ||
220 | case SDLK_KP8: | ||
221 | case SDLK_8: | ||
222 | case SDLK_UP: | ||
223 | new_btn = BUTTON_TOPMIDDLE; | ||
224 | break; | ||
225 | case SDLK_KP9: | ||
226 | case SDLK_9: | ||
227 | new_btn = BUTTON_TOPRIGHT; | ||
228 | break; | ||
229 | case SDLK_KP4: | ||
230 | case SDLK_u: | ||
231 | case SDLK_LEFT: | ||
232 | new_btn = BUTTON_MIDLEFT; | ||
233 | break; | ||
234 | case SDLK_KP5: | ||
235 | case SDLK_i: | ||
236 | new_btn = BUTTON_CENTER; | ||
237 | break; | ||
238 | case SDLK_KP6: | ||
239 | case SDLK_o: | ||
240 | case SDLK_RIGHT: | ||
241 | new_btn = BUTTON_MIDRIGHT; | ||
242 | break; | ||
243 | case SDLK_KP1: | ||
244 | case SDLK_j: | ||
245 | new_btn = BUTTON_BOTTOMLEFT; | ||
246 | break; | ||
247 | case SDLK_KP2: | ||
248 | case SDLK_k: | ||
249 | case SDLK_DOWN: | ||
250 | new_btn = BUTTON_BOTTOMMIDDLE; | ||
251 | break; | ||
252 | case SDLK_KP3: | ||
253 | case SDLK_l: | ||
254 | new_btn = BUTTON_BOTTOMRIGHT; | ||
255 | break; | ||
256 | case SDLK_F4: | ||
257 | if(pressed) | ||
258 | { | ||
259 | touchscreen_set_mode(touchscreen_get_mode() == TOUCHSCREEN_POINT ? TOUCHSCREEN_BUTTON : TOUCHSCREEN_POINT); | ||
260 | printf("Touchscreen mode: %s\n", touchscreen_get_mode() == TOUCHSCREEN_POINT ? "TOUCHSCREEN_POINT" : "TOUCHSCREEN_BUTTON"); | ||
261 | } | ||
262 | break; | ||
263 | |||
264 | #endif | ||
265 | case USB_KEY: | ||
266 | if (!pressed) | ||
267 | { | ||
268 | usb_connected = !usb_connected; | ||
269 | if (usb_connected) | ||
270 | queue_post(&button_queue, SYS_USB_CONNECTED, 0); | ||
271 | else | ||
272 | queue_post(&button_queue, SYS_USB_DISCONNECTED, 0); | ||
273 | } | ||
274 | return; | ||
275 | |||
276 | #ifdef HAS_BUTTON_HOLD | ||
277 | case SDLK_h: | ||
278 | if(pressed) | ||
279 | { | ||
280 | hold_button_state = !hold_button_state; | ||
281 | DEBUGF("Hold button is %s\n", hold_button_state?"ON":"OFF"); | ||
282 | } | ||
283 | return; | ||
284 | #endif | ||
285 | |||
286 | #ifdef HAS_REMOTE_BUTTON_HOLD | ||
287 | case SDLK_j: | ||
288 | if(pressed) | ||
289 | { | ||
290 | remote_hold_button_state = !remote_hold_button_state; | ||
291 | DEBUGF("Remote hold button is %s\n", | ||
292 | remote_hold_button_state?"ON":"OFF"); | ||
293 | } | ||
294 | return; | ||
295 | #endif | ||
296 | |||
297 | #if CONFIG_KEYPAD == GIGABEAT_PAD | ||
298 | case SDLK_KP4: | ||
299 | case SDLK_LEFT: | ||
300 | new_btn = BUTTON_LEFT; | ||
301 | break; | ||
302 | case SDLK_KP6: | ||
303 | case SDLK_RIGHT: | ||
304 | new_btn = BUTTON_RIGHT; | ||
305 | break; | ||
306 | case SDLK_KP8: | ||
307 | case SDLK_UP: | ||
308 | new_btn = BUTTON_UP; | ||
309 | break; | ||
310 | case SDLK_KP2: | ||
311 | case SDLK_DOWN: | ||
312 | new_btn = BUTTON_DOWN; | ||
313 | break; | ||
314 | case SDLK_KP_PLUS: | ||
315 | case SDLK_F8: | ||
316 | new_btn = BUTTON_POWER; | ||
317 | break; | ||
318 | case SDLK_ESCAPE: | ||
319 | new_btn = BUTTON_POWER; | ||
320 | break; | ||
321 | case SDLK_KP_ENTER: | ||
322 | case SDLK_RETURN: | ||
323 | case SDLK_a: | ||
324 | new_btn = BUTTON_A; | ||
325 | break; | ||
326 | case SDLK_KP5: | ||
327 | case SDLK_SPACE: | ||
328 | new_btn = BUTTON_SELECT; | ||
329 | break; | ||
330 | case SDLK_KP_PERIOD: | ||
331 | case SDLK_INSERT: | ||
332 | new_btn = BUTTON_MENU; | ||
333 | break; | ||
334 | case SDLK_KP9: | ||
335 | new_btn = BUTTON_VOL_UP; | ||
336 | break; | ||
337 | case SDLK_KP3: | ||
338 | new_btn = BUTTON_VOL_DOWN; | ||
339 | break; | ||
340 | |||
341 | #elif CONFIG_KEYPAD == GIGABEAT_S_PAD | ||
342 | case SDLK_KP4: | ||
343 | case SDLK_LEFT: | ||
344 | new_btn = BUTTON_LEFT; | ||
345 | break; | ||
346 | case SDLK_KP6: | ||
347 | case SDLK_RIGHT: | ||
348 | new_btn = BUTTON_RIGHT; | ||
349 | break; | ||
350 | case SDLK_KP8: | ||
351 | case SDLK_UP: | ||
352 | new_btn = BUTTON_UP; | ||
353 | break; | ||
354 | case SDLK_KP2: | ||
355 | case SDLK_DOWN: | ||
356 | new_btn = BUTTON_DOWN; | ||
357 | break; | ||
358 | case SDLK_F8: | ||
359 | case SDLK_ESCAPE: | ||
360 | new_btn = BUTTON_POWER; | ||
361 | break; | ||
362 | case SDLK_KP_PLUS: | ||
363 | case SDLK_KP_ENTER: | ||
364 | case SDLK_RETURN: | ||
365 | new_btn = BUTTON_PLAY; | ||
366 | break; | ||
367 | case SDLK_KP7: | ||
368 | new_btn = BUTTON_BACK; | ||
369 | break; | ||
370 | case SDLK_KP5: | ||
371 | case SDLK_SPACE: | ||
372 | new_btn = BUTTON_SELECT; | ||
373 | break; | ||
374 | case SDLK_KP9: | ||
375 | case SDLK_KP_PERIOD: | ||
376 | case SDLK_INSERT: | ||
377 | new_btn = BUTTON_MENU; | ||
378 | break; | ||
379 | |||
380 | #elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD | ||
381 | case SDLK_KP4: | ||
382 | case SDLK_LEFT: | ||
383 | new_btn = BUTTON_LEFT; | ||
384 | break; | ||
385 | case SDLK_KP6: | ||
386 | case SDLK_RIGHT: | ||
387 | new_btn = BUTTON_RIGHT; | ||
388 | break; | ||
389 | case SDLK_KP8: | ||
390 | case SDLK_UP: | ||
391 | new_btn = BUTTON_UP; | ||
392 | break; | ||
393 | case SDLK_KP2: | ||
394 | case SDLK_DOWN: | ||
395 | new_btn = BUTTON_DOWN; | ||
396 | break; | ||
397 | case SDLK_KP_PLUS: | ||
398 | case SDLK_F8: | ||
399 | new_btn = BUTTON_PLAY; | ||
400 | break; | ||
401 | case SDLK_ESCAPE: | ||
402 | new_btn = BUTTON_POWER; | ||
403 | break; | ||
404 | case SDLK_KP_ENTER: | ||
405 | case SDLK_RETURN: | ||
406 | case SDLK_a: | ||
407 | new_btn = BUTTON_POWER; | ||
408 | break; | ||
409 | case SDLK_KP_DIVIDE: | ||
410 | case SDLK_F1: | ||
411 | new_btn = BUTTON_REC; | ||
412 | break; | ||
413 | case SDLK_KP5: | ||
414 | case SDLK_SPACE: | ||
415 | new_btn = BUTTON_SELECT; | ||
416 | break; | ||
417 | |||
418 | #elif CONFIG_KEYPAD == IAUDIO_M3_PAD | ||
419 | case SDLK_KP4: | ||
420 | new_btn = BUTTON_LEFT; | ||
421 | break; | ||
422 | case SDLK_LEFT: | ||
423 | new_btn = BUTTON_RC_REW; | ||
424 | break; | ||
425 | case SDLK_KP6: | ||
426 | new_btn = BUTTON_RIGHT; | ||
427 | break; | ||
428 | case SDLK_RIGHT: | ||
429 | new_btn = BUTTON_RC_FF; | ||
430 | break; | ||
431 | case SDLK_KP8: | ||
432 | new_btn = BUTTON_VOL_UP; | ||
433 | break; | ||
434 | case SDLK_UP: | ||
435 | new_btn = BUTTON_RC_VOL_UP; | ||
436 | break; | ||
437 | case SDLK_KP2: | ||
438 | new_btn = BUTTON_VOL_DOWN; | ||
439 | break; | ||
440 | case SDLK_DOWN: | ||
441 | new_btn = BUTTON_RC_VOL_DOWN; | ||
442 | break; | ||
443 | case SDLK_KP_PERIOD: | ||
444 | new_btn = BUTTON_MODE; | ||
445 | break; | ||
446 | case SDLK_INSERT: | ||
447 | new_btn = BUTTON_RC_MODE; | ||
448 | break; | ||
449 | case SDLK_KP_DIVIDE: | ||
450 | new_btn = BUTTON_REC; | ||
451 | break; | ||
452 | case SDLK_F1: | ||
453 | new_btn = BUTTON_RC_REC; | ||
454 | break; | ||
455 | case SDLK_KP5: | ||
456 | new_btn = BUTTON_PLAY; | ||
457 | break; | ||
458 | case SDLK_SPACE: | ||
459 | new_btn = BUTTON_RC_PLAY; | ||
460 | break; | ||
461 | case SDLK_KP_ENTER: | ||
462 | case SDLK_RETURN: | ||
463 | new_btn = BUTTON_RC_MENU; | ||
464 | break; | ||
465 | |||
466 | #elif (CONFIG_KEYPAD == IPOD_1G2G_PAD) || (CONFIG_KEYPAD == IPOD_3G_PAD) \ | ||
467 | || (CONFIG_KEYPAD == IPOD_4G_PAD) | ||
468 | case SDLK_KP4: | ||
469 | case SDLK_LEFT: | ||
470 | new_btn = BUTTON_LEFT; | ||
471 | break; | ||
472 | case SDLK_KP6: | ||
473 | case SDLK_RIGHT: | ||
474 | new_btn = BUTTON_RIGHT; | ||
475 | break; | ||
476 | case SDLK_KP8: | ||
477 | case SDLK_UP: | ||
478 | new_btn = BUTTON_SCROLL_BACK; | ||
479 | break; | ||
480 | case SDLK_KP2: | ||
481 | case SDLK_DOWN: | ||
482 | new_btn = BUTTON_SCROLL_FWD; | ||
483 | break; | ||
484 | case SDLK_KP_PLUS: | ||
485 | case SDLK_F8: | ||
486 | new_btn = BUTTON_PLAY; | ||
487 | break; | ||
488 | case SDLK_KP5: | ||
489 | case SDLK_SPACE: | ||
490 | new_btn = BUTTON_SELECT; | ||
491 | break; | ||
492 | case SDLK_KP_PERIOD: | ||
493 | case SDLK_INSERT: | ||
494 | new_btn = BUTTON_MENU; | ||
495 | break; | ||
496 | |||
497 | #elif CONFIG_KEYPAD == IRIVER_H10_PAD | ||
498 | case SDLK_KP4: | ||
499 | case SDLK_LEFT: | ||
500 | new_btn = BUTTON_LEFT; | ||
501 | break; | ||
502 | case SDLK_KP6: | ||
503 | case SDLK_RIGHT: | ||
504 | new_btn = BUTTON_RIGHT; | ||
505 | break; | ||
506 | case SDLK_KP8: | ||
507 | case SDLK_UP: | ||
508 | new_btn = BUTTON_SCROLL_UP; | ||
509 | break; | ||
510 | case SDLK_KP2: | ||
511 | case SDLK_DOWN: | ||
512 | new_btn = BUTTON_SCROLL_DOWN; | ||
513 | break; | ||
514 | case SDLK_KP_PLUS: | ||
515 | case SDLK_F8: | ||
516 | new_btn = BUTTON_POWER; | ||
517 | break; | ||
518 | case SDLK_ESCAPE: | ||
519 | new_btn = BUTTON_POWER; | ||
520 | break; | ||
521 | case SDLK_KP_DIVIDE: | ||
522 | case SDLK_F1: | ||
523 | new_btn = BUTTON_REW; | ||
524 | break; | ||
525 | case SDLK_KP_MULTIPLY: | ||
526 | case SDLK_F2: | ||
527 | new_btn = BUTTON_FF; | ||
528 | break; | ||
529 | case SDLK_KP5: | ||
530 | case SDLK_SPACE: | ||
531 | new_btn = BUTTON_PLAY; | ||
532 | break; | ||
533 | |||
534 | #elif (CONFIG_KEYPAD == IRIVER_H100_PAD) || (CONFIG_KEYPAD == IRIVER_H300_PAD) | ||
535 | case SDLK_t: | ||
536 | if(pressed) | ||
537 | switch(_remote_type) | ||
538 | { | ||
539 | case REMOTETYPE_UNPLUGGED: | ||
540 | _remote_type=REMOTETYPE_H100_LCD; | ||
541 | DEBUGF("Changed remote type to H100\n"); | ||
542 | break; | ||
543 | case REMOTETYPE_H100_LCD: | ||
544 | _remote_type=REMOTETYPE_H300_LCD; | ||
545 | DEBUGF("Changed remote type to H300\n"); | ||
546 | break; | ||
547 | case REMOTETYPE_H300_LCD: | ||
548 | _remote_type=REMOTETYPE_H300_NONLCD; | ||
549 | DEBUGF("Changed remote type to H300 NON-LCD\n"); | ||
550 | break; | ||
551 | case REMOTETYPE_H300_NONLCD: | ||
552 | _remote_type=REMOTETYPE_UNPLUGGED; | ||
553 | DEBUGF("Changed remote type to none\n"); | ||
554 | break; | ||
555 | } | ||
556 | break; | ||
557 | case SDLK_KP4: | ||
558 | case SDLK_LEFT: | ||
559 | new_btn = BUTTON_LEFT; | ||
560 | break; | ||
561 | case SDLK_KP6: | ||
562 | case SDLK_RIGHT: | ||
563 | new_btn = BUTTON_RIGHT; | ||
564 | break; | ||
565 | case SDLK_KP8: | ||
566 | case SDLK_UP: | ||
567 | new_btn = BUTTON_UP; | ||
568 | break; | ||
569 | case SDLK_KP2: | ||
570 | case SDLK_DOWN: | ||
571 | new_btn = BUTTON_DOWN; | ||
572 | break; | ||
573 | case SDLK_KP_PLUS: | ||
574 | case SDLK_F8: | ||
575 | new_btn = BUTTON_ON; | ||
576 | break; | ||
577 | case SDLK_KP_ENTER: | ||
578 | case SDLK_RETURN: | ||
579 | case SDLK_a: | ||
580 | new_btn = BUTTON_OFF; | ||
581 | break; | ||
582 | case SDLK_KP_DIVIDE: | ||
583 | case SDLK_F1: | ||
584 | new_btn = BUTTON_REC; | ||
585 | break; | ||
586 | case SDLK_KP5: | ||
587 | case SDLK_SPACE: | ||
588 | new_btn = BUTTON_SELECT; | ||
589 | break; | ||
590 | case SDLK_KP_PERIOD: | ||
591 | case SDLK_INSERT: | ||
592 | new_btn = BUTTON_MODE; | ||
593 | break; | ||
594 | |||
595 | #elif CONFIG_KEYPAD == IRIVER_IFP7XX_PAD | ||
596 | case SDLK_KP4: | ||
597 | case SDLK_LEFT: | ||
598 | new_btn = BUTTON_LEFT; | ||
599 | break; | ||
600 | case SDLK_KP6: | ||
601 | case SDLK_RIGHT: | ||
602 | new_btn = BUTTON_RIGHT; | ||
603 | break; | ||
604 | case SDLK_KP8: | ||
605 | case SDLK_UP: | ||
606 | new_btn = BUTTON_UP; | ||
607 | break; | ||
608 | case SDLK_KP2: | ||
609 | case SDLK_DOWN: | ||
610 | new_btn = BUTTON_DOWN; | ||
611 | break; | ||
612 | case SDLK_KP_PLUS: | ||
613 | case SDLK_F8: | ||
614 | new_btn = BUTTON_PLAY; | ||
615 | break; | ||
616 | case SDLK_KP_ENTER: | ||
617 | case SDLK_RETURN: | ||
618 | case SDLK_a: | ||
619 | new_btn = BUTTON_EQ; | ||
620 | break; | ||
621 | case SDLK_KP5: | ||
622 | case SDLK_SPACE: | ||
623 | new_btn = BUTTON_SELECT; | ||
624 | break; | ||
625 | case SDLK_KP_PERIOD: | ||
626 | case SDLK_INSERT: | ||
627 | new_btn = BUTTON_MODE; | ||
628 | break; | ||
629 | |||
630 | #elif CONFIG_KEYPAD == ONDIO_PAD | ||
631 | case SDLK_KP4: | ||
632 | case SDLK_LEFT: | ||
633 | new_btn = BUTTON_LEFT; | ||
634 | break; | ||
635 | case SDLK_KP6: | ||
636 | case SDLK_RIGHT: | ||
637 | new_btn = BUTTON_RIGHT; | ||
638 | break; | ||
639 | case SDLK_KP8: | ||
640 | case SDLK_UP: | ||
641 | new_btn = BUTTON_UP; | ||
642 | break; | ||
643 | case SDLK_KP2: | ||
644 | case SDLK_DOWN: | ||
645 | new_btn = BUTTON_DOWN; | ||
646 | break; | ||
647 | case SDLK_KP_ENTER: | ||
648 | case SDLK_RETURN: | ||
649 | case SDLK_a: | ||
650 | new_btn = BUTTON_OFF; | ||
651 | break; | ||
652 | case SDLK_KP_PERIOD: | ||
653 | case SDLK_INSERT: | ||
654 | new_btn = BUTTON_MENU; | ||
655 | break; | ||
656 | |||
657 | #elif CONFIG_KEYPAD == PLAYER_PAD | ||
658 | case SDLK_KP4: | ||
659 | case SDLK_LEFT: | ||
660 | new_btn = BUTTON_LEFT; | ||
661 | break; | ||
662 | case SDLK_KP6: | ||
663 | case SDLK_RIGHT: | ||
664 | new_btn = BUTTON_RIGHT; | ||
665 | break; | ||
666 | case SDLK_KP8: | ||
667 | case SDLK_UP: | ||
668 | new_btn = BUTTON_PLAY; | ||
669 | break; | ||
670 | case SDLK_KP2: | ||
671 | case SDLK_DOWN: | ||
672 | new_btn = BUTTON_STOP; | ||
673 | break; | ||
674 | case SDLK_KP_PLUS: | ||
675 | case SDLK_F8: | ||
676 | new_btn = BUTTON_ON; | ||
677 | break; | ||
678 | case SDLK_KP_PERIOD: | ||
679 | case SDLK_INSERT: | ||
680 | new_btn = BUTTON_MENU; | ||
681 | break; | ||
682 | |||
683 | #elif CONFIG_KEYPAD == RECORDER_PAD | ||
684 | case SDLK_KP4: | ||
685 | case SDLK_LEFT: | ||
686 | new_btn = BUTTON_LEFT; | ||
687 | break; | ||
688 | case SDLK_KP6: | ||
689 | case SDLK_RIGHT: | ||
690 | new_btn = BUTTON_RIGHT; | ||
691 | break; | ||
692 | case SDLK_KP8: | ||
693 | case SDLK_UP: | ||
694 | new_btn = BUTTON_UP; | ||
695 | break; | ||
696 | case SDLK_KP2: | ||
697 | case SDLK_DOWN: | ||
698 | new_btn = BUTTON_DOWN; | ||
699 | break; | ||
700 | case SDLK_KP_PLUS: | ||
701 | case SDLK_F8: | ||
702 | new_btn = BUTTON_ON; | ||
703 | break; | ||
704 | case SDLK_KP_ENTER: | ||
705 | case SDLK_RETURN: | ||
706 | case SDLK_a: | ||
707 | new_btn = BUTTON_OFF; | ||
708 | break; | ||
709 | case SDLK_KP_DIVIDE: | ||
710 | case SDLK_F1: | ||
711 | new_btn = BUTTON_F1; | ||
712 | break; | ||
713 | case SDLK_KP_MULTIPLY: | ||
714 | case SDLK_F2: | ||
715 | new_btn = BUTTON_F2; | ||
716 | break; | ||
717 | case SDLK_KP_MINUS: | ||
718 | case SDLK_F3: | ||
719 | new_btn = BUTTON_F3; | ||
720 | break; | ||
721 | case SDLK_KP5: | ||
722 | case SDLK_SPACE: | ||
723 | new_btn = BUTTON_PLAY; | ||
724 | break; | ||
725 | |||
726 | #elif CONFIG_KEYPAD == ARCHOS_AV300_PAD | ||
727 | case SDLK_KP4: | ||
728 | case SDLK_LEFT: | ||
729 | new_btn = BUTTON_LEFT; | ||
730 | break; | ||
731 | case SDLK_KP6: | ||
732 | case SDLK_RIGHT: | ||
733 | new_btn = BUTTON_RIGHT; | ||
734 | break; | ||
735 | case SDLK_KP8: | ||
736 | case SDLK_UP: | ||
737 | new_btn = BUTTON_UP; | ||
738 | break; | ||
739 | case SDLK_KP2: | ||
740 | case SDLK_DOWN: | ||
741 | new_btn = BUTTON_DOWN; | ||
742 | break; | ||
743 | case SDLK_KP_PLUS: | ||
744 | case SDLK_F8: | ||
745 | new_btn = BUTTON_ON; | ||
746 | break; | ||
747 | case SDLK_KP_ENTER: | ||
748 | case SDLK_RETURN: | ||
749 | case SDLK_a: | ||
750 | new_btn = BUTTON_OFF; | ||
751 | break; | ||
752 | case SDLK_KP_DIVIDE: | ||
753 | case SDLK_F1: | ||
754 | new_btn = BUTTON_F1; | ||
755 | break; | ||
756 | case SDLK_KP_MULTIPLY: | ||
757 | case SDLK_F2: | ||
758 | new_btn = BUTTON_F2; | ||
759 | break; | ||
760 | case SDLK_KP_MINUS: | ||
761 | case SDLK_F3: | ||
762 | new_btn = BUTTON_F3; | ||
763 | break; | ||
764 | case SDLK_KP5: | ||
765 | case SDLK_SPACE: | ||
766 | new_btn = BUTTON_SELECT; | ||
767 | break; | ||
768 | |||
769 | #elif CONFIG_KEYPAD == SANSA_E200_PAD | ||
770 | case SDLK_KP4: | ||
771 | case SDLK_LEFT: | ||
772 | new_btn = BUTTON_LEFT; | ||
773 | break; | ||
774 | case SDLK_KP6: | ||
775 | case SDLK_RIGHT: | ||
776 | new_btn = BUTTON_RIGHT; | ||
777 | break; | ||
778 | case SDLK_KP8: | ||
779 | case SDLK_UP: | ||
780 | new_btn = BUTTON_SCROLL_BACK; | ||
781 | break; | ||
782 | case SDLK_KP2: | ||
783 | case SDLK_DOWN: | ||
784 | new_btn = BUTTON_SCROLL_FWD; | ||
785 | break; | ||
786 | case SDLK_KP9: | ||
787 | case SDLK_PAGEUP: | ||
788 | new_btn = BUTTON_UP; | ||
789 | break; | ||
790 | case SDLK_KP3: | ||
791 | case SDLK_PAGEDOWN: | ||
792 | new_btn = BUTTON_DOWN; | ||
793 | break; | ||
794 | case SDLK_KP1: | ||
795 | case SDLK_HOME: | ||
796 | new_btn = BUTTON_POWER; | ||
797 | break; | ||
798 | case SDLK_KP7: | ||
799 | case SDLK_END: | ||
800 | new_btn = BUTTON_REC; | ||
801 | break; | ||
802 | case SDLK_KP5: | ||
803 | case SDLK_SPACE: | ||
804 | new_btn = BUTTON_SELECT; | ||
805 | break; | ||
806 | |||
807 | #elif CONFIG_KEYPAD == SANSA_C200_PAD | ||
808 | case SDLK_KP4: | ||
809 | case SDLK_LEFT: | ||
810 | new_btn = BUTTON_LEFT; | ||
811 | break; | ||
812 | case SDLK_KP6: | ||
813 | case SDLK_RIGHT: | ||
814 | new_btn = BUTTON_RIGHT; | ||
815 | break; | ||
816 | case SDLK_KP8: | ||
817 | case SDLK_UP: | ||
818 | new_btn = BUTTON_UP; | ||
819 | break; | ||
820 | case SDLK_KP2: | ||
821 | case SDLK_DOWN: | ||
822 | new_btn = BUTTON_DOWN; | ||
823 | break; | ||
824 | case SDLK_KP3: | ||
825 | new_btn = BUTTON_POWER; | ||
826 | break; | ||
827 | case SDLK_KP1: | ||
828 | new_btn = BUTTON_REC; | ||
829 | break; | ||
830 | case SDLK_KP5: | ||
831 | case SDLK_KP_ENTER: | ||
832 | case SDLK_RETURN: | ||
833 | new_btn = BUTTON_SELECT; | ||
834 | break; | ||
835 | case SDLK_KP7: | ||
836 | new_btn = BUTTON_VOL_DOWN; | ||
837 | break; | ||
838 | case SDLK_KP9: | ||
839 | new_btn = BUTTON_VOL_UP; | ||
840 | break; | ||
841 | |||
842 | #elif CONFIG_KEYPAD == MROBE500_PAD | ||
843 | case SDLK_F9: | ||
844 | new_btn = BUTTON_RC_HEART; | ||
845 | break; | ||
846 | case SDLK_F10: | ||
847 | new_btn = BUTTON_RC_MODE; | ||
848 | break; | ||
849 | case SDLK_F11: | ||
850 | new_btn = BUTTON_RC_VOL_DOWN; | ||
851 | break; | ||
852 | case SDLK_F12: | ||
853 | new_btn = BUTTON_RC_VOL_UP; | ||
854 | break; | ||
855 | case SDLK_MINUS: | ||
856 | case SDLK_LESS: | ||
857 | case SDLK_LEFTBRACKET: | ||
858 | case SDLK_KP_DIVIDE: | ||
859 | new_btn = BUTTON_LEFT; | ||
860 | break; | ||
861 | case SDLK_PLUS: | ||
862 | case SDLK_GREATER: | ||
863 | case SDLK_RIGHTBRACKET: | ||
864 | case SDLK_KP_MULTIPLY: | ||
865 | new_btn = BUTTON_RIGHT; | ||
866 | break; | ||
867 | case SDLK_PAGEUP: | ||
868 | new_btn = BUTTON_RC_PLAY; | ||
869 | break; | ||
870 | case SDLK_PAGEDOWN: | ||
871 | new_btn = BUTTON_RC_DOWN; | ||
872 | break; | ||
873 | case SDLK_F8: | ||
874 | case SDLK_ESCAPE: | ||
875 | new_btn = BUTTON_POWER; | ||
876 | break; | ||
877 | #elif CONFIG_KEYPAD == MROBE100_PAD | ||
878 | case SDLK_F9: | ||
879 | new_btn = BUTTON_RC_HEART; | ||
880 | break; | ||
881 | case SDLK_F10: | ||
882 | new_btn = BUTTON_RC_MODE; | ||
883 | break; | ||
884 | case SDLK_F11: | ||
885 | new_btn = BUTTON_RC_VOL_DOWN; | ||
886 | break; | ||
887 | case SDLK_F12: | ||
888 | new_btn = BUTTON_RC_VOL_UP; | ||
889 | break; | ||
890 | case SDLK_LEFT: | ||
891 | new_btn = BUTTON_RC_FF; | ||
892 | break; | ||
893 | case SDLK_RIGHT: | ||
894 | new_btn = BUTTON_RC_REW; | ||
895 | break; | ||
896 | case SDLK_UP: | ||
897 | new_btn = BUTTON_RC_PLAY; | ||
898 | break; | ||
899 | case SDLK_DOWN: | ||
900 | new_btn = BUTTON_RC_DOWN; | ||
901 | break; | ||
902 | case SDLK_KP1: | ||
903 | new_btn = BUTTON_DISPLAY; | ||
904 | break; | ||
905 | case SDLK_KP7: | ||
906 | new_btn = BUTTON_MENU; | ||
907 | break; | ||
908 | case SDLK_KP9: | ||
909 | new_btn = BUTTON_PLAY; | ||
910 | break; | ||
911 | case SDLK_KP4: | ||
912 | new_btn = BUTTON_LEFT; | ||
913 | break; | ||
914 | case SDLK_KP6: | ||
915 | new_btn = BUTTON_RIGHT; | ||
916 | break; | ||
917 | case SDLK_KP8: | ||
918 | new_btn = BUTTON_UP; | ||
919 | break; | ||
920 | case SDLK_KP2: | ||
921 | new_btn = BUTTON_DOWN; | ||
922 | break; | ||
923 | case SDLK_KP5: | ||
924 | case SDLK_SPACE: | ||
925 | new_btn = BUTTON_SELECT; | ||
926 | break; | ||
927 | case SDLK_KP_MULTIPLY: | ||
928 | case SDLK_F8: | ||
929 | case SDLK_ESCAPE: | ||
930 | new_btn = BUTTON_POWER; | ||
931 | break; | ||
932 | |||
933 | #elif CONFIG_KEYPAD == COWON_D2_PAD | ||
934 | case SDLK_KP_MULTIPLY: | ||
935 | case SDLK_F8: | ||
936 | case SDLK_ESCAPE: | ||
937 | case SDLK_BACKSPACE: | ||
938 | case SDLK_DELETE: | ||
939 | new_btn = BUTTON_POWER; | ||
940 | break; | ||
941 | case SDLK_KP_PLUS: | ||
942 | case SDLK_EQUALS: | ||
943 | new_btn = BUTTON_PLUS; | ||
944 | break; | ||
945 | case SDLK_KP_MINUS: | ||
946 | case SDLK_MINUS: | ||
947 | new_btn = BUTTON_MINUS; | ||
948 | break; | ||
949 | case SDLK_KP_ENTER: | ||
950 | case SDLK_RETURN: | ||
951 | case SDLK_SPACE: | ||
952 | case SDLK_INSERT: | ||
953 | new_btn = BUTTON_MENU; | ||
954 | break; | ||
955 | #elif CONFIG_KEYPAD == IAUDIO67_PAD | ||
956 | case SDLK_UP: | ||
957 | new_btn = BUTTON_RIGHT; | ||
958 | break; | ||
959 | case SDLK_DOWN: | ||
960 | new_btn = BUTTON_LEFT; | ||
961 | break; | ||
962 | case SDLK_LEFT: | ||
963 | new_btn = BUTTON_STOP; | ||
964 | break; | ||
965 | case SDLK_RETURN: | ||
966 | case SDLK_KP_ENTER: | ||
967 | case SDLK_RIGHT: | ||
968 | new_btn = BUTTON_PLAY; | ||
969 | break; | ||
970 | case SDLK_PLUS: | ||
971 | new_btn = BUTTON_VOLUP; | ||
972 | break; | ||
973 | case SDLK_MINUS: | ||
974 | new_btn = BUTTON_VOLDOWN; | ||
975 | break; | ||
976 | case SDLK_SPACE: | ||
977 | new_btn = BUTTON_MENU; | ||
978 | break; | ||
979 | case SDLK_BACKSPACE: | ||
980 | new_btn = BUTTON_POWER; | ||
981 | break; | ||
982 | #elif CONFIG_KEYPAD == CREATIVEZVM_PAD | ||
983 | case SDLK_KP1: | ||
984 | new_btn = BUTTON_BACK; | ||
985 | break; | ||
986 | case SDLK_KP3: | ||
987 | new_btn = BUTTON_MENU; | ||
988 | break; | ||
989 | case SDLK_KP7: | ||
990 | new_btn = BUTTON_CUSTOM; | ||
991 | break; | ||
992 | case SDLK_KP9: | ||
993 | new_btn = BUTTON_PLAY; | ||
994 | break; | ||
995 | case SDLK_KP4: | ||
996 | case SDLK_LEFT: | ||
997 | new_btn = BUTTON_LEFT; | ||
998 | break; | ||
999 | case SDLK_KP6: | ||
1000 | case SDLK_RIGHT: | ||
1001 | new_btn = BUTTON_RIGHT; | ||
1002 | break; | ||
1003 | case SDLK_KP8: | ||
1004 | case SDLK_UP: | ||
1005 | new_btn = BUTTON_UP; | ||
1006 | break; | ||
1007 | case SDLK_KP2: | ||
1008 | case SDLK_DOWN: | ||
1009 | new_btn = BUTTON_DOWN; | ||
1010 | break; | ||
1011 | case SDLK_KP5: | ||
1012 | case SDLK_SPACE: | ||
1013 | new_btn = BUTTON_SELECT; | ||
1014 | break; | ||
1015 | case SDLK_KP_MULTIPLY: | ||
1016 | case SDLK_F8: | ||
1017 | case SDLK_ESCAPE: | ||
1018 | new_btn = BUTTON_POWER; | ||
1019 | break; | ||
1020 | #elif CONFIG_KEYPAD == CREATIVEZV_PAD | ||
1021 | case SDLK_KP1: | ||
1022 | new_btn = BUTTON_PREV; | ||
1023 | break; | ||
1024 | case SDLK_KP3: | ||
1025 | new_btn = BUTTON_NEXT; | ||
1026 | break; | ||
1027 | case SDLK_KP7: | ||
1028 | new_btn = BUTTON_BACK; | ||
1029 | break; | ||
1030 | case SDLK_p: | ||
1031 | new_btn = BUTTON_PLAY; | ||
1032 | break; | ||
1033 | case SDLK_KP9: | ||
1034 | new_btn = BUTTON_MENU; | ||
1035 | break; | ||
1036 | case SDLK_KP4: | ||
1037 | case SDLK_LEFT: | ||
1038 | new_btn = BUTTON_LEFT; | ||
1039 | break; | ||
1040 | case SDLK_KP6: | ||
1041 | case SDLK_RIGHT: | ||
1042 | new_btn = BUTTON_RIGHT; | ||
1043 | break; | ||
1044 | case SDLK_KP8: | ||
1045 | case SDLK_UP: | ||
1046 | new_btn = BUTTON_UP; | ||
1047 | break; | ||
1048 | case SDLK_KP2: | ||
1049 | case SDLK_DOWN: | ||
1050 | new_btn = BUTTON_DOWN; | ||
1051 | break; | ||
1052 | case SDLK_KP5: | ||
1053 | case SDLK_SPACE: | ||
1054 | new_btn = BUTTON_SELECT; | ||
1055 | break; | ||
1056 | case SDLK_KP_MULTIPLY: | ||
1057 | case SDLK_F8: | ||
1058 | case SDLK_ESCAPE: | ||
1059 | new_btn = BUTTON_POWER; | ||
1060 | break; | ||
1061 | case SDLK_z: | ||
1062 | new_btn = BUTTON_VOL_DOWN; | ||
1063 | break; | ||
1064 | case SDLK_s: | ||
1065 | new_btn = BUTTON_VOL_UP; | ||
1066 | |||
1067 | #elif CONFIG_KEYPAD == MEIZU_M6SL_PAD | ||
1068 | case SDLK_KP1: | ||
1069 | new_btn = BUTTON_PREV; | ||
1070 | break; | ||
1071 | case SDLK_KP3: | ||
1072 | new_btn = BUTTON_NEXT; | ||
1073 | break; | ||
1074 | case SDLK_KP_ENTER: | ||
1075 | case SDLK_RETURN: | ||
1076 | case SDLK_a: | ||
1077 | new_btn = BUTTON_PLAY; | ||
1078 | break; | ||
1079 | case SDLK_KP_PERIOD: | ||
1080 | case SDLK_INSERT: | ||
1081 | new_btn = BUTTON_MENU; | ||
1082 | break; | ||
1083 | case SDLK_KP8: | ||
1084 | case SDLK_UP: | ||
1085 | new_btn = BUTTON_UP; | ||
1086 | break; | ||
1087 | case SDLK_KP2: | ||
1088 | case SDLK_DOWN: | ||
1089 | new_btn = BUTTON_DOWN; | ||
1090 | break; | ||
1091 | case SDLK_KP5: | ||
1092 | case SDLK_SPACE: | ||
1093 | new_btn = BUTTON_SELECT; | ||
1094 | break; | ||
1095 | #elif CONFIG_KEYPAD == SANSA_FUZE_PAD | ||
1096 | case SDLK_KP4: | ||
1097 | case SDLK_LEFT: | ||
1098 | new_btn = BUTTON_LEFT; | ||
1099 | break; | ||
1100 | case SDLK_KP6: | ||
1101 | case SDLK_RIGHT: | ||
1102 | new_btn = BUTTON_RIGHT; | ||
1103 | break; | ||
1104 | case SDLK_KP8: | ||
1105 | case SDLK_UP: | ||
1106 | new_btn = BUTTON_SCROLL_BACK; | ||
1107 | break; | ||
1108 | case SDLK_KP2: | ||
1109 | case SDLK_DOWN: | ||
1110 | new_btn = BUTTON_SCROLL_FWD; | ||
1111 | break; | ||
1112 | case SDLK_PAGEUP: | ||
1113 | case SDLK_KP9: | ||
1114 | new_btn = BUTTON_UP; | ||
1115 | break; | ||
1116 | case SDLK_PAGEDOWN: | ||
1117 | case SDLK_KP3: | ||
1118 | new_btn = BUTTON_DOWN; | ||
1119 | break; | ||
1120 | case SDLK_KP_MINUS: | ||
1121 | case SDLK_KP1: | ||
1122 | new_btn = BUTTON_POWER; | ||
1123 | break; | ||
1124 | case SDLK_KP_MULTIPLY: | ||
1125 | new_btn = BUTTON_HOME; | ||
1126 | break; | ||
1127 | case SDLK_KP5: | ||
1128 | case SDLK_SPACE: | ||
1129 | case SDLK_KP_ENTER: | ||
1130 | case SDLK_RETURN: | ||
1131 | new_btn = BUTTON_SELECT; | ||
1132 | break; | ||
1133 | #elif CONFIG_KEYPAD == SANSA_CLIP_PAD | ||
1134 | case SDLK_KP4: | ||
1135 | case SDLK_LEFT: | ||
1136 | new_btn = BUTTON_LEFT; | ||
1137 | break; | ||
1138 | case SDLK_KP6: | ||
1139 | case SDLK_RIGHT: | ||
1140 | new_btn = BUTTON_RIGHT; | ||
1141 | break; | ||
1142 | case SDLK_KP8: | ||
1143 | case SDLK_UP: | ||
1144 | new_btn = BUTTON_UP; | ||
1145 | break; | ||
1146 | case SDLK_KP2: | ||
1147 | case SDLK_DOWN: | ||
1148 | new_btn = BUTTON_DOWN; | ||
1149 | break; | ||
1150 | |||
1151 | case SDLK_INSERT: | ||
1152 | case SDLK_KP_MULTIPLY: | ||
1153 | new_btn = BUTTON_HOME; | ||
1154 | break; | ||
1155 | case SDLK_SPACE: | ||
1156 | case SDLK_KP5: | ||
1157 | new_btn = BUTTON_SELECT; | ||
1158 | break; | ||
1159 | case SDLK_PAGEDOWN: | ||
1160 | case SDLK_KP3: | ||
1161 | new_btn = BUTTON_VOL_DOWN; | ||
1162 | break; | ||
1163 | case SDLK_PAGEUP: | ||
1164 | case SDLK_KP9: | ||
1165 | new_btn = BUTTON_VOL_UP; | ||
1166 | break; | ||
1167 | case SDLK_ESCAPE: | ||
1168 | case SDLK_KP1: | ||
1169 | new_btn = BUTTON_POWER; | ||
1170 | break; | ||
1171 | #elif CONFIG_KEYPAD == SANSA_M200_PAD | ||
1172 | case SDLK_KP4: | ||
1173 | case SDLK_LEFT: | ||
1174 | new_btn = BUTTON_LEFT; | ||
1175 | break; | ||
1176 | case SDLK_KP6: | ||
1177 | case SDLK_RIGHT: | ||
1178 | new_btn = BUTTON_RIGHT; | ||
1179 | break; | ||
1180 | case SDLK_KP8: | ||
1181 | case SDLK_UP: | ||
1182 | new_btn = BUTTON_UP; | ||
1183 | break; | ||
1184 | case SDLK_KP2: | ||
1185 | case SDLK_DOWN: | ||
1186 | new_btn = BUTTON_DOWN; | ||
1187 | break; | ||
1188 | case SDLK_PLUS: | ||
1189 | new_btn = BUTTON_POWER; | ||
1190 | break; | ||
1191 | case SDLK_KP5: | ||
1192 | new_btn = BUTTON_SELECT; | ||
1193 | break; | ||
1194 | case SDLK_KP7: | ||
1195 | new_btn = BUTTON_VOL_DOWN; | ||
1196 | break; | ||
1197 | case SDLK_KP9: | ||
1198 | new_btn = BUTTON_VOL_UP; | ||
1199 | break; | ||
1200 | #elif CONFIG_KEYPAD == PHILIPS_SA9200_PAD | ||
1201 | case SDLK_KP4: | ||
1202 | case SDLK_LEFT: | ||
1203 | new_btn = BUTTON_LEFT; | ||
1204 | break; | ||
1205 | case SDLK_KP6: | ||
1206 | case SDLK_RIGHT: | ||
1207 | new_btn = BUTTON_RIGHT; | ||
1208 | break; | ||
1209 | case SDLK_KP8: | ||
1210 | case SDLK_UP: | ||
1211 | new_btn = BUTTON_UP; | ||
1212 | break; | ||
1213 | case SDLK_KP2: | ||
1214 | case SDLK_DOWN: | ||
1215 | new_btn = BUTTON_DOWN; | ||
1216 | break; | ||
1217 | case SDLK_KP1: | ||
1218 | new_btn = BUTTON_MENU; | ||
1219 | break; | ||
1220 | case SDLK_KP5: | ||
1221 | case SDLK_SPACE: | ||
1222 | new_btn = BUTTON_PLAY; | ||
1223 | break; | ||
1224 | case SDLK_KP7: | ||
1225 | new_btn = BUTTON_PREV; | ||
1226 | break; | ||
1227 | case SDLK_KP9: | ||
1228 | new_btn = BUTTON_NEXT; | ||
1229 | break; | ||
1230 | case SDLK_KP_ENTER: | ||
1231 | case SDLK_RETURN: | ||
1232 | new_btn = BUTTON_POWER; | ||
1233 | break; | ||
1234 | case SDLK_PAGEUP: | ||
1235 | new_btn = BUTTON_VOL_UP; | ||
1236 | break; | ||
1237 | case SDLK_PAGEDOWN: | ||
1238 | new_btn = BUTTON_VOL_DOWN; | ||
1239 | break; | ||
1240 | #elif CONFIG_KEYPAD == PHILIPS_HDD1630_PAD | ||
1241 | case SDLK_KP4: | ||
1242 | case SDLK_LEFT: | ||
1243 | new_btn = BUTTON_LEFT; | ||
1244 | break; | ||
1245 | case SDLK_KP6: | ||
1246 | case SDLK_RIGHT: | ||
1247 | new_btn = BUTTON_RIGHT; | ||
1248 | break; | ||
1249 | case SDLK_KP8: | ||
1250 | case SDLK_UP: | ||
1251 | new_btn = BUTTON_UP; | ||
1252 | break; | ||
1253 | case SDLK_KP2: | ||
1254 | case SDLK_DOWN: | ||
1255 | new_btn = BUTTON_DOWN; | ||
1256 | break; | ||
1257 | case SDLK_KP5: | ||
1258 | case SDLK_SPACE: | ||
1259 | new_btn = BUTTON_SELECT; | ||
1260 | break; | ||
1261 | case SDLK_KP7: | ||
1262 | case SDLK_ESCAPE: | ||
1263 | new_btn = BUTTON_POWER; | ||
1264 | break; | ||
1265 | case SDLK_KP1: | ||
1266 | new_btn = BUTTON_PLAYLIST; | ||
1267 | break; | ||
1268 | case SDLK_KP9: | ||
1269 | new_btn = BUTTON_VOL_UP; | ||
1270 | break; | ||
1271 | case SDLK_KP3: | ||
1272 | new_btn = BUTTON_VOL_DOWN; | ||
1273 | break; | ||
1274 | case SDLK_KP_MINUS: | ||
1275 | new_btn = BUTTON_MENU; | ||
1276 | break; | ||
1277 | case SDLK_KP_PLUS: | ||
1278 | new_btn = BUTTON_VIEW; | ||
1279 | break; | ||
1280 | #elif CONFIG_KEYPAD == ONDAVX747_PAD | ||
1281 | case SDLK_ESCAPE: | ||
1282 | new_btn = BUTTON_POWER; | ||
1283 | break; | ||
1284 | case SDLK_KP_PLUS: | ||
1285 | case SDLK_PLUS: | ||
1286 | case SDLK_GREATER: | ||
1287 | case SDLK_RIGHTBRACKET: | ||
1288 | case SDLK_KP_MULTIPLY: | ||
1289 | new_btn = BUTTON_VOL_UP; | ||
1290 | break; | ||
1291 | case SDLK_KP_MINUS: | ||
1292 | case SDLK_MINUS: | ||
1293 | case SDLK_LESS: | ||
1294 | case SDLK_LEFTBRACKET: | ||
1295 | case SDLK_KP_DIVIDE: | ||
1296 | new_btn = BUTTON_VOL_DOWN; | ||
1297 | break; | ||
1298 | case SDLK_KP_ENTER: | ||
1299 | case SDLK_RETURN: | ||
1300 | new_btn = BUTTON_MENU; | ||
1301 | break; | ||
1302 | #elif CONFIG_KEYPAD == ONDAVX777_PAD | ||
1303 | case SDLK_ESCAPE: | ||
1304 | new_btn = BUTTON_POWER; | ||
1305 | break; | ||
1306 | #elif CONFIG_KEYPAD == SAMSUNG_YH_PAD | ||
1307 | case SDLK_KP4: | ||
1308 | case SDLK_LEFT: | ||
1309 | new_btn = BUTTON_LEFT; | ||
1310 | break; | ||
1311 | case SDLK_KP6: | ||
1312 | case SDLK_RIGHT: | ||
1313 | new_btn = BUTTON_RIGHT; | ||
1314 | break; | ||
1315 | case SDLK_KP8: | ||
1316 | case SDLK_UP: | ||
1317 | new_btn = BUTTON_UP; | ||
1318 | break; | ||
1319 | case SDLK_KP2: | ||
1320 | case SDLK_DOWN: | ||
1321 | new_btn = BUTTON_DOWN; | ||
1322 | break; | ||
1323 | case SDLK_KP5: | ||
1324 | case SDLK_KP_ENTER: | ||
1325 | new_btn = BUTTON_PLAY; | ||
1326 | break; | ||
1327 | case SDLK_KP9: | ||
1328 | case SDLK_PAGEUP: | ||
1329 | new_btn = BUTTON_FFWD; | ||
1330 | break; | ||
1331 | #ifdef SAMSUNG_YH820 | ||
1332 | case SDLK_KP7: | ||
1333 | #else | ||
1334 | case SDLK_KP3: | ||
1335 | #endif | ||
1336 | case SDLK_PAGEDOWN: | ||
1337 | new_btn = BUTTON_REW; | ||
1338 | break; | ||
1339 | case SDLK_KP_PLUS: | ||
1340 | new_btn = BUTTON_REC; | ||
1341 | break; | ||
1342 | #elif CONFIG_KEYPAD == MINI2440_PAD | ||
1343 | case SDLK_LEFT: | ||
1344 | new_btn = BUTTON_LEFT; | ||
1345 | break; | ||
1346 | case SDLK_RIGHT: | ||
1347 | new_btn = BUTTON_RIGHT; | ||
1348 | break; | ||
1349 | case SDLK_UP: | ||
1350 | new_btn = BUTTON_UP; | ||
1351 | break; | ||
1352 | case SDLK_DOWN: | ||
1353 | new_btn = BUTTON_DOWN; | ||
1354 | break; | ||
1355 | case SDLK_F8: | ||
1356 | case SDLK_ESCAPE: | ||
1357 | new_btn = BUTTON_POWER; | ||
1358 | break; | ||
1359 | case SDLK_KP_ENTER: | ||
1360 | case SDLK_RETURN: | ||
1361 | case SDLK_a: | ||
1362 | new_btn = BUTTON_A; | ||
1363 | break; | ||
1364 | case SDLK_SPACE: | ||
1365 | new_btn = BUTTON_SELECT; | ||
1366 | break; | ||
1367 | case SDLK_KP_PERIOD: | ||
1368 | case SDLK_INSERT: | ||
1369 | new_btn = BUTTON_MENU; | ||
1370 | break; | ||
1371 | case SDLK_KP_PLUS: | ||
1372 | new_btn = BUTTON_VOL_UP; | ||
1373 | break; | ||
1374 | case SDLK_KP_MINUS: | ||
1375 | new_btn = BUTTON_VOL_DOWN; | ||
1376 | break; | ||
1377 | #elif CONFIG_KEYPAD == PBELL_VIBE500_PAD | ||
1378 | case SDLK_KP4: | ||
1379 | case SDLK_LEFT: | ||
1380 | new_btn = BUTTON_PREV; | ||
1381 | break; | ||
1382 | case SDLK_KP6: | ||
1383 | case SDLK_RIGHT: | ||
1384 | new_btn = BUTTON_NEXT; | ||
1385 | break; | ||
1386 | case SDLK_KP8: | ||
1387 | case SDLK_UP: | ||
1388 | new_btn = BUTTON_UP; | ||
1389 | break; | ||
1390 | case SDLK_KP2: | ||
1391 | case SDLK_DOWN: | ||
1392 | new_btn = BUTTON_DOWN; | ||
1393 | break; | ||
1394 | case SDLK_KP7: | ||
1395 | new_btn = BUTTON_MENU; | ||
1396 | break; | ||
1397 | case SDLK_KP9: | ||
1398 | new_btn = BUTTON_PLAY; | ||
1399 | break; | ||
1400 | case SDLK_KP5: | ||
1401 | new_btn = BUTTON_OK; | ||
1402 | break; | ||
1403 | case SDLK_KP_DIVIDE: | ||
1404 | new_btn = BUTTON_CANCEL; | ||
1405 | break; | ||
1406 | case SDLK_KP_PLUS: | ||
1407 | new_btn = BUTTON_POWER; | ||
1408 | break; | ||
1409 | case SDLK_KP_MULTIPLY: | ||
1410 | new_btn = BUTTON_REC; | ||
1411 | break; | ||
1412 | |||
1413 | #elif CONFIG_KEYPAD == MPIO_HD200_PAD | ||
1414 | case SDLK_UP: | ||
1415 | new_btn = BUTTON_PREV; | ||
1416 | break; | ||
1417 | case SDLK_DOWN: | ||
1418 | new_btn = BUTTON_NEXT; | ||
1419 | break; | ||
1420 | case SDLK_SPACE: | ||
1421 | new_btn = BUTTON_SELECT; | ||
1422 | break; | ||
1423 | case SDLK_RETURN: | ||
1424 | new_btn = BUTTON_PLAY; | ||
1425 | break; | ||
1426 | case SDLK_LEFT: | ||
1427 | new_btn = BUTTON_VOL_DOWN; | ||
1428 | break; | ||
1429 | case SDLK_RIGHT: | ||
1430 | new_btn = BUTTON_VOL_UP; | ||
1431 | break; | ||
1432 | case SDLK_ESCAPE: | ||
1433 | new_btn = BUTTON_REC; | ||
1434 | break; | ||
1435 | |||
1436 | #else | ||
1437 | #error No keymap defined! | ||
1438 | #endif /* CONFIG_KEYPAD */ | ||
1439 | case SDLK_KP0: | ||
1440 | case SDLK_F5: | ||
1441 | if(pressed) | ||
1442 | { | ||
1443 | sim_trigger_screendump(); | ||
1444 | return; | ||
1445 | } | ||
1446 | break; | ||
1447 | } | ||
1448 | |||
1449 | /* Call to make up for scrollwheel target implementation. This is | ||
1450 | * not handled in the main button.c driver, but on the target | ||
1451 | * implementation (look at button-e200.c for example if you are trying to | ||
1452 | * figure out why using button_get_data needed a hack before). | ||
1453 | */ | ||
1454 | #if defined(BUTTON_SCROLL_FWD) && defined(BUTTON_SCROLL_BACK) | ||
1455 | if((new_btn == BUTTON_SCROLL_FWD || new_btn == BUTTON_SCROLL_BACK) && | ||
1456 | pressed) | ||
1457 | { | ||
1458 | /* Clear these buttons from the data - adding them to the queue is | ||
1459 | * handled in the scrollwheel drivers for the targets. They do not | ||
1460 | * store the scroll forward/back buttons in their button data for | ||
1461 | * the button_read call. | ||
1462 | */ | ||
1463 | #ifdef HAVE_BACKLIGHT | ||
1464 | backlight_on(); | ||
1465 | #endif | ||
1466 | #ifdef HAVE_BUTTON_LIGHT | ||
1467 | buttonlight_on(); | ||
1468 | #endif | ||
1469 | queue_post(&button_queue, new_btn, 1<<24); | ||
1470 | new_btn &= ~(BUTTON_SCROLL_FWD | BUTTON_SCROLL_BACK); | ||
1471 | } | ||
1472 | #endif | ||
1473 | |||
1474 | if (pressed) | ||
1475 | btn |= new_btn; | ||
1476 | else | ||
1477 | btn &= ~new_btn; | ||
1478 | } | ||
1479 | #if defined(HAVE_BUTTON_DATA) && defined(HAVE_TOUCHSCREEN) | ||
1480 | int button_read_device(int* data) | ||
1481 | { | ||
1482 | *data = mouse_coords; | ||
1483 | #else | ||
1484 | int button_read_device(void) | ||
1485 | { | ||
1486 | #endif | ||
1487 | #ifdef HAS_BUTTON_HOLD | ||
1488 | int hold_button = button_hold(); | ||
1489 | |||
1490 | #ifdef HAVE_BACKLIGHT | ||
1491 | /* light handling */ | ||
1492 | static int hold_button_old = false; | ||
1493 | if (hold_button != hold_button_old) | ||
1494 | { | ||
1495 | hold_button_old = hold_button; | ||
1496 | backlight_hold_changed(hold_button); | ||
1497 | } | ||
1498 | #endif | ||
1499 | |||
1500 | if (hold_button) | ||
1501 | return BUTTON_NONE; | ||
1502 | else | ||
1503 | #endif | ||
1504 | gui_message_loop(); | ||
1505 | |||
1506 | return btn; | ||
1507 | } | ||
1508 | |||
1509 | |||
1510 | #ifdef HAVE_TOUCHSCREEN | ||
1511 | extern bool debug_wps; | ||
1512 | void mouse_tick_task(void) | ||
1513 | { | ||
1514 | static int last_check = 0; | ||
1515 | int x,y; | ||
1516 | if (TIME_BEFORE(current_tick, last_check+(HZ/10))) | ||
1517 | return; | ||
1518 | last_check = current_tick; | ||
1519 | if (SDL_GetMouseState(&x, &y) & SDL_BUTTON(SDL_BUTTON_LEFT)) | ||
1520 | { | ||
1521 | if(background) | ||
1522 | { | ||
1523 | x -= UI_LCD_POSX; | ||
1524 | y -= UI_LCD_POSY; | ||
1525 | |||
1526 | if(x<0 || y<0 || x>SIM_LCD_WIDTH || y>SIM_LCD_HEIGHT) | ||
1527 | return; | ||
1528 | } | ||
1529 | |||
1530 | mouse_coords = (x<<16)|y; | ||
1531 | button_event(BUTTON_TOUCHSCREEN, true); | ||
1532 | if (debug_wps) | ||
1533 | printf("Mouse at: (%d, %d)\n", x, y); | ||
1534 | } | ||
1535 | } | ||
1536 | #endif | ||
1537 | |||
1538 | void button_init_device(void) | ||
1539 | { | ||
1540 | SDL_EnableKeyRepeat(SDL_DEFAULT_REPEAT_DELAY, SDL_DEFAULT_REPEAT_INTERVAL); | ||
1541 | #ifdef HAVE_TOUCHSCREEN | ||
1542 | tick_add_task(mouse_tick_task); | ||
1543 | #endif | ||
1544 | } | ||
1545 | |||
1546 | /* Button maps: simulated key, x, y, radius, name */ | ||
1547 | /* Run sim with --mapping to get coordinates */ | ||
1548 | /* or --debugbuttons to check */ | ||
1549 | /* The First matching button is returned */ | ||
1550 | struct button_map { | ||
1551 | int button, x, y, radius; | ||
1552 | char *description; | ||
1553 | }; | ||
1554 | |||
1555 | #ifdef SANSA_FUZE | ||
1556 | struct button_map bm[] = { | ||
1557 | { SDLK_KP8, 70, 265, 35, "Scroll Back" }, | ||
1558 | { SDLK_KP9, 141, 255, 31, "Play" }, | ||
1559 | { SDLK_KP_MULTIPLY, 228, 267, 18, "Home" }, | ||
1560 | { SDLK_LEFT, 69, 329, 31, "Left" }, | ||
1561 | { SDLK_SPACE, 141, 330, 20, "Select" }, | ||
1562 | { SDLK_RIGHT, 214, 331, 23, "Right" }, | ||
1563 | { SDLK_KP3, 142, 406, 30, "Menu" }, | ||
1564 | { SDLK_DOWN, 221, 384, 24, "Scroll Fwd" }, | ||
1565 | { SDLK_KP_MINUS, 270, 299, 25, "Power" }, | ||
1566 | { SDLK_h, 269, 358, 26, "Hold" }, | ||
1567 | { 0, 0, 0, 0, "None" } | ||
1568 | }; | ||
1569 | #elif defined (SANSA_CLIP) | ||
1570 | struct button_map bm[] = { | ||
1571 | { SDLK_KP_MULTIPLY, 165, 158, 17, "Home" }, | ||
1572 | { SDLK_KP5, 102, 230, 29, "Select" }, | ||
1573 | { SDLK_KP8, 100, 179, 25, "Play" }, | ||
1574 | { SDLK_KP4, 53, 231, 21, "Left" }, | ||
1575 | { SDLK_KP6, 147, 232, 19, "Right" }, | ||
1576 | { SDLK_KP2, 105, 275, 22, "Menu" }, | ||
1577 | { 0, 0, 0, 0, "None" } | ||
1578 | }; | ||
1579 | #elif defined (SANSA_C200) || defined(SANSA_C200V2) | ||
1580 | struct button_map bm[] = { | ||
1581 | |||
1582 | { SDLK_KP7, 84, 7, 21, "Vol Down" }, | ||
1583 | { SDLK_KP9, 158, 7, 20, "Vol Up" }, | ||
1584 | { SDLK_KP1, 173, 130, 27, "Record" }, | ||
1585 | { SDLK_KP5, 277, 75, 21, "Select" }, | ||
1586 | { SDLK_KP4, 233, 75, 24, "Left" }, | ||
1587 | { SDLK_KP6, 313, 74, 18, "Right" }, | ||
1588 | { SDLK_KP8, 276, 34, 15, "Play" }, | ||
1589 | { SDLK_KP2, 277, 119, 17, "Down" }, | ||
1590 | { SDLK_KP3, 314, 113, 19, "Menu" }, | ||
1591 | { 0, 0, 0, 0, "None" } | ||
1592 | }; | ||
1593 | #elif defined (SANSA_E200V2) || defined(SANSA_E200) | ||
1594 | struct button_map bm[] = { | ||
1595 | { SDLK_KP7, 5, 92, 18, "Record" }, | ||
1596 | { SDLK_KP9, 128, 295, 43, "Play" }, | ||
1597 | { SDLK_KP4, 42, 380, 33, "Left" }, | ||
1598 | { SDLK_KP5, 129, 378, 36, "Select" }, | ||
1599 | { SDLK_KP6, 218, 383, 30, "Right" }, | ||
1600 | { SDLK_KP3, 129, 461, 29, "Down" }, | ||
1601 | { SDLK_KP1, 55, 464, 20, "Menu" }, | ||
1602 | { SDLK_KP8, 92, 338, 17, "Scroll Back" }, | ||
1603 | { SDLK_KP2, 167, 342, 17, "Scroll Fwd" }, | ||
1604 | { 0, 0, 0, 0, "None" } | ||
1605 | }; | ||
1606 | #elif defined (SANSA_M200V4) | ||
1607 | struct button_map bm[] = { | ||
1608 | { SDLK_KP_PLUS, 54, 14, 16, "Power" }, | ||
1609 | { SDLK_KP7, 96, 13, 12, "Vol Down" }, | ||
1610 | { SDLK_KP9, 139, 14, 14, "Vol Up" }, | ||
1611 | { SDLK_KP5, 260, 82, 20, "Select" }, | ||
1612 | { SDLK_KP8, 258, 35, 30, "Play" }, | ||
1613 | { SDLK_KP4, 214, 84, 25, "Left" }, | ||
1614 | { SDLK_KP6, 300, 83, 24, "Right" }, | ||
1615 | { SDLK_KP2, 262, 125, 28, "Repeat" }, | ||
1616 | { SDLK_h, 113, 151, 21, "Hold" }, | ||
1617 | { 0, 0, 0, 0, "None" } | ||
1618 | }; | ||
1619 | #elif defined (IPOD_VIDEO) | ||
1620 | struct button_map bm[] = { | ||
1621 | { SDLK_KP_PERIOD, 174, 350, 35, "Menu" }, | ||
1622 | { SDLK_KP8, 110, 380, 33, "Scroll Back" }, | ||
1623 | { SDLK_KP2, 234, 377, 34, "Scroll Fwd" }, | ||
1624 | { SDLK_KP4, 78, 438, 47, "Left" }, | ||
1625 | { SDLK_KP5, 172, 435, 43, "Select" }, | ||
1626 | { SDLK_KP6, 262, 438, 52, "Right" }, | ||
1627 | { SDLK_KP_PLUS, 172, 519, 43, "Play" }, | ||
1628 | { 0, 0, 0 , 0, "None" } | ||
1629 | }; | ||
1630 | #elif defined (IPOD_MINI) || defined(IPOD_MINI2G) | ||
1631 | struct button_map bm[] = { | ||
1632 | { SDLK_KP5, 92, 267, 29, "Select" }, | ||
1633 | { SDLK_KP4, 31, 263, 37, "Left" }, | ||
1634 | { SDLK_KP6, 150, 268, 33, "Right" }, | ||
1635 | { SDLK_KP_PERIOD, 93, 209, 30, "Menu" }, | ||
1636 | { SDLK_KP_PLUS, 93, 324, 25, "Play" }, | ||
1637 | { SDLK_KP8, 53, 220, 29, "Scroll Back" }, | ||
1638 | { SDLK_KP2, 134, 219, 31, "Scroll Fwd" }, | ||
1639 | { 0, 0, 0 , 0, "None" } | ||
1640 | }; | ||
1641 | #elif defined (IPOD_3G) | ||
1642 | struct button_map bm[] = { | ||
1643 | { SDLK_KP5, 108, 296, 26, "Select" }, | ||
1644 | { SDLK_KP8, 70, 255, 26, "Scroll Back" }, | ||
1645 | { SDLK_KP2, 149, 256, 28, "Scroll Fwd" }, | ||
1646 | { SDLK_KP4, 27, 186, 22, "Left" }, | ||
1647 | { SDLK_KP_PERIOD, 82, 185, 22, "Menu" }, | ||
1648 | { SDLK_KP_PERIOD, 133, 185, 21, "Play" }, | ||
1649 | { SDLK_KP6, 189, 188, 21, "Right" }, | ||
1650 | { 0, 0, 0 , 0, "None" } | ||
1651 | }; | ||
1652 | #elif defined (IPOD_4G) | ||
1653 | struct button_map bm[] = { | ||
1654 | { SDLK_KP5, 96, 269, 27, "Select" }, | ||
1655 | { SDLK_KP4, 39, 267, 30, "Left" }, | ||
1656 | { SDLK_KP6, 153, 270, 27, "Right" }, | ||
1657 | { SDLK_KP_PERIOD, 96, 219, 30, "Menu" }, | ||
1658 | { SDLK_KP_PLUS, 95, 326, 27, "Play" }, | ||
1659 | { SDLK_KP8, 57, 233, 29, "Scroll Back" }, | ||
1660 | { SDLK_KP2, 132, 226, 29, "Scroll Fwd" }, | ||
1661 | { 0, 0, 0 , 0, "None" } | ||
1662 | }; | ||
1663 | #elif defined (IPOD_COLOR) | ||
1664 | struct button_map bm[] = { | ||
1665 | { SDLK_KP5, 128, 362, 35, "Select" }, | ||
1666 | { SDLK_KP4, 55, 358, 38, "Left" }, | ||
1667 | { SDLK_KP6, 203, 359, 39, "Right" }, | ||
1668 | { SDLK_KP_PERIOD, 128, 282, 34, "Menu" }, | ||
1669 | { SDLK_KP_PLUS, 129, 439, 41, "Play" }, | ||
1670 | { SDLK_KP8, 76, 309, 34, "Scroll Back" }, | ||
1671 | { SDLK_KP2, 182, 311, 45, "Scroll Fwd" }, | ||
1672 | { 0, 0, 0 , 0, "None" } | ||
1673 | }; | ||
1674 | #elif defined (IPOD_1G2G) | ||
1675 | struct button_map bm[] = { | ||
1676 | { SDLK_KP5, 112, 265, 31, "Select" }, | ||
1677 | { SDLK_KP8, 74, 224, 28, "Scroll Back" }, | ||
1678 | { SDLK_KP2, 146, 228, 28, "Scroll Fwd" }, | ||
1679 | /* Dummy button to make crescent shape */ | ||
1680 | { SDLK_y, 112, 265, 76, "None" }, | ||
1681 | { SDLK_KP8, 74, 224, 28, "Scroll Back" }, | ||
1682 | { SDLK_KP2, 146, 228, 28, "Scroll Fwd" }, | ||
1683 | { SDLK_KP6, 159, 268, 64, "Right" }, | ||
1684 | { SDLK_KP4, 62, 266, 62, "Left" }, | ||
1685 | { SDLK_KP_PERIOD, 111, 216, 64, "Menu" }, | ||
1686 | { SDLK_KP_PLUS, 111, 326, 55, "Down" }, | ||
1687 | { 0, 0, 0 , 0, "None" } | ||
1688 | }; | ||
1689 | #elif defined (IPOD_NANO) | ||
1690 | struct button_map bm[] = { | ||
1691 | { SDLK_KP5, 98, 316, 37, "Select" }, | ||
1692 | { SDLK_KP4, 37, 312, 28, "Left" }, | ||
1693 | { SDLK_KP6, 160, 313, 25, "Right" }, | ||
1694 | { SDLK_KP_PERIOD,102, 256, 23, "Menu" }, | ||
1695 | { SDLK_KP_PLUS, 99, 378, 28, "Play" }, | ||
1696 | { SDLK_KP8, 58, 272, 24, "Scroll Back" }, | ||
1697 | { SDLK_KP2, 141, 274, 22, "Scroll Fwd" }, | ||
1698 | { 0, 0, 0 , 0, "None" } | ||
1699 | }; | ||
1700 | #elif defined (IPOD_NANO2G) | ||
1701 | struct button_map bm[] = { | ||
1702 | { SDLK_KP5, 118, 346, 37, "Select" }, | ||
1703 | { SDLK_KP4, 51, 345, 28, "Left" }, | ||
1704 | { SDLK_KP6, 180, 346, 26, "Right" }, | ||
1705 | { SDLK_KP_PERIOD, 114, 286, 23, "Menu" }, | ||
1706 | { SDLK_KP_PLUS, 115, 412, 27, "Down" }, | ||
1707 | { SDLK_KP8, 67, 303, 28, "Scroll Back" }, | ||
1708 | { SDLK_KP2, 163, 303, 27, "Scroll Fwd" }, | ||
1709 | { 0, 0, 0 , 0, "None" } | ||
1710 | }; | ||
1711 | #elif defined (COWON_D2) | ||
1712 | struct button_map bm[] = { | ||
1713 | { SDLK_DELETE, 51, 14, 17, "Power" }, | ||
1714 | { SDLK_h, 138, 14, 16, "Hold" }, | ||
1715 | { SDLK_MINUS, 320, 14, 10, "Minus" }, | ||
1716 | { SDLK_INSERT, 347, 13, 13, "Menu" }, | ||
1717 | { SDLK_KP_PLUS, 374, 14, 12, "Plus" }, | ||
1718 | { 0, 0, 0, 0, "None" } | ||
1719 | }; | ||
1720 | #elif defined (IAUDIO_M3) | ||
1721 | struct button_map bm[] = { | ||
1722 | { SDLK_KP5, 256, 72, 29, "Play" }, | ||
1723 | { SDLK_KP6, 255, 137, 28, "Right" }, | ||
1724 | { SDLK_KP4, 257, 201, 26, "Left" }, | ||
1725 | { SDLK_KP8, 338, 31, 27, "Up" }, | ||
1726 | { SDLK_KP2, 339, 92, 23, "Down" }, | ||
1727 | { SDLK_KP_PERIOD, 336, 50, 23, "Mode" }, | ||
1728 | { SDLK_KP_DIVIDE, 336, 147, 23, "Rec" }, | ||
1729 | { SDLK_h, 336, 212, 30, "Hold" }, | ||
1730 | /* remote */ | ||
1731 | { SDLK_SPACE, 115, 308, 20, "RC Play" }, | ||
1732 | { SDLK_RIGHT, 85, 308, 20, "RC Rew" }, | ||
1733 | { SDLK_LEFT, 143, 308, 20, "RC FF" }, | ||
1734 | { SDLK_UP, 143, 498, 20, "RC Up" }, | ||
1735 | { SDLK_DOWN, 85, 498, 20, "RC Down" }, | ||
1736 | { SDLK_INSERT, 212, 308, 30, "RC Mode" }, | ||
1737 | { SDLK_F1, 275, 308, 25, "RC Rec" }, | ||
1738 | { SDLK_KP_ENTER, 115, 498, 20, "RC Menu" }, | ||
1739 | { 0, 0, 0, 0, "None" } | ||
1740 | }; | ||
1741 | #elif defined (IAUDIO_M5) | ||
1742 | struct button_map bm[] = { | ||
1743 | { SDLK_KP_ENTER, 333, 41, 17, "Enter" }, | ||
1744 | { SDLK_h, 334, 74, 21, "Hold" }, | ||
1745 | { SDLK_KP_DIVIDE, 333, 142, 24, "Record" }, | ||
1746 | { SDLK_KP_PLUS, 332, 213, 20, "Play" }, | ||
1747 | { SDLK_KP5, 250, 291, 19, "Select" }, | ||
1748 | { SDLK_KP8, 249, 236, 32, "Up" }, | ||
1749 | { SDLK_KP4, 194, 292, 29, "Left" }, | ||
1750 | { SDLK_KP6, 297, 290, 27, "Right" }, | ||
1751 | { SDLK_KP2, 252, 335, 28, "Down" }, | ||
1752 | { 0, 0, 0, 0, "None" } | ||
1753 | }; | ||
1754 | #elif defined (IAUDIO_7) | ||
1755 | struct button_map bm[] = { | ||
1756 | { 0, 0, 0, 0, "None" } | ||
1757 | }; | ||
1758 | #elif defined (IAUDIO_X5) | ||
1759 | struct button_map bm[] = { | ||
1760 | { SDLK_KP_ENTER, 275, 38, 17, "Power" }, | ||
1761 | { SDLK_h, 274, 83, 16, "Hold" }, | ||
1762 | { SDLK_KP_DIVIDE, 276, 128, 22, "Record" }, | ||
1763 | { SDLK_KP_PLUS, 274, 186, 22, "Play" }, | ||
1764 | { SDLK_KP5, 200, 247, 16, "Select" }, | ||
1765 | { SDLK_KP8, 200, 206, 16, "Up" }, | ||
1766 | { SDLK_KP4, 163, 248, 19, "Left" }, | ||
1767 | { SDLK_KP6, 225, 247, 24, "Right" }, | ||
1768 | { SDLK_KP2, 199, 279, 20, "Down" }, | ||
1769 | { 0, 0, 0, 0, "None" } | ||
1770 | }; | ||
1771 | #elif defined (ARCHOS_PLAYER) | ||
1772 | struct button_map bm[] = { | ||
1773 | { SDLK_KP_PLUS, 79, 252, 23, "On" }, | ||
1774 | { SDLK_KP_PERIOD, 81, 310, 20, "Menu" }, | ||
1775 | { SDLK_KP8, 154, 237, 28, "Play" }, | ||
1776 | { SDLK_KP4, 121, 282, 23, "Left" }, | ||
1777 | { SDLK_KP6, 187, 282, 22, "Right" }, | ||
1778 | { SDLK_KP2, 157, 312, 20, "Down" }, | ||
1779 | { 0, 0, 0, 0, "None" } | ||
1780 | }; | ||
1781 | #elif defined (ARCHOS_RECORDER) | ||
1782 | struct button_map bm[] = { | ||
1783 | { SDLK_F1, 94, 205, 22, "F1" }, | ||
1784 | { SDLK_F2, 136, 204, 21, "F2" }, | ||
1785 | { SDLK_F3, 174, 204, 24, "F3" }, | ||
1786 | { SDLK_KP_PLUS, 75, 258, 19, "On" }, | ||
1787 | { SDLK_KP_ENTER, 76, 307, 15, "Off" }, | ||
1788 | { SDLK_KP5, 151, 290, 20, "Select" }, | ||
1789 | { SDLK_KP8, 152, 251, 23, "Up" }, | ||
1790 | { SDLK_KP4, 113, 288, 26, "Left" }, | ||
1791 | { SDLK_KP6, 189, 291, 23, "Right" }, | ||
1792 | { SDLK_KP2, 150, 327, 27, "Down" }, | ||
1793 | { 0, 0, 0, 0, "None" } | ||
1794 | }; | ||
1795 | #elif defined (ARCHOS_FMRECORDER) || defined (ARCHOS_RECORDERV2) | ||
1796 | struct button_map bm[] = { | ||
1797 | { SDLK_F1, 88, 210, 28, "F1" }, | ||
1798 | { SDLK_F2, 144, 212, 28, "F2" }, | ||
1799 | { SDLK_F3, 197, 212, 28, "F3" }, | ||
1800 | { SDLK_KP5, 144, 287, 21, "Select" }, | ||
1801 | { SDLK_KP_PLUS, 86, 320, 13, "Menu" }, | ||
1802 | { SDLK_KP_ENTER, 114, 347, 13, "Stop" }, | ||
1803 | { SDLK_y, 144, 288, 31, "None" }, | ||
1804 | { SDLK_KP8, 144, 259, 25, "Up" }, | ||
1805 | { SDLK_KP2, 144, 316, 31, "Down" }, | ||
1806 | { SDLK_KP6, 171, 287, 32, "Right" }, | ||
1807 | { SDLK_KP4, 117, 287, 31, "Left" }, | ||
1808 | { 0, 0, 0, 0, "None" } | ||
1809 | }; | ||
1810 | #elif defined (ARCHOS_ONDIOSP) || defined (ARCHOS_ONDIOFM) | ||
1811 | struct button_map bm[] = { | ||
1812 | { SDLK_KP_ENTER, 75, 23, 30, "Enter" }, | ||
1813 | { SDLK_KP8, 75, 174, 33, "KP8" }, | ||
1814 | { SDLK_KP4, 26, 186, 48, "KP4" }, | ||
1815 | { SDLK_KP6, 118, 196, 32, "KP6" }, | ||
1816 | { SDLK_KP2, 75, 234, 16, "KP2" }, | ||
1817 | { SDLK_KP_PERIOD, 54, 250, 24, "Period" }, | ||
1818 | { 0, 0, 0, 0, "None" } | ||
1819 | }; | ||
1820 | #elif defined (IRIVER_H10) | ||
1821 | struct button_map bm[] = { | ||
1822 | { SDLK_KP_PLUS, 38, 70, 37, "Power" }, | ||
1823 | { SDLK_KP4, 123, 194, 26, "Cancel" }, | ||
1824 | { SDLK_KP6, 257, 195, 34, "Select" }, | ||
1825 | { SDLK_KP8, 190, 221, 28, "Up" }, | ||
1826 | { SDLK_KP2, 192, 320, 27, "Down" }, | ||
1827 | { SDLK_KP_DIVIDE, 349, 49, 20, "Rew" }, | ||
1828 | { SDLK_KP5, 349, 96, 20, "Play" }, | ||
1829 | { SDLK_KP_MULTIPLY, 350, 141, 23, "FF" }, | ||
1830 | { 0, 0, 0, 0, "None" } | ||
1831 | }; | ||
1832 | #elif defined (IRIVER_H10_5GB) | ||
1833 | struct button_map bm[] = { | ||
1834 | { SDLK_KP_PLUS, 34, 76, 23, "Power" }, | ||
1835 | { SDLK_KP4, 106, 222, 28, "Cancel" }, | ||
1836 | { SDLK_KP6, 243, 220, 31, "Select" }, | ||
1837 | { SDLK_KP8, 176, 254, 34, "Up" }, | ||
1838 | { SDLK_KP2, 175, 371, 35, "Down" }, | ||
1839 | { SDLK_KP_DIVIDE, 319, 63, 26, "Rew" }, | ||
1840 | { SDLK_KP5, 320, 124, 26, "Play" }, | ||
1841 | { SDLK_KP_MULTIPLY, 320, 181, 32, "FF" }, | ||
1842 | { 0, 0, 0, 0, "None" } | ||
1843 | }; | ||
1844 | #elif defined (IRIVER_H120) || defined (IRIVER_H100) | ||
1845 | struct button_map bm[] = { | ||
1846 | { SDLK_KP_DIVIDE, 46, 162, 13, "Record" }, | ||
1847 | { SDLK_KP_PLUS, 327, 36, 16, "Play" }, | ||
1848 | { SDLK_KP_ENTER, 330, 99, 18, "Stop" }, | ||
1849 | { SDLK_KP_PERIOD, 330, 163, 18, "AB" }, | ||
1850 | { SDLK_KP5, 186, 227, 27, "5" }, | ||
1851 | { SDLK_KP8, 187, 185, 19, "8" }, | ||
1852 | { SDLK_KP4, 142, 229, 23, "4" }, | ||
1853 | { SDLK_KP6, 231, 229, 22, "6" }, | ||
1854 | { SDLK_KP2, 189, 272, 28, "2" }, | ||
1855 | /* Remote Buttons */ | ||
1856 | { SDLK_KP_ENTER, 250, 404, 20, "Stop" }, | ||
1857 | { SDLK_SPACE, 285, 439, 29, "Space" }, | ||
1858 | { SDLK_h, 336, 291, 24, "Hold" }, | ||
1859 | { 0, 0, 0, 0, "None" } | ||
1860 | }; | ||
1861 | #elif defined (IRIVER_H300) | ||
1862 | struct button_map bm[] = { | ||
1863 | { SDLK_KP_PLUS, 56, 335, 20, "Play" }, | ||
1864 | { SDLK_KP8, 140, 304, 29, "Up" }, | ||
1865 | { SDLK_KP_DIVIDE, 233, 331, 23, "Record" }, | ||
1866 | { SDLK_KP_ENTER, 54, 381, 24, "Stop" }, | ||
1867 | { SDLK_KP4, 100, 353, 17, "Left" }, | ||
1868 | { SDLK_KP5, 140, 351, 19, "Navi" }, | ||
1869 | { SDLK_KP6, 185, 356, 19, "Right" }, | ||
1870 | { SDLK_KP_PERIOD, 230, 380, 20, "AB" }, | ||
1871 | { SDLK_KP2, 142, 402, 24, "Down" }, | ||
1872 | { SDLK_KP_ENTER, 211, 479, 21, "Stop" }, | ||
1873 | { SDLK_KP_PLUS, 248, 513, 29, "Play" }, | ||
1874 | { 0, 0, 0, 0, "None" } | ||
1875 | }; | ||
1876 | #elif defined (MROBE_500) | ||
1877 | struct button_map bm[] = { | ||
1878 | { SDLK_KP9, 171, 609, 9, "Play" }, | ||
1879 | { SDLK_KP4, 158, 623, 9, "Left" }, | ||
1880 | { SDLK_KP6, 184, 622, 9, "Right" }, | ||
1881 | { SDLK_KP7, 171, 638, 11, "Menu" }, | ||
1882 | { 0, 0, 0, 0, "None" } | ||
1883 | }; | ||
1884 | #elif defined (MROBE_100) | ||
1885 | struct button_map bm[] = { | ||
1886 | { SDLK_KP7, 80, 233, 30, "Menu" }, | ||
1887 | { SDLK_KP8, 138, 250, 19, "Up" }, | ||
1888 | { SDLK_KP9, 201, 230, 27, "Play" }, | ||
1889 | { SDLK_KP4, 63, 305, 25, "Left" }, | ||
1890 | { SDLK_KP5, 125, 309, 28, "Select" }, | ||
1891 | { SDLK_KP6, 200, 307, 35, "Right" }, | ||
1892 | { SDLK_KP1, 52, 380, 32, "Display" }, | ||
1893 | { SDLK_KP2, 125, 363, 30, "Down" }, | ||
1894 | { SDLK_KP9, 168, 425, 10, "Play" }, | ||
1895 | { SDLK_KP4, 156, 440, 11, "Left" }, | ||
1896 | { SDLK_KP6, 180, 440, 13, "Right" }, | ||
1897 | { SDLK_KP7, 169, 452, 10, "Menu" }, | ||
1898 | { SDLK_KP_MULTIPLY, 222, 15, 16, "Power" }, | ||
1899 | { 0, 0, 0, 0, "None" } | ||
1900 | }; | ||
1901 | #elif defined (GIGABEAT_F) | ||
1902 | struct button_map bm[] = { | ||
1903 | { SDLK_KP_PLUS, 361, 187, 22, "Power" }, | ||
1904 | { SDLK_KP_PERIOD, 361, 270, 17, "Menu" }, | ||
1905 | { SDLK_KP9, 365, 345, 26, "Vol Up" }, | ||
1906 | { SDLK_KP3, 363, 433, 25, "Vol Down" }, | ||
1907 | { SDLK_KP_ENTER, 365, 520, 19, "A" }, | ||
1908 | { SDLK_KP8, 167, 458, 35, "Up" }, | ||
1909 | { SDLK_KP4, 86, 537, 29, "Left" }, | ||
1910 | { SDLK_KP5, 166, 536, 30, "Select" }, | ||
1911 | { SDLK_KP6, 248, 536, 30, "Right" }, | ||
1912 | { SDLK_KP2, 169, 617, 28, "Down" }, | ||
1913 | { 0, 0, 0, 0, "None" } | ||
1914 | }; | ||
1915 | #elif defined (GIGABEAT_S) | ||
1916 | struct button_map bm[] = { | ||
1917 | { SDLK_KP_PLUS, 416, 383, 23, "Play" }, | ||
1918 | { SDLK_KP7, 135, 442, 46, "Back" }, | ||
1919 | { SDLK_KP9, 288, 447, 35, "Menu" }, | ||
1920 | { SDLK_KP8, 214, 480, 32, "Up" }, | ||
1921 | { SDLK_KP4, 128, 558, 33, "Left" }, | ||
1922 | { SDLK_KP5, 214, 556, 34, "Select" }, | ||
1923 | { SDLK_KP6, 293, 558, 35, "Right" }, | ||
1924 | { SDLK_KP2, 214, 637, 38, "Down" }, | ||
1925 | { 0, 0, 0, 0, "None" } | ||
1926 | }; | ||
1927 | #elif defined (SAMSUNG_YH820) | ||
1928 | struct button_map bm[] = { | ||
1929 | { SDLK_KP_PLUS, 330, 53, 23, "Record" }, | ||
1930 | { SDLK_KP7, 132, 208, 21, "Left" }, | ||
1931 | { SDLK_KP5, 182, 210, 18, "Play" }, | ||
1932 | { SDLK_KP9, 234, 211, 22, "Right" }, | ||
1933 | { SDLK_KP8, 182, 260, 15, "Up" }, | ||
1934 | { SDLK_KP4, 122, 277, 29, "Menu" }, | ||
1935 | { SDLK_KP6, 238, 276, 25, "Select" }, | ||
1936 | { SDLK_KP2, 183, 321, 24, "Down" }, | ||
1937 | { 0, 0, 0, 0, "None" } | ||
1938 | }; | ||
1939 | #elif defined (SAMSUNG_YH920) || defined (SAMSUNG_YH925) | ||
1940 | struct button_map bm[] = { | ||
1941 | { SDLK_KP9, 370, 32, 15, "FF" }, | ||
1942 | { SDLK_KP5, 369, 84, 25, "Play" }, | ||
1943 | { SDLK_KP5, 367, 125, 27, "Play" }, | ||
1944 | { SDLK_KP3, 369, 188, 17, "Rew" }, | ||
1945 | { SDLK_KP_PLUS, 370, 330, 30, "Record" }, | ||
1946 | { SDLK_KP4, 146, 252, 32, "Menu" }, | ||
1947 | { SDLK_KP8, 204, 226, 27, "Up" }, | ||
1948 | { SDLK_KP6, 257, 250, 34, "Select" }, | ||
1949 | { SDLK_KP2, 205, 294, 35, "Down" }, | ||
1950 | { 0, 0, 0, 0, "None" } | ||
1951 | }; | ||
1952 | #elif defined (ONDA_VX747) || defined (ONDA_VX747P) | ||
1953 | struct button_map bm[] = { | ||
1954 | { SDLK_MINUS, 113, 583, 28, "Minus" }, | ||
1955 | { SDLK_PLUS, 227, 580, 28, "Plus" }, | ||
1956 | { SDLK_RETURN, 171, 583, 34, "Menu" }, | ||
1957 | { 0, 0, 0, 0, "None" } | ||
1958 | }; | ||
1959 | #elif defined (PHILIPS_SA9200) | ||
1960 | struct button_map bm[] = { | ||
1961 | { SDLK_KP_ENTER, 25, 155, 33, "Power" }, | ||
1962 | { SDLK_PAGEUP, 210, 98, 31, "Vol Up" }, | ||
1963 | { SDLK_PAGEDOWN, 210, 168, 34, "Vol Down" }, | ||
1964 | { SDLK_KP7, 40, 249, 26, "Prev" }, | ||
1965 | { SDLK_KP8, 110, 247, 22, "Up" }, | ||
1966 | { SDLK_KP9, 183, 249, 31, "Next" }, | ||
1967 | { SDLK_KP4, 45, 305, 25, "Left" }, | ||
1968 | { SDLK_KP5, 111, 304, 24, "Play" }, | ||
1969 | { SDLK_KP6, 183, 304, 21, "Right" }, | ||
1970 | { SDLK_KP1, 43, 377, 21, "Menu" }, | ||
1971 | { SDLK_KP2, 112, 371, 24, "Down" }, | ||
1972 | { 0, 0, 0, 0, "None" } | ||
1973 | }; | ||
1974 | #elif defined (CREATIVE_ZVM) || defined (CREATIVE_ZVM60GB) || \ | ||
1975 | defined (CREATIVE_ZV) | ||
1976 | struct button_map bm[] = { | ||
1977 | { SDLK_KP7, 52, 414, 35, "Custom" }, | ||
1978 | { SDLK_KP8, 185, 406, 55, "Up" }, | ||
1979 | { SDLK_KP9, 315, 421, 46, "Play" }, | ||
1980 | { SDLK_KP4, 122, 500, 41, "Left" }, | ||
1981 | { SDLK_KP6, 247, 493, 49, "Right" }, | ||
1982 | { SDLK_KP1, 58, 577, 49, "Back" }, | ||
1983 | { SDLK_KP2, 186, 585, 46, "Down" }, | ||
1984 | { SDLK_KP3, 311, 569, 47, "Menu" }, | ||
1985 | { 0, 0, 0, 0, "None" } | ||
1986 | }; | ||
1987 | #elif defined (MPIO_HD200) | ||
1988 | struct button_map bm[] = { | ||
1989 | { SDLK_ESCAPE, 369, 257, 20, "Rec" }, | ||
1990 | { SDLK_RETURN, 369, 305, 20, "Play/Stop" }, | ||
1991 | { SDLK_UP, 353, 168, 10, "Rew" }, | ||
1992 | { SDLK_DOWN, 353, 198, 10, "FF" }, | ||
1993 | { SDLK_SPACE, 353, 186, 10, "Select" }, | ||
1994 | { SDLK_LEFT, 123, 67, 20, "Vol Down" }, | ||
1995 | { SDLK_RIGHT, 206, 67, 20, "Vol Up" }, | ||
1996 | { SDLK_h, 369, 402, 30, "Hold" }, | ||
1997 | { 0, 0, 0, 0, "None" } | ||
1998 | }; | ||
1999 | #else | ||
2000 | struct button_map bm[] = { | ||
2001 | { 0, 0, 0, 0, ""} | ||
2002 | }; | ||
2003 | #endif | ||
2004 | |||
2005 | static int xy2button( int x, int y) | ||
2006 | { | ||
2007 | int i; | ||
2008 | extern bool debug_buttons; | ||
2009 | |||
2010 | for ( i = 0; bm[i].button; i++ ) | ||
2011 | /* check distance from center of button < radius */ | ||
2012 | if ( ( (x-bm[i].x)*(x-bm[i].x) ) + ( ( y-bm[i].y)*(y-bm[i].y) ) < bm[i].radius*bm[i].radius ) { | ||
2013 | if (debug_buttons) | ||
2014 | printf("Button: %s\n", bm[i].description ); | ||
2015 | return bm[i].button; | ||
2016 | } | ||
2017 | return 0; | ||
2018 | } | ||
diff --git a/firmware/target/hosted/sdl/button-sdl.h b/firmware/target/hosted/sdl/button-sdl.h new file mode 100644 index 0000000000..75a68c49bc --- /dev/null +++ b/firmware/target/hosted/sdl/button-sdl.h | |||
@@ -0,0 +1,32 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2009 by Thomas Martitz | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | |||
23 | #ifndef __BUTTON_SDL_H__ | ||
24 | #define __BUTTON_SDL_H__ | ||
25 | |||
26 | #include <stdbool.h> | ||
27 | #include "config.h" | ||
28 | |||
29 | bool button_hold(void); | ||
30 | void button_init_device(void); | ||
31 | |||
32 | #endif /* __BUTTON_SDL_H__ */ | ||
diff --git a/firmware/target/hosted/sdl/kernel-sdl.c b/firmware/target/hosted/sdl/kernel-sdl.c new file mode 100644 index 0000000000..d796921e35 --- /dev/null +++ b/firmware/target/hosted/sdl/kernel-sdl.c | |||
@@ -0,0 +1,162 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2002 by Felix Arends | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <stdlib.h> | ||
23 | #include <stdio.h> | ||
24 | #include <SDL.h> | ||
25 | #include <SDL_thread.h> | ||
26 | #include "memory.h" | ||
27 | #include "system-sdl.h" | ||
28 | #include "thread-sdl.h" | ||
29 | #include "kernel.h" | ||
30 | #include "thread.h" | ||
31 | #include "panic.h" | ||
32 | #include "debug.h" | ||
33 | |||
34 | static SDL_TimerID tick_timer_id; | ||
35 | long start_tick; | ||
36 | |||
37 | /* Condition to signal that "interrupts" may proceed */ | ||
38 | static SDL_cond *sim_thread_cond; | ||
39 | /* Mutex to serialize changing levels and exclude other threads while | ||
40 | * inside a handler */ | ||
41 | static SDL_mutex *sim_irq_mtx; | ||
42 | static int interrupt_level = HIGHEST_IRQ_LEVEL; | ||
43 | static int handlers_pending = 0; | ||
44 | static int status_reg = 0; | ||
45 | |||
46 | /* Nescessary logic: | ||
47 | * 1) All threads must pass unblocked | ||
48 | * 2) Current handler must always pass unblocked | ||
49 | * 3) Threads must be excluded when irq routine is running | ||
50 | * 4) No more than one handler routine should execute at a time | ||
51 | */ | ||
52 | int set_irq_level(int level) | ||
53 | { | ||
54 | SDL_LockMutex(sim_irq_mtx); | ||
55 | |||
56 | int oldlevel = interrupt_level; | ||
57 | |||
58 | if (status_reg == 0 && level == 0 && oldlevel != 0) | ||
59 | { | ||
60 | /* Not in a handler and "interrupts" are being reenabled */ | ||
61 | if (handlers_pending > 0) | ||
62 | SDL_CondSignal(sim_thread_cond); | ||
63 | } | ||
64 | |||
65 | interrupt_level = level; /* save new level */ | ||
66 | |||
67 | SDL_UnlockMutex(sim_irq_mtx); | ||
68 | return oldlevel; | ||
69 | } | ||
70 | |||
71 | void sim_enter_irq_handler(void) | ||
72 | { | ||
73 | SDL_LockMutex(sim_irq_mtx); | ||
74 | handlers_pending++; | ||
75 | |||
76 | if(interrupt_level != 0) | ||
77 | { | ||
78 | /* "Interrupts" are disabled. Wait for reenable */ | ||
79 | SDL_CondWait(sim_thread_cond, sim_irq_mtx); | ||
80 | } | ||
81 | |||
82 | status_reg = 1; | ||
83 | } | ||
84 | |||
85 | void sim_exit_irq_handler(void) | ||
86 | { | ||
87 | if (--handlers_pending > 0) | ||
88 | SDL_CondSignal(sim_thread_cond); | ||
89 | |||
90 | status_reg = 0; | ||
91 | SDL_UnlockMutex(sim_irq_mtx); | ||
92 | } | ||
93 | |||
94 | static bool sim_kernel_init(void) | ||
95 | { | ||
96 | sim_irq_mtx = SDL_CreateMutex(); | ||
97 | if (sim_irq_mtx == NULL) | ||
98 | { | ||
99 | panicf("Cannot create sim_handler_mtx\n"); | ||
100 | return false; | ||
101 | } | ||
102 | |||
103 | sim_thread_cond = SDL_CreateCond(); | ||
104 | if (sim_thread_cond == NULL) | ||
105 | { | ||
106 | panicf("Cannot create sim_thread_cond\n"); | ||
107 | return false; | ||
108 | } | ||
109 | |||
110 | return true; | ||
111 | } | ||
112 | |||
113 | void sim_kernel_shutdown(void) | ||
114 | { | ||
115 | SDL_RemoveTimer(tick_timer_id); | ||
116 | SDL_DestroyMutex(sim_irq_mtx); | ||
117 | SDL_DestroyCond(sim_thread_cond); | ||
118 | } | ||
119 | |||
120 | Uint32 tick_timer(Uint32 interval, void *param) | ||
121 | { | ||
122 | long new_tick; | ||
123 | |||
124 | (void) interval; | ||
125 | (void) param; | ||
126 | |||
127 | new_tick = (SDL_GetTicks() - start_tick) / (1000/HZ); | ||
128 | |||
129 | while(new_tick != current_tick) | ||
130 | { | ||
131 | sim_enter_irq_handler(); | ||
132 | |||
133 | /* Run through the list of tick tasks - increments tick | ||
134 | * on each iteration. */ | ||
135 | call_tick_tasks(); | ||
136 | |||
137 | sim_exit_irq_handler(); | ||
138 | } | ||
139 | |||
140 | return 1; | ||
141 | } | ||
142 | |||
143 | void tick_start(unsigned int interval_in_ms) | ||
144 | { | ||
145 | if (!sim_kernel_init()) | ||
146 | { | ||
147 | panicf("Could not initialize kernel!"); | ||
148 | exit(-1); | ||
149 | } | ||
150 | |||
151 | if (tick_timer_id != NULL) | ||
152 | { | ||
153 | SDL_RemoveTimer(tick_timer_id); | ||
154 | tick_timer_id = NULL; | ||
155 | } | ||
156 | else | ||
157 | { | ||
158 | start_tick = SDL_GetTicks(); | ||
159 | } | ||
160 | |||
161 | tick_timer_id = SDL_AddTimer(interval_in_ms, tick_timer, NULL); | ||
162 | } | ||
diff --git a/firmware/target/hosted/sdl/lcd-bitmap.c b/firmware/target/hosted/sdl/lcd-bitmap.c new file mode 100644 index 0000000000..6dfbffff37 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-bitmap.c | |||
@@ -0,0 +1,416 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include "debug.h" | ||
23 | #include "sim-ui-defines.h" | ||
24 | #include "system.h" | ||
25 | #include "lcd-sdl.h" | ||
26 | #include "screendump.h" | ||
27 | |||
28 | SDL_Surface* lcd_surface; | ||
29 | |||
30 | #if LCD_DEPTH <= 8 | ||
31 | #ifdef HAVE_BACKLIGHT | ||
32 | SDL_Color lcd_bl_color_dark = {RED_CMP(LCD_BL_DARKCOLOR), | ||
33 | GREEN_CMP(LCD_BL_DARKCOLOR), | ||
34 | BLUE_CMP(LCD_BL_DARKCOLOR), 0}; | ||
35 | SDL_Color lcd_bl_color_bright = {RED_CMP(LCD_BL_BRIGHTCOLOR), | ||
36 | GREEN_CMP(LCD_BL_BRIGHTCOLOR), | ||
37 | BLUE_CMP(LCD_BL_BRIGHTCOLOR), 0}; | ||
38 | #ifdef HAVE_LCD_SPLIT | ||
39 | SDL_Color lcd_bl_color2_dark = {RED_CMP(LCD_BL_DARKCOLOR_2), | ||
40 | GREEN_CMP(LCD_BL_DARKCOLOR_2), | ||
41 | BLUE_CMP(LCD_BL_DARKCOLOR_2), 0}; | ||
42 | SDL_Color lcd_bl_color2_bright = {RED_CMP(LCD_BL_BRIGHTCOLOR_2), | ||
43 | GREEN_CMP(LCD_BL_BRIGHTCOLOR_2), | ||
44 | BLUE_CMP(LCD_BL_BRIGHTCOLOR_2), 0}; | ||
45 | #endif | ||
46 | #endif /* HAVE_BACKLIGHT */ | ||
47 | SDL_Color lcd_color_dark = {RED_CMP(LCD_DARKCOLOR), | ||
48 | GREEN_CMP(LCD_DARKCOLOR), | ||
49 | BLUE_CMP(LCD_DARKCOLOR), 0}; | ||
50 | SDL_Color lcd_color_bright = {RED_CMP(LCD_BRIGHTCOLOR), | ||
51 | GREEN_CMP(LCD_BRIGHTCOLOR), | ||
52 | BLUE_CMP(LCD_BRIGHTCOLOR), 0}; | ||
53 | #ifdef HAVE_LCD_SPLIT | ||
54 | SDL_Color lcd_color2_dark = {RED_CMP(LCD_DARKCOLOR_2), | ||
55 | GREEN_CMP(LCD_DARKCOLOR_2), | ||
56 | BLUE_CMP(LCD_DARKCOLOR_2), 0}; | ||
57 | SDL_Color lcd_color2_bright = {RED_CMP(LCD_BRIGHTCOLOR_2), | ||
58 | GREEN_CMP(LCD_BRIGHTCOLOR_2), | ||
59 | BLUE_CMP(LCD_BRIGHTCOLOR_2), 0}; | ||
60 | #endif | ||
61 | |||
62 | #ifdef HAVE_LCD_SPLIT | ||
63 | #define NUM_SHADES 128 | ||
64 | #else | ||
65 | #define NUM_SHADES 129 | ||
66 | #endif | ||
67 | |||
68 | #else /* LCD_DEPTH > 8 */ | ||
69 | |||
70 | #ifdef HAVE_TRANSFLECTIVE_LCD | ||
71 | #define BACKLIGHT_OFF_ALPHA 85 /* 1/3 brightness */ | ||
72 | #else | ||
73 | #define BACKLIGHT_OFF_ALPHA 0 /* pitch black */ | ||
74 | #endif | ||
75 | |||
76 | #endif /* LCD_DEPTH */ | ||
77 | |||
78 | #if LCD_DEPTH < 8 | ||
79 | unsigned long (*lcd_ex_getpixel)(int, int) = NULL; | ||
80 | #endif /* LCD_DEPTH < 8 */ | ||
81 | |||
82 | #if LCD_DEPTH == 2 | ||
83 | /* Only defined for positive, non-split LCD for now */ | ||
84 | static const unsigned char colorindex[4] = {128, 85, 43, 0}; | ||
85 | #endif | ||
86 | |||
87 | static unsigned long get_lcd_pixel(int x, int y) | ||
88 | { | ||
89 | #if LCD_DEPTH == 1 | ||
90 | #ifdef HAVE_NEGATIVE_LCD | ||
91 | return (lcd_framebuffer[y/8][x] & (1 << (y & 7))) ? (NUM_SHADES-1) : 0; | ||
92 | #else | ||
93 | return (lcd_framebuffer[y/8][x] & (1 << (y & 7))) ? 0 : (NUM_SHADES-1); | ||
94 | #endif | ||
95 | #elif LCD_DEPTH == 2 | ||
96 | #if LCD_PIXELFORMAT == HORIZONTAL_PACKING | ||
97 | return colorindex[(lcd_framebuffer[y][x/4] >> (2 * (~x & 3))) & 3]; | ||
98 | #elif LCD_PIXELFORMAT == VERTICAL_PACKING | ||
99 | return colorindex[(lcd_framebuffer[y/4][x] >> (2 * (y & 3))) & 3]; | ||
100 | #elif LCD_PIXELFORMAT == VERTICAL_INTERLEAVED | ||
101 | unsigned bits = (lcd_framebuffer[y/8][x] >> (y & 7)) & 0x0101; | ||
102 | return colorindex[(bits | (bits >> 7)) & 3]; | ||
103 | #endif | ||
104 | #elif LCD_DEPTH == 16 | ||
105 | #if LCD_PIXELFORMAT == RGB565SWAPPED | ||
106 | unsigned bits = lcd_framebuffer[y][x]; | ||
107 | return (bits >> 8) | (bits << 8); | ||
108 | #else | ||
109 | #if defined(LCD_STRIDEFORMAT) && LCD_STRIDEFORMAT == VERTICAL_STRIDE | ||
110 | return *(&lcd_framebuffer[0][0]+LCD_HEIGHT*x+y); | ||
111 | #else | ||
112 | return lcd_framebuffer[y][x]; | ||
113 | #endif | ||
114 | #endif | ||
115 | #endif | ||
116 | } | ||
117 | |||
118 | void lcd_update(void) | ||
119 | { | ||
120 | /* update a full screen rect */ | ||
121 | lcd_update_rect(0, 0, LCD_WIDTH, LCD_HEIGHT); | ||
122 | } | ||
123 | |||
124 | void lcd_update_rect(int x_start, int y_start, int width, int height) | ||
125 | { | ||
126 | sdl_update_rect(lcd_surface, x_start, y_start, width, height, | ||
127 | LCD_WIDTH, LCD_HEIGHT, get_lcd_pixel); | ||
128 | sdl_gui_update(lcd_surface, x_start, y_start, width, | ||
129 | height + LCD_SPLIT_LINES, SIM_LCD_WIDTH, SIM_LCD_HEIGHT, | ||
130 | background ? UI_LCD_POSX : 0, background? UI_LCD_POSY : 0); | ||
131 | } | ||
132 | |||
133 | #ifdef HAVE_BACKLIGHT | ||
134 | void sim_backlight(int value) | ||
135 | { | ||
136 | #if LCD_DEPTH <= 8 | ||
137 | if (value > 0) { | ||
138 | sdl_set_gradient(lcd_surface, &lcd_bl_color_dark, | ||
139 | &lcd_bl_color_bright, 0, NUM_SHADES); | ||
140 | #ifdef HAVE_LCD_SPLIT | ||
141 | sdl_set_gradient(lcd_surface, &lcd_bl_color2_dark, | ||
142 | &lcd_bl_color2_bright, NUM_SHADES, NUM_SHADES); | ||
143 | #endif | ||
144 | } else { | ||
145 | sdl_set_gradient(lcd_surface, &lcd_color_dark, | ||
146 | &lcd_color_bright, 0, NUM_SHADES); | ||
147 | #ifdef HAVE_LCD_SPLIT | ||
148 | sdl_set_gradient(lcd_surface, &lcd_color2_dark, | ||
149 | &lcd_color2_bright, NUM_SHADES, NUM_SHADES); | ||
150 | #endif | ||
151 | } | ||
152 | #else /* LCD_DEPTH > 8 */ | ||
153 | SDL_SetAlpha(lcd_surface, SDL_SRCALPHA, (value * 255) / 100); | ||
154 | #endif /* LCD_DEPTH */ | ||
155 | |||
156 | sdl_gui_update(lcd_surface, 0, 0, SIM_LCD_WIDTH, SIM_LCD_HEIGHT, | ||
157 | SIM_LCD_WIDTH, SIM_LCD_HEIGHT, | ||
158 | background ? UI_LCD_POSX : 0, background? UI_LCD_POSY : 0); | ||
159 | } | ||
160 | #endif /* HAVE_BACKLIGHT */ | ||
161 | |||
162 | /* initialise simulator lcd driver */ | ||
163 | void sim_lcd_init(void) | ||
164 | { | ||
165 | #if LCD_DEPTH == 16 | ||
166 | lcd_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, | ||
167 | SIM_LCD_WIDTH * display_zoom, | ||
168 | SIM_LCD_HEIGHT * display_zoom, | ||
169 | LCD_DEPTH, 0, 0, 0, 0); | ||
170 | #elif LCD_DEPTH <= 8 | ||
171 | lcd_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, | ||
172 | SIM_LCD_WIDTH * display_zoom, | ||
173 | SIM_LCD_HEIGHT * display_zoom, | ||
174 | 8, 0, 0, 0, 0); | ||
175 | |||
176 | #ifdef HAVE_BACKLIGHT | ||
177 | sdl_set_gradient(lcd_surface, &lcd_bl_color_dark, | ||
178 | &lcd_bl_color_bright, 0, NUM_SHADES); | ||
179 | #ifdef HAVE_LCD_SPLIT | ||
180 | sdl_set_gradient(lcd_surface, &lcd_bl_color2_dark, | ||
181 | &lcd_bl_color2_bright, NUM_SHADES, NUM_SHADES); | ||
182 | #endif | ||
183 | #else /* !HAVE_BACKLIGHT */ | ||
184 | sdl_set_gradient(lcd_surface, &lcd_color_dark, | ||
185 | &lcd_color_bright, 0, NUM_SHADES); | ||
186 | #ifdef HAVE_LCD_SPLIT | ||
187 | sdl_set_gradient(lcd_surface, &lcd_color2_dark, | ||
188 | &lcd_color2_bright, NUM_SHADES, NUM_SHADES); | ||
189 | #endif | ||
190 | #endif /* !HAVE_BACKLIGHT */ | ||
191 | #endif /* LCD_DEPTH */ | ||
192 | } | ||
193 | |||
194 | #if LCD_DEPTH < 8 | ||
195 | void sim_lcd_ex_init(unsigned long (*getpixel)(int, int)) | ||
196 | { | ||
197 | lcd_ex_getpixel = getpixel; | ||
198 | } | ||
199 | |||
200 | void sim_lcd_ex_update_rect(int x_start, int y_start, int width, int height) | ||
201 | { | ||
202 | if (lcd_ex_getpixel) { | ||
203 | sdl_update_rect(lcd_surface, x_start, y_start, width, height, | ||
204 | LCD_WIDTH, LCD_HEIGHT, lcd_ex_getpixel); | ||
205 | sdl_gui_update(lcd_surface, x_start, y_start, width, | ||
206 | height + LCD_SPLIT_LINES, SIM_LCD_WIDTH, SIM_LCD_HEIGHT, | ||
207 | background ? UI_LCD_POSX : 0, | ||
208 | background ? UI_LCD_POSY : 0); | ||
209 | } | ||
210 | } | ||
211 | #endif | ||
212 | |||
213 | #ifdef HAVE_LCD_COLOR | ||
214 | /** | ||
215 | * |R| |1.000000 -0.000001 1.402000| |Y'| | ||
216 | * |G| = |1.000000 -0.334136 -0.714136| |Pb| | ||
217 | * |B| |1.000000 1.772000 0.000000| |Pr| | ||
218 | * Scaled, normalized, rounded and tweaked to yield RGB 565: | ||
219 | * |R| |74 0 101| |Y' - 16| >> 9 | ||
220 | * |G| = |74 -24 -51| |Cb - 128| >> 8 | ||
221 | * |B| |74 128 0| |Cr - 128| >> 9 | ||
222 | */ | ||
223 | #define YFAC (74) | ||
224 | #define RVFAC (101) | ||
225 | #define GUFAC (-24) | ||
226 | #define GVFAC (-51) | ||
227 | #define BUFAC (128) | ||
228 | |||
229 | static inline int clamp(int val, int min, int max) | ||
230 | { | ||
231 | if (val < min) | ||
232 | val = min; | ||
233 | else if (val > max) | ||
234 | val = max; | ||
235 | return val; | ||
236 | } | ||
237 | |||
238 | void lcd_yuv_set_options(unsigned options) | ||
239 | { | ||
240 | (void)options; | ||
241 | } | ||
242 | |||
243 | /* Draw a partial YUV colour bitmap - similiar behavior to lcd_blit_yuv | ||
244 | in the core */ | ||
245 | void lcd_blit_yuv(unsigned char * const src[3], | ||
246 | int src_x, int src_y, int stride, | ||
247 | int x, int y, int width, int height) | ||
248 | { | ||
249 | const unsigned char *ysrc, *usrc, *vsrc; | ||
250 | int linecounter; | ||
251 | fb_data *dst, *row_end; | ||
252 | long z; | ||
253 | |||
254 | /* width and height must be >= 2 and an even number */ | ||
255 | width &= ~1; | ||
256 | linecounter = height >> 1; | ||
257 | |||
258 | #if LCD_WIDTH >= LCD_HEIGHT | ||
259 | dst = &lcd_framebuffer[y][x]; | ||
260 | row_end = dst + width; | ||
261 | #else | ||
262 | dst = &lcd_framebuffer[x][LCD_WIDTH - y - 1]; | ||
263 | row_end = dst + LCD_WIDTH * width; | ||
264 | #endif | ||
265 | |||
266 | z = stride * src_y; | ||
267 | ysrc = src[0] + z + src_x; | ||
268 | usrc = src[1] + (z >> 2) + (src_x >> 1); | ||
269 | vsrc = src[2] + (usrc - src[1]); | ||
270 | |||
271 | /* stride => amount to jump from end of last row to start of next */ | ||
272 | stride -= width; | ||
273 | |||
274 | /* upsampling, YUV->RGB conversion and reduction to RGB565 in one go */ | ||
275 | |||
276 | do | ||
277 | { | ||
278 | do | ||
279 | { | ||
280 | int y, cb, cr, rv, guv, bu, r, g, b; | ||
281 | |||
282 | y = YFAC*(*ysrc++ - 16); | ||
283 | cb = *usrc++ - 128; | ||
284 | cr = *vsrc++ - 128; | ||
285 | |||
286 | rv = RVFAC*cr; | ||
287 | guv = GUFAC*cb + GVFAC*cr; | ||
288 | bu = BUFAC*cb; | ||
289 | |||
290 | r = y + rv; | ||
291 | g = y + guv; | ||
292 | b = y + bu; | ||
293 | |||
294 | if ((unsigned)(r | g | b) > 64*256-1) | ||
295 | { | ||
296 | r = clamp(r, 0, 64*256-1); | ||
297 | g = clamp(g, 0, 64*256-1); | ||
298 | b = clamp(b, 0, 64*256-1); | ||
299 | } | ||
300 | |||
301 | *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9); | ||
302 | |||
303 | #if LCD_WIDTH >= LCD_HEIGHT | ||
304 | dst++; | ||
305 | #else | ||
306 | dst += LCD_WIDTH; | ||
307 | #endif | ||
308 | |||
309 | y = YFAC*(*ysrc++ - 16); | ||
310 | r = y + rv; | ||
311 | g = y + guv; | ||
312 | b = y + bu; | ||
313 | |||
314 | if ((unsigned)(r | g | b) > 64*256-1) | ||
315 | { | ||
316 | r = clamp(r, 0, 64*256-1); | ||
317 | g = clamp(g, 0, 64*256-1); | ||
318 | b = clamp(b, 0, 64*256-1); | ||
319 | } | ||
320 | |||
321 | *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9); | ||
322 | |||
323 | #if LCD_WIDTH >= LCD_HEIGHT | ||
324 | dst++; | ||
325 | #else | ||
326 | dst += LCD_WIDTH; | ||
327 | #endif | ||
328 | } | ||
329 | while (dst < row_end); | ||
330 | |||
331 | ysrc += stride; | ||
332 | usrc -= width >> 1; | ||
333 | vsrc -= width >> 1; | ||
334 | |||
335 | #if LCD_WIDTH >= LCD_HEIGHT | ||
336 | row_end += LCD_WIDTH; | ||
337 | dst += LCD_WIDTH - width; | ||
338 | #else | ||
339 | row_end -= 1; | ||
340 | dst -= LCD_WIDTH*width + 1; | ||
341 | #endif | ||
342 | |||
343 | do | ||
344 | { | ||
345 | int y, cb, cr, rv, guv, bu, r, g, b; | ||
346 | |||
347 | y = YFAC*(*ysrc++ - 16); | ||
348 | cb = *usrc++ - 128; | ||
349 | cr = *vsrc++ - 128; | ||
350 | |||
351 | rv = RVFAC*cr; | ||
352 | guv = GUFAC*cb + GVFAC*cr; | ||
353 | bu = BUFAC*cb; | ||
354 | |||
355 | r = y + rv; | ||
356 | g = y + guv; | ||
357 | b = y + bu; | ||
358 | |||
359 | if ((unsigned)(r | g | b) > 64*256-1) | ||
360 | { | ||
361 | r = clamp(r, 0, 64*256-1); | ||
362 | g = clamp(g, 0, 64*256-1); | ||
363 | b = clamp(b, 0, 64*256-1); | ||
364 | } | ||
365 | |||
366 | *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9); | ||
367 | |||
368 | #if LCD_WIDTH >= LCD_HEIGHT | ||
369 | dst++; | ||
370 | #else | ||
371 | dst += LCD_WIDTH; | ||
372 | #endif | ||
373 | |||
374 | y = YFAC*(*ysrc++ - 16); | ||
375 | r = y + rv; | ||
376 | g = y + guv; | ||
377 | b = y + bu; | ||
378 | |||
379 | if ((unsigned)(r | g | b) > 64*256-1) | ||
380 | { | ||
381 | r = clamp(r, 0, 64*256-1); | ||
382 | g = clamp(g, 0, 64*256-1); | ||
383 | b = clamp(b, 0, 64*256-1); | ||
384 | } | ||
385 | |||
386 | *dst = LCD_RGBPACK_LCD(r >> 9, g >> 8, b >> 9); | ||
387 | |||
388 | #if LCD_WIDTH >= LCD_HEIGHT | ||
389 | dst++; | ||
390 | #else | ||
391 | dst += LCD_WIDTH; | ||
392 | #endif | ||
393 | } | ||
394 | while (dst < row_end); | ||
395 | |||
396 | ysrc += stride; | ||
397 | usrc += stride >> 1; | ||
398 | vsrc += stride >> 1; | ||
399 | |||
400 | #if LCD_WIDTH >= LCD_HEIGHT | ||
401 | row_end += LCD_WIDTH; | ||
402 | dst += LCD_WIDTH - width; | ||
403 | #else | ||
404 | row_end -= 1; | ||
405 | dst -= LCD_WIDTH*width + 1; | ||
406 | #endif | ||
407 | } | ||
408 | while (--linecounter > 0); | ||
409 | |||
410 | #if LCD_WIDTH >= LCD_HEIGHT | ||
411 | lcd_update_rect(x, y, width, height); | ||
412 | #else | ||
413 | lcd_update_rect(LCD_WIDTH - y - height, x, height, width); | ||
414 | #endif | ||
415 | } | ||
416 | #endif /* HAVE_LCD_COLOR */ | ||
diff --git a/firmware/target/hosted/sdl/lcd-bitmap.h b/firmware/target/hosted/sdl/lcd-bitmap.h new file mode 100644 index 0000000000..a898744b41 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-bitmap.h | |||
@@ -0,0 +1,35 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __LCDBITMAP_H__ | ||
23 | #define __LCDBITMAP_H__ | ||
24 | |||
25 | #include "lcd.h" | ||
26 | #include "SDL.h" | ||
27 | |||
28 | void sim_lcd_init(void); | ||
29 | #if LCD_DEPTH < 8 | ||
30 | void sim_lcd_ex_init(unsigned long (*getpixel)(int, int)); | ||
31 | void sim_lcd_ex_update_rect(int x, int y, int width, int height); | ||
32 | #endif | ||
33 | |||
34 | #endif /* #ifndef __LCDBITMAP_H__ */ | ||
35 | |||
diff --git a/firmware/target/hosted/sdl/lcd-charcells.c b/firmware/target/hosted/sdl/lcd-charcells.c new file mode 100644 index 0000000000..900cbb04dd --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-charcells.c | |||
@@ -0,0 +1,198 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <string.h> | ||
23 | #include <unistd.h> | ||
24 | #include <fcntl.h> | ||
25 | #include "system.h" | ||
26 | #include "debug.h" | ||
27 | #include "lcd.h" | ||
28 | #include "lcd-charcell.h" | ||
29 | #include "screendump.h" | ||
30 | #include "general.h" | ||
31 | |||
32 | #include "lcd-playersim.h" | ||
33 | #include "sim-ui-defines.h" | ||
34 | #include "lcd-sdl.h" | ||
35 | |||
36 | /* can't include file.h here */ | ||
37 | #ifndef MAX_PATH | ||
38 | #define MAX_PATH 260 | ||
39 | #endif | ||
40 | |||
41 | /* extern functions, needed for screendump() */ | ||
42 | extern int sim_creat(const char *name, mode_t mode); | ||
43 | |||
44 | SDL_Surface* lcd_surface; | ||
45 | |||
46 | SDL_Color lcd_bl_color_dark = {RED_CMP(LCD_BL_DARKCOLOR), | ||
47 | GREEN_CMP(LCD_BL_DARKCOLOR), | ||
48 | BLUE_CMP(LCD_BL_DARKCOLOR), 0}; | ||
49 | SDL_Color lcd_bl_color_bright = {RED_CMP(LCD_BL_BRIGHTCOLOR), | ||
50 | GREEN_CMP(LCD_BL_BRIGHTCOLOR), | ||
51 | BLUE_CMP(LCD_BL_BRIGHTCOLOR), 0}; | ||
52 | SDL_Color lcd_color_dark = {RED_CMP(LCD_DARKCOLOR), | ||
53 | GREEN_CMP(LCD_DARKCOLOR), | ||
54 | BLUE_CMP(LCD_DARKCOLOR), 0}; | ||
55 | SDL_Color lcd_color_bright = {RED_CMP(LCD_BRIGHTCOLOR), | ||
56 | GREEN_CMP(LCD_BRIGHTCOLOR), | ||
57 | BLUE_CMP(LCD_BRIGHTCOLOR), 0}; | ||
58 | |||
59 | |||
60 | static unsigned long get_lcd_pixel(int x, int y) | ||
61 | { | ||
62 | return sim_lcd_framebuffer[y][x]; | ||
63 | } | ||
64 | |||
65 | void sim_lcd_update_rect(int x_start, int y_start, int width, int height) | ||
66 | { | ||
67 | sdl_update_rect(lcd_surface, x_start, y_start, width, height, | ||
68 | SIM_LCD_WIDTH, SIM_LCD_HEIGHT, get_lcd_pixel); | ||
69 | sdl_gui_update(lcd_surface, x_start, y_start, width, height, | ||
70 | SIM_LCD_WIDTH, SIM_LCD_HEIGHT, | ||
71 | background ? UI_LCD_POSX : 0, background ? UI_LCD_POSY : 0); | ||
72 | } | ||
73 | |||
74 | void lcd_update(void) | ||
75 | { | ||
76 | int x, y; | ||
77 | |||
78 | for (y = 0; y < lcd_pattern_count; y++) | ||
79 | if (lcd_patterns[y].count > 0) | ||
80 | sim_lcd_define_pattern(y, lcd_patterns[y].pattern); | ||
81 | |||
82 | for (y = 0; y < LCD_HEIGHT; y++) | ||
83 | for (x = 0; x < LCD_WIDTH; x++) | ||
84 | lcd_print_char(x, y, lcd_charbuffer[y][x]); | ||
85 | |||
86 | if (lcd_cursor.visible) | ||
87 | lcd_print_char(lcd_cursor.x, lcd_cursor.y, lcd_cursor.hw_char); | ||
88 | |||
89 | sim_lcd_update_rect(0, ICON_HEIGHT, SIM_LCD_WIDTH, | ||
90 | LCD_HEIGHT*CHAR_HEIGHT*CHAR_PIXEL); | ||
91 | } | ||
92 | |||
93 | #ifdef HAVE_BACKLIGHT | ||
94 | void sim_backlight(int value) | ||
95 | { | ||
96 | if (value > 0) { | ||
97 | sdl_set_gradient(lcd_surface, &lcd_bl_color_bright, | ||
98 | &lcd_bl_color_dark, 0, (1<<LCD_DEPTH)); | ||
99 | } else { | ||
100 | sdl_set_gradient(lcd_surface, &lcd_color_bright, | ||
101 | &lcd_color_dark, 0, (1<<LCD_DEPTH)); | ||
102 | } | ||
103 | |||
104 | sim_lcd_update_rect(0, 0, SIM_LCD_WIDTH, SIM_LCD_HEIGHT); | ||
105 | } | ||
106 | #endif | ||
107 | |||
108 | /* initialise simulator lcd driver */ | ||
109 | void sim_lcd_init(void) | ||
110 | { | ||
111 | lcd_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, | ||
112 | SIM_LCD_WIDTH * display_zoom, | ||
113 | SIM_LCD_HEIGHT * display_zoom, | ||
114 | 8, 0, 0, 0, 0); | ||
115 | |||
116 | sdl_set_gradient(lcd_surface, &lcd_bl_color_bright, | ||
117 | &lcd_bl_color_dark, 0, (1<<LCD_DEPTH)); | ||
118 | } | ||
119 | |||
120 | #define BMP_COMPRESSION 0 /* BI_RGB */ | ||
121 | #define BMP_NUMCOLORS (1 << LCD_DEPTH) | ||
122 | #define BMP_BPP 1 | ||
123 | #define BMP_LINESIZE (((SIM_LCD_WIDTH + 31) / 32) * 4) | ||
124 | |||
125 | #define BMP_HEADERSIZE (54 + 4 * BMP_NUMCOLORS) | ||
126 | #define BMP_DATASIZE (BMP_LINESIZE * SIM_LCD_HEIGHT) | ||
127 | #define BMP_TOTALSIZE (BMP_HEADERSIZE + BMP_DATASIZE) | ||
128 | |||
129 | #define LE16_CONST(x) (x)&0xff, ((x)>>8)&0xff | ||
130 | #define LE32_CONST(x) (x)&0xff, ((x)>>8)&0xff, ((x)>>16)&0xff, ((x)>>24)&0xff | ||
131 | |||
132 | static const unsigned char bmpheader[] = | ||
133 | { | ||
134 | 0x42, 0x4d, /* 'BM' */ | ||
135 | LE32_CONST(BMP_TOTALSIZE), /* Total file size */ | ||
136 | 0x00, 0x00, 0x00, 0x00, /* Reserved */ | ||
137 | LE32_CONST(BMP_HEADERSIZE), /* Offset to start of pixel data */ | ||
138 | |||
139 | 0x28, 0x00, 0x00, 0x00, /* Size of (2nd) header */ | ||
140 | LE32_CONST(SIM_LCD_WIDTH), /* Width in pixels */ | ||
141 | LE32_CONST(SIM_LCD_HEIGHT), /* Height in pixels */ | ||
142 | 0x01, 0x00, /* Number of planes (always 1) */ | ||
143 | LE16_CONST(BMP_BPP), /* Bits per pixel 1/4/8/16/24 */ | ||
144 | LE32_CONST(BMP_COMPRESSION),/* Compression mode */ | ||
145 | LE32_CONST(BMP_DATASIZE), /* Size of bitmap data */ | ||
146 | 0xc4, 0x0e, 0x00, 0x00, /* Horizontal resolution (pixels/meter) */ | ||
147 | 0xc4, 0x0e, 0x00, 0x00, /* Vertical resolution (pixels/meter) */ | ||
148 | LE32_CONST(BMP_NUMCOLORS), /* Number of used colours */ | ||
149 | LE32_CONST(BMP_NUMCOLORS), /* Number of important colours */ | ||
150 | |||
151 | BMP_COLOR(LCD_BL_BRIGHTCOLOR), | ||
152 | BMP_COLOR(LCD_BL_DARKCOLOR) | ||
153 | }; | ||
154 | |||
155 | void screen_dump(void) | ||
156 | { | ||
157 | int fd; | ||
158 | char filename[MAX_PATH]; | ||
159 | int x, y; | ||
160 | static unsigned char line[BMP_LINESIZE]; | ||
161 | |||
162 | create_numbered_filename(filename, "", "dump_", ".bmp", 4 | ||
163 | IF_CNFN_NUM_(, NULL)); | ||
164 | DEBUGF("screen_dump\n"); | ||
165 | |||
166 | fd = sim_creat(filename, 0666); | ||
167 | if (fd < 0) | ||
168 | return; | ||
169 | |||
170 | write(fd, bmpheader, sizeof(bmpheader)); | ||
171 | SDL_LockSurface(lcd_surface); | ||
172 | |||
173 | /* BMP image goes bottom up */ | ||
174 | for (y = SIM_LCD_HEIGHT - 1; y >= 0; y--) | ||
175 | { | ||
176 | Uint8 *src = (Uint8 *)lcd_surface->pixels | ||
177 | + y * SIM_LCD_WIDTH * display_zoom * display_zoom; | ||
178 | unsigned char *dst = line; | ||
179 | unsigned dst_mask = 0x80; | ||
180 | |||
181 | memset(line, 0, sizeof(line)); | ||
182 | for (x = SIM_LCD_WIDTH; x > 0; x--) | ||
183 | { | ||
184 | if (*src) | ||
185 | *dst |= dst_mask; | ||
186 | src += display_zoom; | ||
187 | dst_mask >>= 1; | ||
188 | if (dst_mask == 0) | ||
189 | { | ||
190 | dst++; | ||
191 | dst_mask = 0x80; | ||
192 | } | ||
193 | } | ||
194 | write(fd, line, sizeof(line)); | ||
195 | } | ||
196 | SDL_UnlockSurface(lcd_surface); | ||
197 | close(fd); | ||
198 | } | ||
diff --git a/firmware/target/hosted/sdl/lcd-charcells.h b/firmware/target/hosted/sdl/lcd-charcells.h new file mode 100644 index 0000000000..890594f766 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-charcells.h | |||
@@ -0,0 +1,34 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __LCDCHARCELL_H__ | ||
23 | #define __LCDCHARCELL_H__ | ||
24 | |||
25 | #include "lcd.h" | ||
26 | #include "SDL.h" | ||
27 | |||
28 | #ifdef HAVE_LCD_CHARCELLS | ||
29 | void sim_lcd_init(void); | ||
30 | void screen_dump(void); | ||
31 | #endif | ||
32 | |||
33 | #endif /* #ifndef __LCDCHARCELL_H__ */ | ||
34 | |||
diff --git a/firmware/target/hosted/sdl/lcd-remote-bitmap.c b/firmware/target/hosted/sdl/lcd-remote-bitmap.c new file mode 100644 index 0000000000..9972f3e423 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-remote-bitmap.c | |||
@@ -0,0 +1,111 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include "sim-ui-defines.h" | ||
23 | #include "lcd-sdl.h" | ||
24 | #include "lcd-remote-bitmap.h" | ||
25 | #include "screendump.h" | ||
26 | #include "system.h" /* background */ | ||
27 | |||
28 | SDL_Surface *remote_surface = 0; | ||
29 | |||
30 | SDL_Color remote_bl_color_dark = {RED_CMP(LCD_REMOTE_BL_DARKCOLOR), | ||
31 | GREEN_CMP(LCD_REMOTE_BL_DARKCOLOR), | ||
32 | BLUE_CMP(LCD_REMOTE_BL_DARKCOLOR), 0}; | ||
33 | SDL_Color remote_bl_color_bright = {RED_CMP(LCD_REMOTE_BL_BRIGHTCOLOR), | ||
34 | GREEN_CMP(LCD_REMOTE_BL_BRIGHTCOLOR), | ||
35 | BLUE_CMP(LCD_REMOTE_BL_BRIGHTCOLOR), 0}; | ||
36 | SDL_Color remote_color_dark = {RED_CMP(LCD_REMOTE_DARKCOLOR), | ||
37 | GREEN_CMP(LCD_REMOTE_DARKCOLOR), | ||
38 | BLUE_CMP(LCD_REMOTE_DARKCOLOR), 0}; | ||
39 | SDL_Color remote_color_bright = {RED_CMP(LCD_REMOTE_BRIGHTCOLOR), | ||
40 | GREEN_CMP(LCD_REMOTE_BRIGHTCOLOR), | ||
41 | BLUE_CMP(LCD_REMOTE_BRIGHTCOLOR), 0}; | ||
42 | |||
43 | #define NUM_SHADES 129 | ||
44 | |||
45 | #if LCD_REMOTE_DEPTH == 2 | ||
46 | /* Only defined for positive, non-split LCD for now */ | ||
47 | static const unsigned char colorindex[4] = {128, 85, 43, 0}; | ||
48 | #endif | ||
49 | |||
50 | static unsigned long get_lcd_remote_pixel(int x, int y) | ||
51 | { | ||
52 | #if LCD_REMOTE_DEPTH == 1 | ||
53 | return lcd_remote_framebuffer[y/8][x] & (1 << (y & 7)) ? 0 : (NUM_SHADES-1); | ||
54 | #elif LCD_REMOTE_DEPTH == 2 | ||
55 | #if LCD_REMOTE_PIXELFORMAT == VERTICAL_INTERLEAVED | ||
56 | unsigned bits = (lcd_remote_framebuffer[y/8][x] >> (y & 7)) & 0x0101; | ||
57 | return colorindex[(bits | (bits >> 7)) & 3]; | ||
58 | #endif | ||
59 | #endif | ||
60 | } | ||
61 | |||
62 | void lcd_remote_update (void) | ||
63 | { | ||
64 | lcd_remote_update_rect(0, 0, LCD_REMOTE_WIDTH, LCD_REMOTE_HEIGHT); | ||
65 | } | ||
66 | |||
67 | void lcd_remote_update_rect(int x_start, int y_start, int width, int height) | ||
68 | { | ||
69 | if (remote_surface) | ||
70 | { | ||
71 | sdl_update_rect(remote_surface, x_start, y_start, width, height, | ||
72 | LCD_REMOTE_WIDTH, LCD_REMOTE_HEIGHT, get_lcd_remote_pixel); | ||
73 | sdl_gui_update(remote_surface, x_start, y_start, width, height, | ||
74 | LCD_REMOTE_WIDTH, LCD_REMOTE_HEIGHT, background ? UI_REMOTE_POSX : 0, | ||
75 | background ? UI_REMOTE_POSY : LCD_HEIGHT); | ||
76 | } | ||
77 | } | ||
78 | |||
79 | void sim_remote_backlight(int value) | ||
80 | { | ||
81 | if (remote_surface) | ||
82 | { | ||
83 | if (value > 0) | ||
84 | { | ||
85 | sdl_set_gradient(remote_surface, &remote_bl_color_dark, | ||
86 | &remote_bl_color_bright, 0, NUM_SHADES); | ||
87 | } | ||
88 | else | ||
89 | { | ||
90 | sdl_set_gradient(remote_surface, &remote_color_dark, | ||
91 | &remote_color_bright, 0, NUM_SHADES); | ||
92 | } | ||
93 | sdl_gui_update(remote_surface, 0, 0, LCD_REMOTE_WIDTH, LCD_REMOTE_HEIGHT, | ||
94 | LCD_REMOTE_WIDTH, LCD_REMOTE_HEIGHT, | ||
95 | background ? UI_REMOTE_POSX : 0, | ||
96 | background? UI_REMOTE_POSY : LCD_HEIGHT); | ||
97 | } | ||
98 | } | ||
99 | |||
100 | /* initialise simulator lcd remote driver */ | ||
101 | void sim_lcd_remote_init(void) | ||
102 | { | ||
103 | remote_surface = SDL_CreateRGBSurface(SDL_SWSURFACE, | ||
104 | LCD_REMOTE_WIDTH * display_zoom, | ||
105 | LCD_REMOTE_HEIGHT * display_zoom, | ||
106 | 8, 0, 0, 0, 0); | ||
107 | |||
108 | sdl_set_gradient(remote_surface, &remote_bl_color_dark, | ||
109 | &remote_bl_color_bright, 0, NUM_SHADES); | ||
110 | } | ||
111 | |||
diff --git a/firmware/target/hosted/sdl/lcd-remote-bitmap.h b/firmware/target/hosted/sdl/lcd-remote-bitmap.h new file mode 100644 index 0000000000..0a92ee6b79 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-remote-bitmap.h | |||
@@ -0,0 +1,32 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __LCDREMOTE_H__ | ||
23 | #define __LCDREMOTE_H__ | ||
24 | |||
25 | #include "lcd.h" | ||
26 | #include "lcd-remote.h" | ||
27 | #include "SDL.h" | ||
28 | |||
29 | void sim_lcd_remote_init(void); | ||
30 | |||
31 | #endif /* #ifndef __LCDREMOTE_H__ */ | ||
32 | |||
diff --git a/firmware/target/hosted/sdl/lcd-sdl.c b/firmware/target/hosted/sdl/lcd-sdl.c new file mode 100644 index 0000000000..15e4ba95c3 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-sdl.c | |||
@@ -0,0 +1,113 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <SDL.h> | ||
23 | #include "lcd-sdl.h" | ||
24 | #include "sim-ui-defines.h" | ||
25 | #include "system.h" /* for MIN() and MAX() */ | ||
26 | |||
27 | int display_zoom = 1; | ||
28 | |||
29 | void sdl_update_rect(SDL_Surface *surface, int x_start, int y_start, int width, | ||
30 | int height, int max_x, int max_y, | ||
31 | unsigned long (*getpixel)(int, int)) | ||
32 | { | ||
33 | int x, y; | ||
34 | int xmax, ymax; | ||
35 | SDL_Rect dest; | ||
36 | |||
37 | ymax = y_start + height; | ||
38 | xmax = x_start + width; | ||
39 | |||
40 | if(xmax > max_x) | ||
41 | xmax = max_x; | ||
42 | if(ymax >= max_y) | ||
43 | ymax = max_y; | ||
44 | |||
45 | SDL_LockSurface(surface); | ||
46 | |||
47 | dest.w = display_zoom; | ||
48 | dest.h = display_zoom; | ||
49 | |||
50 | for (x = x_start; x < xmax; x++) { | ||
51 | dest.x = x * display_zoom; | ||
52 | |||
53 | #ifdef HAVE_LCD_SPLIT | ||
54 | for (y = y_start; y < MIN(ymax, LCD_SPLIT_POS); y++) { | ||
55 | dest.y = y * display_zoom; | ||
56 | |||
57 | SDL_FillRect(surface, &dest, (Uint32)(getpixel(x, y) | 0x80)); | ||
58 | } | ||
59 | for (y = MAX(y_start, LCD_SPLIT_POS); y < ymax; y++) { | ||
60 | dest.y = (y + LCD_SPLIT_LINES) * display_zoom ; | ||
61 | |||
62 | SDL_FillRect(surface, &dest, (Uint32)getpixel(x, y)); | ||
63 | } | ||
64 | #else | ||
65 | for (y = y_start; y < ymax; y++) { | ||
66 | dest.y = y * display_zoom; | ||
67 | |||
68 | SDL_FillRect(surface, &dest, (Uint32)getpixel(x, y)); | ||
69 | } | ||
70 | #endif | ||
71 | } | ||
72 | |||
73 | SDL_UnlockSurface(surface); | ||
74 | } | ||
75 | |||
76 | void sdl_gui_update(SDL_Surface *surface, int x_start, int y_start, int width, | ||
77 | int height, int max_x, int max_y, int ui_x, int ui_y) | ||
78 | { | ||
79 | if (x_start + width > max_x) | ||
80 | width = max_x - x_start; | ||
81 | if (y_start + height > max_y) | ||
82 | height = max_y - y_start; | ||
83 | |||
84 | SDL_Rect src = {x_start * display_zoom, y_start * display_zoom, | ||
85 | width * display_zoom, height * display_zoom}; | ||
86 | SDL_Rect dest= {(ui_x + x_start) * display_zoom, | ||
87 | (ui_y + y_start) * display_zoom, | ||
88 | width * display_zoom, height * display_zoom}; | ||
89 | |||
90 | if (surface->flags & SDL_SRCALPHA) /* alpha needs a black background */ | ||
91 | SDL_FillRect(gui_surface, &dest, 0); | ||
92 | |||
93 | SDL_BlitSurface(surface, &src, gui_surface, &dest); | ||
94 | |||
95 | SDL_Flip(gui_surface); | ||
96 | } | ||
97 | |||
98 | /* set a range of bitmap indices to a gradient from startcolour to endcolour */ | ||
99 | void sdl_set_gradient(SDL_Surface *surface, SDL_Color *start, SDL_Color *end, | ||
100 | int first, int steps) | ||
101 | { | ||
102 | int i; | ||
103 | SDL_Color palette[steps]; | ||
104 | |||
105 | for (i = 0; i < steps; i++) { | ||
106 | palette[i].r = start->r + (end->r - start->r) * i / (steps - 1); | ||
107 | palette[i].g = start->g + (end->g - start->g) * i / (steps - 1); | ||
108 | palette[i].b = start->b + (end->b - start->b) * i / (steps - 1); | ||
109 | } | ||
110 | |||
111 | SDL_SetPalette(surface, SDL_LOGPAL|SDL_PHYSPAL, palette, first, steps); | ||
112 | } | ||
113 | |||
diff --git a/firmware/target/hosted/sdl/lcd-sdl.h b/firmware/target/hosted/sdl/lcd-sdl.h new file mode 100644 index 0000000000..1f57b06b95 --- /dev/null +++ b/firmware/target/hosted/sdl/lcd-sdl.h | |||
@@ -0,0 +1,43 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __LCDSDL_H__ | ||
23 | #define __LCDSDL_H__ | ||
24 | |||
25 | #include "lcd.h" | ||
26 | #include "SDL.h" | ||
27 | |||
28 | /* Default display zoom level */ | ||
29 | extern int display_zoom; | ||
30 | extern SDL_Surface *gui_surface; | ||
31 | |||
32 | void sdl_update_rect(SDL_Surface *surface, int x_start, int y_start, int width, | ||
33 | int height, int max_x, int max_y, | ||
34 | unsigned long (*getpixel)(int, int)); | ||
35 | |||
36 | void sdl_gui_update(SDL_Surface *surface, int x_start, int y_start, int width, | ||
37 | int height, int max_x, int max_y, int ui_x, int ui_y); | ||
38 | |||
39 | void sdl_set_gradient(SDL_Surface *surface, SDL_Color *start, SDL_Color *end, | ||
40 | int first, int steps); | ||
41 | |||
42 | #endif /* #ifndef __LCDSDL_H__ */ | ||
43 | |||
diff --git a/firmware/target/hosted/sdl/pcm-sdl.c b/firmware/target/hosted/sdl/pcm-sdl.c new file mode 100644 index 0000000000..1772db94f4 --- /dev/null +++ b/firmware/target/hosted/sdl/pcm-sdl.c | |||
@@ -0,0 +1,373 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2005 by Nick Lanham | ||
11 | * Copyright (C) 2010 by Thomas Martitz | ||
12 | * | ||
13 | * This program is free software; you can redistribute it and/or | ||
14 | * modify it under the terms of the GNU General Public License | ||
15 | * as published by the Free Software Foundation; either version 2 | ||
16 | * of the License, or (at your option) any later version. | ||
17 | * | ||
18 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
19 | * KIND, either express or implied. | ||
20 | * | ||
21 | ****************************************************************************/ | ||
22 | |||
23 | #include "autoconf.h" | ||
24 | |||
25 | #include <stdlib.h> | ||
26 | #include <stdbool.h> | ||
27 | #include <SDL.h> | ||
28 | #include "config.h" | ||
29 | #include "debug.h" | ||
30 | #include "sound.h" | ||
31 | #include "audiohw.h" | ||
32 | #include "system.h" | ||
33 | |||
34 | #include "pcm.h" | ||
35 | #include "pcm_sampr.h" | ||
36 | |||
37 | #ifdef DEBUG | ||
38 | #include <stdio.h> | ||
39 | extern bool debug_audio; | ||
40 | #endif | ||
41 | |||
42 | static int sim_volume = 0; | ||
43 | |||
44 | #if CONFIG_CODEC == SWCODEC | ||
45 | static int cvt_status = -1; | ||
46 | |||
47 | static Uint8* pcm_data; | ||
48 | static size_t pcm_data_size; | ||
49 | static size_t pcm_sample_bytes; | ||
50 | static size_t pcm_channel_bytes; | ||
51 | |||
52 | struct pcm_udata | ||
53 | { | ||
54 | Uint8 *stream; | ||
55 | Uint32 num_in; | ||
56 | Uint32 num_out; | ||
57 | #ifdef DEBUG | ||
58 | FILE *debug; | ||
59 | #endif | ||
60 | } udata; | ||
61 | |||
62 | static SDL_AudioSpec obtained; | ||
63 | static SDL_AudioCVT cvt; | ||
64 | |||
65 | void pcm_play_lock(void) | ||
66 | { | ||
67 | SDL_LockAudio(); | ||
68 | } | ||
69 | |||
70 | void pcm_play_unlock(void) | ||
71 | { | ||
72 | SDL_UnlockAudio(); | ||
73 | } | ||
74 | |||
75 | static void pcm_dma_apply_settings_nolock(void) | ||
76 | { | ||
77 | cvt_status = SDL_BuildAudioCVT(&cvt, AUDIO_S16SYS, 2, pcm_sampr, | ||
78 | obtained.format, obtained.channels, obtained.freq); | ||
79 | |||
80 | if (cvt_status < 0) { | ||
81 | cvt.len_ratio = (double)obtained.freq / (double)pcm_sampr; | ||
82 | } | ||
83 | } | ||
84 | |||
85 | void pcm_dma_apply_settings(void) | ||
86 | { | ||
87 | pcm_play_lock(); | ||
88 | pcm_dma_apply_settings_nolock(); | ||
89 | pcm_play_unlock(); | ||
90 | } | ||
91 | |||
92 | void pcm_play_dma_start(const void *addr, size_t size) | ||
93 | { | ||
94 | pcm_dma_apply_settings_nolock(); | ||
95 | |||
96 | pcm_data = (Uint8 *) addr; | ||
97 | pcm_data_size = size; | ||
98 | |||
99 | SDL_PauseAudio(0); | ||
100 | } | ||
101 | |||
102 | void pcm_play_dma_stop(void) | ||
103 | { | ||
104 | SDL_PauseAudio(1); | ||
105 | #ifdef DEBUG | ||
106 | if (udata.debug != NULL) { | ||
107 | fclose(udata.debug); | ||
108 | udata.debug = NULL; | ||
109 | DEBUGF("Audio debug file closed\n"); | ||
110 | } | ||
111 | #endif | ||
112 | } | ||
113 | |||
114 | void pcm_play_dma_pause(bool pause) | ||
115 | { | ||
116 | if (pause) | ||
117 | SDL_PauseAudio(1); | ||
118 | else | ||
119 | SDL_PauseAudio(0); | ||
120 | } | ||
121 | |||
122 | size_t pcm_get_bytes_waiting(void) | ||
123 | { | ||
124 | return pcm_data_size; | ||
125 | } | ||
126 | |||
127 | void write_to_soundcard(struct pcm_udata *udata) | ||
128 | { | ||
129 | #ifdef DEBUG | ||
130 | if (debug_audio && (udata->debug == NULL)) { | ||
131 | udata->debug = fopen("audiodebug.raw", "ab"); | ||
132 | DEBUGF("Audio debug file open\n"); | ||
133 | } | ||
134 | #endif | ||
135 | if (cvt.needed) { | ||
136 | Uint32 rd = udata->num_in; | ||
137 | Uint32 wr = (double)rd * cvt.len_ratio; | ||
138 | |||
139 | if (wr > udata->num_out) { | ||
140 | wr = udata->num_out; | ||
141 | rd = (double)wr / cvt.len_ratio; | ||
142 | |||
143 | if (rd > udata->num_in) | ||
144 | { | ||
145 | rd = udata->num_in; | ||
146 | wr = (double)rd * cvt.len_ratio; | ||
147 | } | ||
148 | } | ||
149 | |||
150 | if (wr == 0 || rd == 0) | ||
151 | { | ||
152 | udata->num_out = udata->num_in = 0; | ||
153 | return; | ||
154 | } | ||
155 | |||
156 | if (cvt_status > 0) { | ||
157 | cvt.len = rd * pcm_sample_bytes; | ||
158 | cvt.buf = (Uint8 *) malloc(cvt.len * cvt.len_mult); | ||
159 | |||
160 | memcpy(cvt.buf, pcm_data, cvt.len); | ||
161 | |||
162 | SDL_ConvertAudio(&cvt); | ||
163 | SDL_MixAudio(udata->stream, cvt.buf, cvt.len_cvt, sim_volume); | ||
164 | |||
165 | udata->num_in = cvt.len / pcm_sample_bytes; | ||
166 | udata->num_out = cvt.len_cvt / pcm_sample_bytes; | ||
167 | |||
168 | #ifdef DEBUG | ||
169 | if (udata->debug != NULL) { | ||
170 | fwrite(cvt.buf, sizeof(Uint8), cvt.len_cvt, udata->debug); | ||
171 | } | ||
172 | #endif | ||
173 | free(cvt.buf); | ||
174 | } | ||
175 | else { | ||
176 | /* Convert is bad, so do silence */ | ||
177 | Uint32 num = wr*obtained.channels; | ||
178 | udata->num_in = rd; | ||
179 | udata->num_out = wr; | ||
180 | |||
181 | switch (pcm_channel_bytes) | ||
182 | { | ||
183 | case 1: | ||
184 | { | ||
185 | Uint8 *stream = udata->stream; | ||
186 | while (num-- > 0) | ||
187 | *stream++ = obtained.silence; | ||
188 | break; | ||
189 | } | ||
190 | case 2: | ||
191 | { | ||
192 | Uint16 *stream = (Uint16 *)udata->stream; | ||
193 | while (num-- > 0) | ||
194 | *stream++ = obtained.silence; | ||
195 | break; | ||
196 | } | ||
197 | } | ||
198 | #ifdef DEBUG | ||
199 | if (udata->debug != NULL) { | ||
200 | fwrite(udata->stream, sizeof(Uint8), wr, udata->debug); | ||
201 | } | ||
202 | #endif | ||
203 | } | ||
204 | } else { | ||
205 | udata->num_in = udata->num_out = MIN(udata->num_in, udata->num_out); | ||
206 | SDL_MixAudio(udata->stream, pcm_data, | ||
207 | udata->num_out * pcm_sample_bytes, sim_volume); | ||
208 | #ifdef DEBUG | ||
209 | if (udata->debug != NULL) { | ||
210 | fwrite(pcm_data, sizeof(Uint8), udata->num_out * pcm_sample_bytes, | ||
211 | udata->debug); | ||
212 | } | ||
213 | #endif | ||
214 | } | ||
215 | } | ||
216 | |||
217 | void sdl_audio_callback(struct pcm_udata *udata, Uint8 *stream, int len) | ||
218 | { | ||
219 | udata->stream = stream; | ||
220 | |||
221 | /* Write what we have in the PCM buffer */ | ||
222 | if (pcm_data_size > 0) | ||
223 | goto start; | ||
224 | |||
225 | /* Audio card wants more? Get some more then. */ | ||
226 | while (len > 0) { | ||
227 | if ((ssize_t)pcm_data_size <= 0) { | ||
228 | pcm_data_size = 0; | ||
229 | |||
230 | if (pcm_callback_for_more) | ||
231 | pcm_callback_for_more(&pcm_data, &pcm_data_size); | ||
232 | } | ||
233 | |||
234 | if (pcm_data_size > 0) { | ||
235 | start: | ||
236 | udata->num_in = pcm_data_size / pcm_sample_bytes; | ||
237 | udata->num_out = len / pcm_sample_bytes; | ||
238 | |||
239 | write_to_soundcard(udata); | ||
240 | |||
241 | udata->num_in *= pcm_sample_bytes; | ||
242 | udata->num_out *= pcm_sample_bytes; | ||
243 | |||
244 | pcm_data += udata->num_in; | ||
245 | pcm_data_size -= udata->num_in; | ||
246 | udata->stream += udata->num_out; | ||
247 | len -= udata->num_out; | ||
248 | } else { | ||
249 | DEBUGF("sdl_audio_callback: No Data.\n"); | ||
250 | pcm_play_dma_stop(); | ||
251 | pcm_play_dma_stopped_callback(); | ||
252 | break; | ||
253 | } | ||
254 | } | ||
255 | } | ||
256 | |||
257 | const void * pcm_play_dma_get_peak_buffer(int *count) | ||
258 | { | ||
259 | uintptr_t addr = (uintptr_t)pcm_data; | ||
260 | *count = pcm_data_size / 4; | ||
261 | return (void *)((addr + 2) & ~3); | ||
262 | } | ||
263 | |||
264 | #ifdef HAVE_RECORDING | ||
265 | void pcm_rec_lock(void) | ||
266 | { | ||
267 | } | ||
268 | |||
269 | void pcm_rec_unlock(void) | ||
270 | { | ||
271 | } | ||
272 | |||
273 | void pcm_rec_dma_init(void) | ||
274 | { | ||
275 | } | ||
276 | |||
277 | void pcm_rec_dma_close(void) | ||
278 | { | ||
279 | } | ||
280 | |||
281 | void pcm_rec_dma_start(void *start, size_t size) | ||
282 | { | ||
283 | (void)start; | ||
284 | (void)size; | ||
285 | } | ||
286 | |||
287 | void pcm_rec_dma_stop(void) | ||
288 | { | ||
289 | } | ||
290 | |||
291 | void pcm_rec_dma_record_more(void *start, size_t size) | ||
292 | { | ||
293 | (void)start; | ||
294 | (void)size; | ||
295 | } | ||
296 | |||
297 | unsigned long pcm_rec_status(void) | ||
298 | { | ||
299 | return 0; | ||
300 | } | ||
301 | |||
302 | const void * pcm_rec_dma_get_peak_buffer(void) | ||
303 | { | ||
304 | return NULL; | ||
305 | } | ||
306 | |||
307 | #endif /* HAVE_RECORDING */ | ||
308 | |||
309 | void pcm_play_dma_init(void) | ||
310 | { | ||
311 | if (SDL_InitSubSystem(SDL_INIT_AUDIO)) | ||
312 | { | ||
313 | DEBUGF("Could not initialize SDL audio subsystem!\n"); | ||
314 | return; | ||
315 | } | ||
316 | |||
317 | SDL_AudioSpec wanted_spec; | ||
318 | #ifdef DEBUG | ||
319 | udata.debug = NULL; | ||
320 | if (debug_audio) { | ||
321 | udata.debug = fopen("audiodebug.raw", "wb"); | ||
322 | DEBUGF("Audio debug file open\n"); | ||
323 | } | ||
324 | #endif | ||
325 | /* Set 16-bit stereo audio at 44Khz */ | ||
326 | wanted_spec.freq = 44100; | ||
327 | wanted_spec.format = AUDIO_S16SYS; | ||
328 | wanted_spec.channels = 2; | ||
329 | wanted_spec.samples = 2048; | ||
330 | wanted_spec.callback = | ||
331 | (void (SDLCALL *)(void *userdata, | ||
332 | Uint8 *stream, int len))sdl_audio_callback; | ||
333 | wanted_spec.userdata = &udata; | ||
334 | |||
335 | /* Open the audio device and start playing sound! */ | ||
336 | if(SDL_OpenAudio(&wanted_spec, &obtained) < 0) { | ||
337 | DEBUGF("Unable to open audio: %s\n", SDL_GetError()); | ||
338 | return; | ||
339 | } | ||
340 | |||
341 | switch (obtained.format) | ||
342 | { | ||
343 | case AUDIO_U8: | ||
344 | case AUDIO_S8: | ||
345 | pcm_channel_bytes = 1; | ||
346 | break; | ||
347 | case AUDIO_U16LSB: | ||
348 | case AUDIO_S16LSB: | ||
349 | case AUDIO_U16MSB: | ||
350 | case AUDIO_S16MSB: | ||
351 | pcm_channel_bytes = 2; | ||
352 | break; | ||
353 | default: | ||
354 | DEBUGF("Unknown sample format obtained: %u\n", | ||
355 | (unsigned)obtained.format); | ||
356 | return; | ||
357 | } | ||
358 | |||
359 | pcm_sample_bytes = obtained.channels * pcm_channel_bytes; | ||
360 | |||
361 | pcm_dma_apply_settings_nolock(); | ||
362 | } | ||
363 | |||
364 | void pcm_postinit(void) | ||
365 | { | ||
366 | } | ||
367 | |||
368 | void pcm_set_mixer_volume(int volume) | ||
369 | { | ||
370 | sim_volume = volume; | ||
371 | } | ||
372 | |||
373 | #endif /* CONFIG_CODEC == SWCODEC */ | ||
diff --git a/firmware/target/hosted/sdl/sim-ui-defines.h b/firmware/target/hosted/sdl/sim-ui-defines.h new file mode 100644 index 0000000000..567a618fc3 --- /dev/null +++ b/firmware/target/hosted/sdl/sim-ui-defines.h | |||
@@ -0,0 +1,405 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __UISDL_H__ | ||
23 | #define __UISDL_H__ | ||
24 | |||
25 | #include <stdbool.h> | ||
26 | #include "SDL.h" | ||
27 | #include "config.h" | ||
28 | |||
29 | /* colour definitions are R, G, B */ | ||
30 | |||
31 | #if defined(ARCHOS_RECORDER) | ||
32 | #define UI_TITLE "Jukebox Recorder" | ||
33 | #define UI_WIDTH 270 /* width of GUI window */ | ||
34 | #define UI_HEIGHT 406 /* height of GUI window */ | ||
35 | #define UI_LCD_POSX 80 /* x position of lcd */ | ||
36 | #define UI_LCD_POSY 104 /* y position of lcd */ | ||
37 | |||
38 | #elif defined(ARCHOS_PLAYER) | ||
39 | #define UI_TITLE "Jukebox Player" | ||
40 | #define UI_WIDTH 284 /* width of GUI window */ | ||
41 | #define UI_HEIGHT 420 /* height of GUI window */ | ||
42 | #define UI_LCD_POSX 75 /* x position of lcd */ | ||
43 | #define UI_LCD_POSY 116 /* y position of lcd */ | ||
44 | |||
45 | #elif defined(ARCHOS_FMRECORDER) || defined(ARCHOS_RECORDERV2) | ||
46 | #define UI_TITLE "Jukebox FM Recorder" | ||
47 | #define UI_WIDTH 285 /* width of GUI window */ | ||
48 | #define UI_HEIGHT 414 /* height of GUI window */ | ||
49 | #define UI_LCD_POSX 87 /* x position of lcd */ | ||
50 | #define UI_LCD_POSY 77 /* y position of lcd */ | ||
51 | |||
52 | #elif defined(ARCHOS_ONDIOSP) || defined(ARCHOS_ONDIOFM) | ||
53 | #define UI_TITLE "Ondio" | ||
54 | #define UI_WIDTH 155 /* width of GUI window */ | ||
55 | #define UI_HEIGHT 334 /* height of GUI window */ | ||
56 | #define UI_LCD_POSX 21 /* x position of lcd */ | ||
57 | #define UI_LCD_POSY 82 /* y position of lcd */ | ||
58 | |||
59 | #elif defined(IRIVER_H120) || defined(IRIVER_H100) | ||
60 | #define UI_TITLE "iriver H1x0" | ||
61 | #define UI_WIDTH 379 /* width of GUI window */ | ||
62 | #define UI_HEIGHT 508 /* height of GUI window */ | ||
63 | #define UI_LCD_POSX 109 /* x position of lcd */ | ||
64 | #define UI_LCD_POSY 23 /* y position of lcd */ | ||
65 | #define UI_REMOTE_POSX 50 /* x position of remote lcd */ | ||
66 | #define UI_REMOTE_POSY 403 /* y position of remote lcd */ | ||
67 | |||
68 | #elif defined(IRIVER_H300) | ||
69 | #define UI_TITLE "iriver H300" | ||
70 | #define UI_WIDTH 288 /* width of GUI window */ | ||
71 | #define UI_HEIGHT 581 /* height of GUI window */ | ||
72 | #define UI_LCD_POSX 26 /* x position of lcd */ | ||
73 | #define UI_LCD_POSY 36 /* y position of lcd */ | ||
74 | #define UI_REMOTE_POSX 12 /* x position of remote lcd */ | ||
75 | #define UI_REMOTE_POSY 478 /* y position of remote lcd */ | ||
76 | |||
77 | #elif defined(IPOD_1G2G) | ||
78 | #define UI_TITLE "iPod 1G/2G" | ||
79 | #define UI_WIDTH 224 /* width of GUI window */ | ||
80 | #define UI_HEIGHT 382 /* height of GUI window */ | ||
81 | #define UI_LCD_POSX 32 /* x position of lcd */ | ||
82 | #define UI_LCD_POSY 12 /* y position of lcd */ | ||
83 | |||
84 | #elif defined(IPOD_3G) | ||
85 | #define UI_TITLE "iPod 3G" | ||
86 | #define UI_WIDTH 218 /* width of GUI window */ | ||
87 | #define UI_HEIGHT 389 /* height of GUI window */ | ||
88 | #define UI_LCD_POSX 29 /* x position of lcd */ | ||
89 | #define UI_LCD_POSY 16 /* y position of lcd */ | ||
90 | |||
91 | #elif defined(IPOD_4G) | ||
92 | #define UI_TITLE "iPod 4G" | ||
93 | #define UI_WIDTH 196 /* width of GUI window */ | ||
94 | #define UI_HEIGHT 370 /* height of GUI window */ | ||
95 | #define UI_LCD_POSX 19 /* x position of lcd */ | ||
96 | #define UI_LCD_POSY 14 /* y position of lcd */ | ||
97 | |||
98 | #elif defined(IPOD_MINI) || defined(IPOD_MINI2G) | ||
99 | #define UI_TITLE "iPod mini" | ||
100 | #define UI_WIDTH 191 /* width of GUI window */ | ||
101 | #define UI_HEIGHT 365 /* height of GUI window */ | ||
102 | #define UI_LCD_POSX 24 /* x position of lcd */ | ||
103 | #define UI_LCD_POSY 17 /* y position of lcd */ | ||
104 | |||
105 | #elif defined(IPOD_COLOR) | ||
106 | #define UI_TITLE "iPod Color" | ||
107 | #define UI_WIDTH 261 /* width of GUI window */ | ||
108 | #define UI_HEIGHT 493 /* height of GUI window */ | ||
109 | #define UI_LCD_POSX 21 /* x position of lcd */ | ||
110 | #define UI_LCD_POSY 16 /* y position of lcd */ | ||
111 | |||
112 | #elif defined(IPOD_NANO) | ||
113 | #define UI_TITLE "iPod Nano" | ||
114 | #define UI_WIDTH 199 /* width of GUI window */ | ||
115 | #define UI_HEIGHT 421 /* height of GUI window */ | ||
116 | #define UI_LCD_POSX 13 /* x position of lcd */ | ||
117 | #define UI_LCD_POSY 14 /* y position of lcd */ | ||
118 | |||
119 | #elif defined(IPOD_NANO2G) | ||
120 | #define UI_TITLE "iPod Nano 2G" | ||
121 | #define UI_WIDTH 235 /* width of GUI window */ | ||
122 | #define UI_HEIGHT 537 /* height of GUI window */ | ||
123 | #define UI_LCD_POSX 29 /* x position of lcd */ | ||
124 | #define UI_LCD_POSY 33 /* y position of lcd */ | ||
125 | |||
126 | #elif defined(IPOD_VIDEO) | ||
127 | #define UI_TITLE "iPod Video" | ||
128 | #define UI_WIDTH 350 /* width of GUI window */ | ||
129 | #define UI_HEIGHT 591 /* height of GUI window */ | ||
130 | #define UI_LCD_POSX 14 /* x position of lcd */ | ||
131 | #define UI_LCD_POSY 12 /* y position of lcd */ | ||
132 | |||
133 | #elif defined(IAUDIO_X5) | ||
134 | #define UI_TITLE "iAudio X5" | ||
135 | #define UI_WIDTH 300 /* width of GUI window */ | ||
136 | #define UI_HEIGHT 558 /* height of GUI window */ | ||
137 | #define UI_LCD_POSX 55 /* x position of lcd */ | ||
138 | #define UI_LCD_POSY 61 /* y position of lcd */ | ||
139 | #define UI_REMOTE_POSX 12 /* x position of remote lcd */ | ||
140 | #define UI_REMOTE_POSY 462 /* y position of remote lcd */ | ||
141 | |||
142 | #elif defined(IAUDIO_M5) | ||
143 | #define UI_TITLE "iAudio M5" | ||
144 | #define UI_WIDTH 374 /* width of GUI window */ | ||
145 | #define UI_HEIGHT 650 /* height of GUI window */ | ||
146 | #define UI_LCD_POSX 82 /* x position of lcd */ | ||
147 | #define UI_LCD_POSY 74 /* y position of lcd */ | ||
148 | #define UI_REMOTE_POSX 59 /* x position of remote lcd */ | ||
149 | #define UI_REMOTE_POSY 509 /* y position of remote lcd */ | ||
150 | |||
151 | #elif defined(IAUDIO_M3) | ||
152 | #define UI_TITLE "iAudio M3" | ||
153 | #define UI_WIDTH 397 /* width of GUI window */ | ||
154 | #define UI_HEIGHT 501 /* height of GUI window */ | ||
155 | #define UI_LCD_POSX 92 /* x position of lcd */ | ||
156 | #define UI_LCD_POSY 348 /* y position of lcd */ | ||
157 | |||
158 | #elif defined(GIGABEAT_F) | ||
159 | #define UI_TITLE "Toshiba Gigabeat" | ||
160 | #define UI_WIDTH 401 /* width of GUI window */ | ||
161 | #define UI_HEIGHT 655 /* height of GUI window */ | ||
162 | #define UI_LCD_POSX 48 /* x position of lcd */ | ||
163 | #define UI_LCD_POSY 60 /* y position of lcd */ | ||
164 | |||
165 | #elif defined(GIGABEAT_S) | ||
166 | #define UI_TITLE "Toshiba Gigabeat" | ||
167 | #define UI_WIDTH 450 /* width of GUI window */ | ||
168 | #define UI_HEIGHT 688 /* height of GUI window */ | ||
169 | #define UI_LCD_POSX 96 /* x position of lcd */ | ||
170 | #define UI_LCD_POSY 90 /* y position of lcd */ | ||
171 | |||
172 | #elif defined(MROBE_500) | ||
173 | #if LCD_WIDTH==320 | ||
174 | #define UI_TITLE "Olympus M:Robe 500" | ||
175 | #define UI_WIDTH 450 /* width of GUI window */ | ||
176 | #define UI_HEIGHT 350 /* height of GUI window */ | ||
177 | #define UI_LCD_POSX 65 /* x position of lcd */ | ||
178 | #define UI_LCD_POSY 30 /* y position of lcd */ | ||
179 | #define UI_REMOTE_POSX 36 /* x position of remote lcd */ | ||
180 | #define UI_REMOTE_POSY 318 /* y position of remote lcd */ | ||
181 | #else | ||
182 | #define UI_TITLE "Olympus M:Robe 500" | ||
183 | #define UI_WIDTH 895 /* width of GUI window */ | ||
184 | #define UI_HEIGHT 646 /* height of GUI window */ | ||
185 | #define UI_LCD_POSX 129 /* x position of lcd */ | ||
186 | #define UI_LCD_POSY 60 /* y position of lcd */ | ||
187 | #define UI_REMOTE_POSX 37 /* x position of remote lcd */ | ||
188 | #define UI_REMOTE_POSY 615 /* y position of remote lcd */ | ||
189 | #endif | ||
190 | |||
191 | #elif defined(IRIVER_H10) | ||
192 | #define UI_TITLE "iriver H10 20Gb" | ||
193 | #define UI_WIDTH 392 /* width of GUI window */ | ||
194 | #define UI_HEIGHT 391 /* height of GUI window */ | ||
195 | #define UI_LCD_POSX 111 /* x position of lcd */ | ||
196 | #define UI_LCD_POSY 30 /* y position of lcd */ | ||
197 | |||
198 | #elif defined(IRIVER_H10_5GB) | ||
199 | #define UI_TITLE "iriver H10 5/6Gb" | ||
200 | #define UI_WIDTH 353 /* width of GUI window */ | ||
201 | #define UI_HEIGHT 460 /* height of GUI window */ | ||
202 | #define UI_LCD_POSX 112 /* x position of lcd */ | ||
203 | #define UI_LCD_POSY 45 /* y position of lcd */ | ||
204 | |||
205 | #elif defined(SANSA_E200) || defined(SANSA_E200V2) | ||
206 | #ifdef SANSA_E200 | ||
207 | #define UI_TITLE "Sansa e200" | ||
208 | #else | ||
209 | #define UI_TITLE "Sansa e200v2" | ||
210 | #endif | ||
211 | #define UI_WIDTH 260 /* width of GUI window */ | ||
212 | #define UI_HEIGHT 502 /* height of GUI window */ | ||
213 | #define UI_LCD_POSX 42 /* x position of lcd */ | ||
214 | #define UI_LCD_POSY 37 /* y position of lcd */ | ||
215 | |||
216 | #elif defined(SANSA_C200) || defined(SANSA_C200V2) | ||
217 | #ifdef SANSA_C200 | ||
218 | #define UI_TITLE "Sansa c200" | ||
219 | #else | ||
220 | #define UI_TITLE "Sansa c200v2" | ||
221 | #endif | ||
222 | #define UI_WIDTH 350 /* width of GUI window */ | ||
223 | #define UI_HEIGHT 152 /* height of GUI window */ | ||
224 | #define UI_LCD_POSX 42 /* x position of lcd */ | ||
225 | #define UI_LCD_POSY 35 /* y position of lcd */ | ||
226 | |||
227 | #elif defined(IRIVER_IFP7XX) | ||
228 | #define UI_TITLE "iriver iFP7xx" | ||
229 | #define UI_WIDTH 425 /* width of GUI window */ | ||
230 | #define UI_HEIGHT 183 /* height of GUI window */ | ||
231 | #define UI_LCD_POSX 115 /* x position of lcd */ | ||
232 | #define UI_LCD_POSY 54 /* y position of lcd */ | ||
233 | |||
234 | #elif defined(ARCHOS_AV300) | ||
235 | #define UI_TITLE "Archos AV300" | ||
236 | /* We are temporarily using a 2bpp LCD driver and dummy bitmap */ | ||
237 | #define UI_WIDTH 420 /* width of GUI window */ | ||
238 | #define UI_HEIGHT 340 /* height of GUI window */ | ||
239 | #define UI_LCD_POSX 50 /* x position of lcd */ | ||
240 | #define UI_LCD_POSY 50 /* y position of lcd */ | ||
241 | |||
242 | #elif defined(MROBE_100) | ||
243 | #define UI_TITLE "Olympus M:Robe 100" | ||
244 | #define UI_WIDTH 247 /* width of GUI window */ | ||
245 | #define UI_HEIGHT 462 /* height of GUI window */ | ||
246 | #define UI_LCD_POSX 43 /* x position of lcd */ | ||
247 | #define UI_LCD_POSY 25 /* y position of lcd */ | ||
248 | #define UI_REMOTE_POSX 34 /* x position of remote lcd */ | ||
249 | #define UI_REMOTE_POSY 432 /* y position of remote lcd */ | ||
250 | |||
251 | #elif defined(COWON_D2) | ||
252 | #define UI_TITLE "Cowon D2" | ||
253 | #define UI_WIDTH 472 /* width of GUI window */ | ||
254 | #define UI_HEIGHT 368 /* height of GUI window */ | ||
255 | #define UI_LCD_POSX 58 /* x position of lcd */ | ||
256 | #define UI_LCD_POSY 67 /* y position of lcd */ | ||
257 | |||
258 | #elif defined(IAUDIO_7) | ||
259 | #define UI_TITLE "iAudio7" | ||
260 | #define UI_WIDTH 494 /* width of GUI window */ | ||
261 | #define UI_HEIGHT 214 /* height of GUI window */ | ||
262 | #define UI_LCD_POSX 131 /* x position of lcd */ | ||
263 | #define UI_LCD_POSY 38 /* y position of lcd */ | ||
264 | |||
265 | #elif defined(CREATIVE_ZVM) || defined(CREATIVE_ZVM60GB) | ||
266 | #ifdef CREATIVE_ZVM | ||
267 | #define UI_TITLE "Creative Zen Vision:M 30GB" | ||
268 | #else | ||
269 | #define UI_TITLE "Creative Zen Vision:M 60GB" | ||
270 | #endif | ||
271 | #define UI_WIDTH 383 /* width of GUI window */ | ||
272 | #define UI_HEIGHT 643 /* height of GUI window */ | ||
273 | #define UI_LCD_POSX 31 /* x position of lcd */ | ||
274 | #define UI_LCD_POSY 62 /* y position of lcd */ | ||
275 | |||
276 | #elif defined(CREATIVE_ZV) | ||
277 | #define UI_TITLE "Creative Zen Vision" | ||
278 | #define UI_WIDTH 1054 /* width of GUI window */ | ||
279 | #define UI_HEIGHT 643 /* height of GUI window */ | ||
280 | #define UI_LCD_POSX 129 /* x position of lcd */ | ||
281 | #define UI_LCD_POSY 85 /* y position of lcd */ | ||
282 | |||
283 | #elif defined(MEIZU_M6SL) | ||
284 | #define UI_TITLE "Meizu M6" | ||
285 | #define UI_WIDTH 512 /* width of GUI window */ | ||
286 | #define UI_HEIGHT 322 /* height of GUI window */ | ||
287 | #define UI_LCD_POSX 39 /* x position of lcd */ | ||
288 | #define UI_LCD_POSY 38 /* y position of lcd */ | ||
289 | |||
290 | #elif defined(SANSA_FUZE) || defined(SANSA_FUZEV2) | ||
291 | #ifdef SANSA_FUZE | ||
292 | #define UI_TITLE "Sansa Fuze" | ||
293 | #else | ||
294 | #define UI_TITLE "Sansa Fuzev2" | ||
295 | #endif | ||
296 | #define UI_WIDTH 279 /* width of GUI window */ | ||
297 | #define UI_HEIGHT 449 /* height of GUI window */ | ||
298 | #define UI_LCD_POSX 30 /* x position of lcd */ | ||
299 | #define UI_LCD_POSY 31 /* y position of lcd */ | ||
300 | |||
301 | #elif defined(SANSA_CLIP) || defined(SANSA_CLIPV2) | ||
302 | #if defined(SANSA_CLIP) | ||
303 | #define CLIP_VERSION "" | ||
304 | #elif defined(SANSA_CLIPV2) | ||
305 | #define CLIP_VERSION "v2" | ||
306 | #endif | ||
307 | #define UI_TITLE "Sansa Clip"CLIP_VERSION | ||
308 | #define UI_WIDTH 205 /* width of GUI window */ | ||
309 | #define UI_HEIGHT 325 /* height of GUI window */ | ||
310 | #define UI_LCD_POSX 38 /* x position of lcd */ | ||
311 | #define UI_LCD_POSY 38 /* y position of lcd */ | ||
312 | |||
313 | #elif defined(SANSA_CLIPPLUS) | ||
314 | #define UI_TITLE "Sansa Clip+" | ||
315 | #define UI_WIDTH 205 /* width of GUI window */ | ||
316 | #define UI_HEIGHT 325 /* height of GUI window */ | ||
317 | #define UI_LCD_POSX 42 /* x position of lcd */ | ||
318 | #define UI_LCD_POSY 42 /* y position of lcd */ | ||
319 | |||
320 | |||
321 | |||
322 | #elif defined(PHILIPS_SA9200) | ||
323 | #define UI_TITLE "Philips GoGear SA9200" | ||
324 | #define UI_WIDTH 233 /* width of GUI window */ | ||
325 | #define UI_HEIGHT 435 /* height of GUI window */ | ||
326 | #define UI_LCD_POSX 50 /* x position of lcd */ | ||
327 | #define UI_LCD_POSY 50 /* y position of lcd */ | ||
328 | |||
329 | #elif defined(PHILIPS_HDD1630) | ||
330 | #define UI_TITLE "Philips GoGear HDD1630" | ||
331 | #define UI_WIDTH 407 /* width of GUI window */ | ||
332 | #define UI_HEIGHT 391 /* height of GUI window */ | ||
333 | #define UI_LCD_POSX 143 /* x position of lcd */ | ||
334 | #define UI_LCD_POSY 27 /* y position of lcd */ | ||
335 | |||
336 | #elif defined(SANSA_M200V4) | ||
337 | #define UI_TITLE "sansa m200v4" | ||
338 | #define UI_WIDTH 350 /* width of GUI window */ | ||
339 | #define UI_HEIGHT 168 /* height of GUI window */ | ||
340 | #define UI_LCD_POSX 42 /* x position of lcd */ | ||
341 | #define UI_LCD_POSY 55 /* y position of lcd */ | ||
342 | |||
343 | #elif defined(ONDA_VX747) || defined(ONDA_VX747P) | ||
344 | #ifdef ONDA_VX747 | ||
345 | #define UI_TITLE "Onda VX747" | ||
346 | #else | ||
347 | #define UI_TITLE "Onda VX747+" | ||
348 | #endif | ||
349 | #define UI_WIDTH 340 /* width of GUI window */ | ||
350 | #define UI_HEIGHT 601 /* height of GUI window */ | ||
351 | #define UI_LCD_POSX 45 /* x position of lcd */ | ||
352 | #define UI_LCD_POSY 90 /* y position of lcd */ | ||
353 | |||
354 | #elif defined(ONDA_VX777) | ||
355 | #define UI_TITLE "Onda VX777" | ||
356 | #define UI_WIDTH 306 /* width of GUI window */ | ||
357 | #define UI_HEIGHT 558 /* height of GUI window */ | ||
358 | #define UI_LCD_POSX 32 /* x position of lcd */ | ||
359 | #define UI_LCD_POSY 81 /* y position of lcd */ | ||
360 | |||
361 | #elif defined(SAMSUNG_YH820) | ||
362 | #define UI_TITLE "Samsung YH-820" | ||
363 | #define UI_WIDTH 368 /* width of GUI window */ | ||
364 | #define UI_HEIGHT 428 /* height of GUI window */ | ||
365 | #define UI_LCD_POSX 120 /* x position of lcd */ | ||
366 | #define UI_LCD_POSY 75 /* y position of lcd */ | ||
367 | |||
368 | #elif defined(SAMSUNG_YH920) || defined(SAMSUNG_YH925) | ||
369 | #ifdef SAMSUNG_YH920 | ||
370 | #define UI_TITLE "Samsung YH-920" | ||
371 | #else | ||
372 | #define UI_TITLE "Samsung YH-925" | ||
373 | #endif | ||
374 | #define UI_WIDTH 408 /* width of GUI window */ | ||
375 | #define UI_HEIGHT 454 /* height of GUI window */ | ||
376 | #define UI_LCD_POSX 124 /* x position of lcd */ | ||
377 | #define UI_LCD_POSY 42 /* y position of lcd */ | ||
378 | |||
379 | #elif defined(MINI2440) | ||
380 | #define UI_TITLE "Mini2440" | ||
381 | #define UI_WIDTH 441 /* width of GUI window */ | ||
382 | #define UI_HEIGHT 436 /* height of GUI window */ | ||
383 | #define UI_LCD_POSX 148 /* x position of lcd */ | ||
384 | #define UI_LCD_POSY 50 /* y position of lcd */ | ||
385 | |||
386 | #elif defined(PBELL_VIBE500) | ||
387 | #define UI_TITLE "Packard Bell Vibe 500" | ||
388 | #define UI_WIDTH 287 /* width of GUI window */ | ||
389 | #define UI_HEIGHT 488 /* height of GUI window */ | ||
390 | #define UI_LCD_POSX 64 /* x position of lcd */ | ||
391 | #define UI_LCD_POSY 61 /* y position of lcd */ | ||
392 | |||
393 | #elif defined(MPIO_HD200) | ||
394 | #define UI_TITLE "MPIO HD200" | ||
395 | #define UI_WIDTH 430 /* width of GUI window */ | ||
396 | #define UI_HEIGHT 479 /* height of GUI window */ | ||
397 | #define UI_LCD_POSX 101 | ||
398 | #define UI_LCD_POSY 195 | ||
399 | |||
400 | #elif defined(SIMULATOR) | ||
401 | #error no UI defines | ||
402 | #endif | ||
403 | |||
404 | #endif /* #ifndef __UISDL_H__ */ | ||
405 | |||
diff --git a/firmware/target/hosted/sdl/system-sdl.c b/firmware/target/hosted/sdl/system-sdl.c new file mode 100644 index 0000000000..693e8d1b57 --- /dev/null +++ b/firmware/target/hosted/sdl/system-sdl.c | |||
@@ -0,0 +1,236 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 by Daniel Everton <dan@iocaine.org> | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <SDL.h> | ||
23 | #include <stdlib.h> | ||
24 | #include <string.h> | ||
25 | #include <setjmp.h> | ||
26 | #include "system-sdl.h" | ||
27 | #include "thread-sdl.h" | ||
28 | #include "sim-ui-defines.h" | ||
29 | #include "lcd-sdl.h" | ||
30 | #ifdef HAVE_LCD_BITMAP | ||
31 | #include "lcd-bitmap.h" | ||
32 | #elif defined(HAVE_LCD_CHARCELLS) | ||
33 | #include "lcd-charcells.h" | ||
34 | #endif | ||
35 | #ifdef HAVE_REMOTE_LCD | ||
36 | #include "lcd-remote-bitmap.h" | ||
37 | #endif | ||
38 | #include "panic.h" | ||
39 | #include "debug.h" | ||
40 | |||
41 | SDL_Surface *gui_surface; | ||
42 | |||
43 | bool background = true; /* use backgrounds by default */ | ||
44 | #ifdef HAVE_REMOTE_LCD | ||
45 | bool showremote = true; /* include remote by default */ | ||
46 | #endif | ||
47 | bool mapping = false; | ||
48 | bool debug_buttons = false; | ||
49 | |||
50 | bool lcd_display_redraw = true; /* Used for player simulator */ | ||
51 | char having_new_lcd = true; /* Used for player simulator */ | ||
52 | bool sim_alarm_wakeup = false; | ||
53 | const char *sim_root_dir = NULL; | ||
54 | extern int display_zoom; | ||
55 | |||
56 | #ifdef DEBUG | ||
57 | bool debug_audio = false; | ||
58 | #endif | ||
59 | |||
60 | bool debug_wps = false; | ||
61 | int wps_verbose_level = 3; | ||
62 | |||
63 | |||
64 | void sys_poweroff(void) | ||
65 | { | ||
66 | /* Order here is relevent to prevent deadlocks and use of destroyed | ||
67 | sync primitives by kernel threads */ | ||
68 | sim_thread_shutdown(); | ||
69 | sim_kernel_shutdown(); | ||
70 | SDL_Quit(); | ||
71 | } | ||
72 | |||
73 | void system_init(void) | ||
74 | { | ||
75 | SDL_Surface *picture_surface; | ||
76 | int width, height; | ||
77 | |||
78 | if (SDL_Init(SDL_INIT_VIDEO|SDL_INIT_TIMER)) | ||
79 | panicf("%s", SDL_GetError()); | ||
80 | |||
81 | /* Try and load the background image. If it fails go without */ | ||
82 | if (background) { | ||
83 | picture_surface = SDL_LoadBMP("UI256.bmp"); | ||
84 | if (picture_surface == NULL) { | ||
85 | background = false; | ||
86 | DEBUGF("warn: %s\n", SDL_GetError()); | ||
87 | } | ||
88 | } | ||
89 | |||
90 | /* Set things up */ | ||
91 | if (background) | ||
92 | { | ||
93 | width = UI_WIDTH; | ||
94 | height = UI_HEIGHT; | ||
95 | } | ||
96 | else | ||
97 | { | ||
98 | #ifdef HAVE_REMOTE_LCD | ||
99 | if (showremote) | ||
100 | { | ||
101 | width = SIM_LCD_WIDTH > SIM_REMOTE_WIDTH ? SIM_LCD_WIDTH : SIM_REMOTE_WIDTH; | ||
102 | height = SIM_LCD_HEIGHT + SIM_REMOTE_HEIGHT; | ||
103 | } | ||
104 | else | ||
105 | #endif | ||
106 | { | ||
107 | width = SIM_LCD_WIDTH; | ||
108 | height = SIM_LCD_HEIGHT; | ||
109 | } | ||
110 | } | ||
111 | |||
112 | |||
113 | if ((gui_surface = SDL_SetVideoMode(width * display_zoom, height * display_zoom, 24, SDL_HWSURFACE|SDL_DOUBLEBUF)) == NULL) { | ||
114 | panicf("%s", SDL_GetError()); | ||
115 | } | ||
116 | |||
117 | SDL_WM_SetCaption(UI_TITLE, NULL); | ||
118 | |||
119 | sim_lcd_init(); | ||
120 | #ifdef HAVE_REMOTE_LCD | ||
121 | if (showremote) | ||
122 | sim_lcd_remote_init(); | ||
123 | #endif | ||
124 | |||
125 | if (background && picture_surface != NULL) { | ||
126 | SDL_BlitSurface(picture_surface, NULL, gui_surface, NULL); | ||
127 | SDL_UpdateRect(gui_surface, 0, 0, 0, 0); | ||
128 | } | ||
129 | } | ||
130 | |||
131 | void system_exception_wait(void) | ||
132 | { | ||
133 | sim_thread_exception_wait(); | ||
134 | } | ||
135 | |||
136 | void system_reboot(void) | ||
137 | { | ||
138 | sim_thread_exception_wait(); | ||
139 | } | ||
140 | |||
141 | void sys_handle_argv(int argc, char *argv[]) | ||
142 | { | ||
143 | if (argc >= 1) | ||
144 | { | ||
145 | int x; | ||
146 | for (x = 1; x < argc; x++) | ||
147 | { | ||
148 | #ifdef DEBUG | ||
149 | if (!strcmp("--debugaudio", argv[x])) | ||
150 | { | ||
151 | debug_audio = true; | ||
152 | printf("Writing debug audio file.\n"); | ||
153 | } | ||
154 | else | ||
155 | #endif | ||
156 | if (!strcmp("--debugwps", argv[x])) | ||
157 | { | ||
158 | debug_wps = true; | ||
159 | printf("WPS debug mode enabled.\n"); | ||
160 | } | ||
161 | else if (!strcmp("--nobackground", argv[x])) | ||
162 | { | ||
163 | background = false; | ||
164 | printf("Disabling background image.\n"); | ||
165 | } | ||
166 | #ifdef HAVE_REMOTE_LCD | ||
167 | else if (!strcmp("--noremote", argv[x])) | ||
168 | { | ||
169 | showremote = false; | ||
170 | background = false; | ||
171 | printf("Disabling remote image.\n"); | ||
172 | } | ||
173 | #endif | ||
174 | else if (!strcmp("--old_lcd", argv[x])) | ||
175 | { | ||
176 | having_new_lcd = false; | ||
177 | printf("Using old LCD layout.\n"); | ||
178 | } | ||
179 | else if (!strcmp("--zoom", argv[x])) | ||
180 | { | ||
181 | x++; | ||
182 | if(x < argc) | ||
183 | display_zoom=atoi(argv[x]); | ||
184 | else | ||
185 | display_zoom = 2; | ||
186 | printf("Window zoom is %d\n", display_zoom); | ||
187 | } | ||
188 | else if (!strcmp("--alarm", argv[x])) | ||
189 | { | ||
190 | sim_alarm_wakeup = true; | ||
191 | printf("Simulating alarm wakeup.\n"); | ||
192 | } | ||
193 | else if (!strcmp("--root", argv[x])) | ||
194 | { | ||
195 | x++; | ||
196 | if (x < argc) | ||
197 | { | ||
198 | sim_root_dir = argv[x]; | ||
199 | printf("Root directory: %s\n", sim_root_dir); | ||
200 | } | ||
201 | } | ||
202 | else if (!strcmp("--mapping", argv[x])) | ||
203 | { | ||
204 | mapping = true; | ||
205 | printf("Printing click coords with drag radii.\n"); | ||
206 | } | ||
207 | else if (!strcmp("--debugbuttons", argv[x])) | ||
208 | { | ||
209 | debug_buttons = true; | ||
210 | printf("Printing background button clicks.\n"); | ||
211 | } | ||
212 | else | ||
213 | { | ||
214 | printf("rockboxui\n"); | ||
215 | printf("Arguments:\n"); | ||
216 | #ifdef DEBUG | ||
217 | printf(" --debugaudio \t Write raw PCM data to audiodebug.raw\n"); | ||
218 | #endif | ||
219 | printf(" --debugwps \t Print advanced WPS debug info\n"); | ||
220 | printf(" --nobackground \t Disable the background image\n"); | ||
221 | #ifdef HAVE_REMOTE_LCD | ||
222 | printf(" --noremote \t Disable the remote image (will disable backgrounds)\n"); | ||
223 | #endif | ||
224 | printf(" --old_lcd \t [Player] simulate old playermodel (ROM version<4.51)\n"); | ||
225 | printf(" --zoom [VAL]\t Window zoom (will disable backgrounds)\n"); | ||
226 | printf(" --alarm \t Simulate a wake-up on alarm\n"); | ||
227 | printf(" --root [DIR]\t Set root directory\n"); | ||
228 | printf(" --mapping \t Output coordinates and radius for mapping backgrounds\n"); | ||
229 | exit(0); | ||
230 | } | ||
231 | } | ||
232 | } | ||
233 | if (display_zoom > 1) { | ||
234 | background = false; | ||
235 | } | ||
236 | } | ||
diff --git a/firmware/target/hosted/sdl/system-sdl.h b/firmware/target/hosted/sdl/system-sdl.h new file mode 100644 index 0000000000..917e6e89da --- /dev/null +++ b/firmware/target/hosted/sdl/system-sdl.h | |||
@@ -0,0 +1,52 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2007 by Michael Sevakis | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | #ifndef _SYSTEM_SDL_H_ | ||
22 | #define _SYSTEM_SDL_H_ | ||
23 | |||
24 | #include <stdbool.h> | ||
25 | |||
26 | #define HIGHEST_IRQ_LEVEL 1 | ||
27 | |||
28 | int set_irq_level(int level); | ||
29 | |||
30 | #define disable_irq() \ | ||
31 | ((void)set_irq_level(HIGHEST_IRQ_LEVEL)) | ||
32 | |||
33 | #define enable_irq() \ | ||
34 | ((void)set_irq_level(0)) | ||
35 | |||
36 | #define disable_irq_save() \ | ||
37 | set_irq_level(HIGHEST_IRQ_LEVEL) | ||
38 | |||
39 | #define restore_irq(level) \ | ||
40 | ((void)set_irq_level(level)) | ||
41 | |||
42 | void sim_enter_irq_handler(void); | ||
43 | void sim_exit_irq_handler(void); | ||
44 | void sim_kernel_shutdown(void); | ||
45 | void sys_poweroff(void); | ||
46 | void sys_handle_argv(int argc, char *argv[]); | ||
47 | |||
48 | extern bool background; /* True if the background image is enabled */ | ||
49 | extern int display_zoom; | ||
50 | extern long start_tick; | ||
51 | |||
52 | #endif /* _SYSTEM_SDL_H_ */ | ||
diff --git a/firmware/target/hosted/sdl/thread-sdl.c b/firmware/target/hosted/sdl/thread-sdl.c new file mode 100644 index 0000000000..fbe2621d40 --- /dev/null +++ b/firmware/target/hosted/sdl/thread-sdl.c | |||
@@ -0,0 +1,610 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include <stdbool.h> | ||
23 | #include <time.h> | ||
24 | #include <SDL.h> | ||
25 | #include <SDL_thread.h> | ||
26 | #include <stdlib.h> | ||
27 | #include <memory.h> | ||
28 | #include <setjmp.h> | ||
29 | #include "system-sdl.h" | ||
30 | #include "thread-sdl.h" | ||
31 | #include "system.h" | ||
32 | #include "kernel.h" | ||
33 | #include "thread.h" | ||
34 | #include "debug.h" | ||
35 | |||
36 | /* Define this as 1 to show informational messages that are not errors. */ | ||
37 | #define THREAD_SDL_DEBUGF_ENABLED 0 | ||
38 | |||
39 | #if THREAD_SDL_DEBUGF_ENABLED | ||
40 | #define THREAD_SDL_DEBUGF(...) DEBUGF(__VA_ARGS__) | ||
41 | static char __name[32]; | ||
42 | #define THREAD_SDL_GET_NAME(thread) \ | ||
43 | ({ thread_get_name(__name, ARRAYLEN(__name), thread); __name; }) | ||
44 | #else | ||
45 | #define THREAD_SDL_DEBUGF(...) | ||
46 | #define THREAD_SDL_GET_NAME(thread) | ||
47 | #endif | ||
48 | |||
49 | #define THREAD_PANICF(str...) \ | ||
50 | ({ fprintf(stderr, str); exit(-1); }) | ||
51 | |||
52 | /* Thread/core entries as in rockbox core */ | ||
53 | static struct core_entry cores[NUM_CORES]; | ||
54 | struct thread_entry threads[MAXTHREADS]; | ||
55 | /* Jump buffers for graceful exit - kernel threads don't stay neatly | ||
56 | * in their start routines responding to messages so this is the only | ||
57 | * way to get them back in there so they may exit */ | ||
58 | static jmp_buf thread_jmpbufs[MAXTHREADS]; | ||
59 | /* this mutex locks out other Rockbox threads while one runs, | ||
60 | * that enables us to simulate a cooperative environment even if | ||
61 | * the host is preemptive */ | ||
62 | static SDL_mutex *m; | ||
63 | static volatile bool threads_exit = false; | ||
64 | |||
65 | extern long start_tick; | ||
66 | |||
67 | void sim_thread_shutdown(void) | ||
68 | { | ||
69 | int i; | ||
70 | |||
71 | /* Tell all threads jump back to their start routines, unlock and exit | ||
72 | gracefully - we'll check each one in turn for it's status. Threads | ||
73 | _could_ terminate via remove_thread or multiple threads could exit | ||
74 | on each unlock but that is safe. */ | ||
75 | |||
76 | /* Do this before trying to acquire lock */ | ||
77 | threads_exit = true; | ||
78 | |||
79 | /* Take control */ | ||
80 | SDL_LockMutex(m); | ||
81 | |||
82 | for (i = 0; i < MAXTHREADS; i++) | ||
83 | { | ||
84 | struct thread_entry *thread = &threads[i]; | ||
85 | /* exit all current threads, except the main one */ | ||
86 | if (thread->context.t != NULL) | ||
87 | { | ||
88 | /* Signal thread on delay or block */ | ||
89 | SDL_Thread *t = thread->context.t; | ||
90 | SDL_SemPost(thread->context.s); | ||
91 | SDL_UnlockMutex(m); | ||
92 | /* Wait for it to finish */ | ||
93 | SDL_WaitThread(t, NULL); | ||
94 | /* Relock for next thread signal */ | ||
95 | SDL_LockMutex(m); | ||
96 | } | ||
97 | } | ||
98 | |||
99 | SDL_UnlockMutex(m); | ||
100 | SDL_DestroyMutex(m); | ||
101 | } | ||
102 | |||
103 | static void new_thread_id(unsigned int slot_num, | ||
104 | struct thread_entry *thread) | ||
105 | { | ||
106 | unsigned int version = | ||
107 | (thread->id + (1u << THREAD_ID_VERSION_SHIFT)) | ||
108 | & THREAD_ID_VERSION_MASK; | ||
109 | |||
110 | if (version == 0) | ||
111 | version = 1u << THREAD_ID_VERSION_SHIFT; | ||
112 | |||
113 | thread->id = version | (slot_num & THREAD_ID_SLOT_MASK); | ||
114 | } | ||
115 | |||
116 | static struct thread_entry * find_empty_thread_slot(void) | ||
117 | { | ||
118 | struct thread_entry *thread = NULL; | ||
119 | int n; | ||
120 | |||
121 | for (n = 0; n < MAXTHREADS; n++) | ||
122 | { | ||
123 | int state = threads[n].state; | ||
124 | |||
125 | if (state == STATE_KILLED) | ||
126 | { | ||
127 | thread = &threads[n]; | ||
128 | break; | ||
129 | } | ||
130 | } | ||
131 | |||
132 | return thread; | ||
133 | } | ||
134 | |||
135 | |||
136 | /* Initialize SDL threading */ | ||
137 | void init_threads(void) | ||
138 | { | ||
139 | struct thread_entry *thread; | ||
140 | int n; | ||
141 | |||
142 | memset(cores, 0, sizeof(cores)); | ||
143 | memset(threads, 0, sizeof(threads)); | ||
144 | |||
145 | m = SDL_CreateMutex(); | ||
146 | |||
147 | if (SDL_LockMutex(m) == -1) | ||
148 | { | ||
149 | fprintf(stderr, "Couldn't lock mutex\n"); | ||
150 | return; | ||
151 | } | ||
152 | |||
153 | /* Initialize all IDs */ | ||
154 | for (n = 0; n < MAXTHREADS; n++) | ||
155 | threads[n].id = THREAD_ID_INIT(n); | ||
156 | |||
157 | /* Slot 0 is reserved for the main thread - initialize it here and | ||
158 | then create the SDL thread - it is possible to have a quick, early | ||
159 | shutdown try to access the structure. */ | ||
160 | thread = &threads[0]; | ||
161 | thread->stack = (uintptr_t *)" "; | ||
162 | thread->stack_size = 8; | ||
163 | thread->name = "main"; | ||
164 | thread->state = STATE_RUNNING; | ||
165 | thread->context.s = SDL_CreateSemaphore(0); | ||
166 | thread->context.t = NULL; /* NULL for the implicit main thread */ | ||
167 | cores[CURRENT_CORE].running = thread; | ||
168 | |||
169 | if (thread->context.s == NULL) | ||
170 | { | ||
171 | fprintf(stderr, "Failed to create main semaphore\n"); | ||
172 | return; | ||
173 | } | ||
174 | |||
175 | THREAD_SDL_DEBUGF("Main thread: %p\n", thread); | ||
176 | |||
177 | return; | ||
178 | } | ||
179 | |||
180 | void sim_thread_exception_wait(void) | ||
181 | { | ||
182 | while (1) | ||
183 | { | ||
184 | SDL_Delay(HZ/10); | ||
185 | if (threads_exit) | ||
186 | thread_exit(); | ||
187 | } | ||
188 | } | ||
189 | |||
190 | /* A way to yield and leave the threading system for extended periods */ | ||
191 | void sim_thread_lock(void *me) | ||
192 | { | ||
193 | SDL_LockMutex(m); | ||
194 | cores[CURRENT_CORE].running = (struct thread_entry *)me; | ||
195 | |||
196 | if (threads_exit) | ||
197 | thread_exit(); | ||
198 | } | ||
199 | |||
200 | void * sim_thread_unlock(void) | ||
201 | { | ||
202 | struct thread_entry *current = cores[CURRENT_CORE].running; | ||
203 | SDL_UnlockMutex(m); | ||
204 | return current; | ||
205 | } | ||
206 | |||
207 | struct thread_entry * thread_id_entry(unsigned int thread_id) | ||
208 | { | ||
209 | return (thread_id == THREAD_ID_CURRENT) ? | ||
210 | cores[CURRENT_CORE].running : | ||
211 | &threads[thread_id & THREAD_ID_SLOT_MASK]; | ||
212 | } | ||
213 | |||
214 | static void add_to_list_l(struct thread_entry **list, | ||
215 | struct thread_entry *thread) | ||
216 | { | ||
217 | if (*list == NULL) | ||
218 | { | ||
219 | /* Insert into unoccupied list */ | ||
220 | thread->l.next = thread; | ||
221 | thread->l.prev = thread; | ||
222 | *list = thread; | ||
223 | } | ||
224 | else | ||
225 | { | ||
226 | /* Insert last */ | ||
227 | thread->l.next = *list; | ||
228 | thread->l.prev = (*list)->l.prev; | ||
229 | thread->l.prev->l.next = thread; | ||
230 | (*list)->l.prev = thread; | ||
231 | } | ||
232 | } | ||
233 | |||
234 | static void remove_from_list_l(struct thread_entry **list, | ||
235 | struct thread_entry *thread) | ||
236 | { | ||
237 | if (thread == thread->l.next) | ||
238 | { | ||
239 | /* The only item */ | ||
240 | *list = NULL; | ||
241 | return; | ||
242 | } | ||
243 | |||
244 | if (thread == *list) | ||
245 | { | ||
246 | /* List becomes next item */ | ||
247 | *list = thread->l.next; | ||
248 | } | ||
249 | |||
250 | /* Fix links to jump over the removed entry. */ | ||
251 | thread->l.prev->l.next = thread->l.next; | ||
252 | thread->l.next->l.prev = thread->l.prev; | ||
253 | } | ||
254 | |||
255 | unsigned int thread_get_current(void) | ||
256 | { | ||
257 | return cores[CURRENT_CORE].running->id; | ||
258 | } | ||
259 | |||
260 | void switch_thread(void) | ||
261 | { | ||
262 | struct thread_entry *current = cores[CURRENT_CORE].running; | ||
263 | |||
264 | enable_irq(); | ||
265 | |||
266 | switch (current->state) | ||
267 | { | ||
268 | case STATE_RUNNING: | ||
269 | { | ||
270 | SDL_UnlockMutex(m); | ||
271 | /* Any other thread waiting already will get it first */ | ||
272 | SDL_LockMutex(m); | ||
273 | break; | ||
274 | } /* STATE_RUNNING: */ | ||
275 | |||
276 | case STATE_BLOCKED: | ||
277 | { | ||
278 | int oldlevel; | ||
279 | |||
280 | SDL_UnlockMutex(m); | ||
281 | SDL_SemWait(current->context.s); | ||
282 | SDL_LockMutex(m); | ||
283 | |||
284 | oldlevel = disable_irq_save(); | ||
285 | current->state = STATE_RUNNING; | ||
286 | restore_irq(oldlevel); | ||
287 | break; | ||
288 | } /* STATE_BLOCKED: */ | ||
289 | |||
290 | case STATE_BLOCKED_W_TMO: | ||
291 | { | ||
292 | int result, oldlevel; | ||
293 | |||
294 | SDL_UnlockMutex(m); | ||
295 | result = SDL_SemWaitTimeout(current->context.s, current->tmo_tick); | ||
296 | SDL_LockMutex(m); | ||
297 | |||
298 | oldlevel = disable_irq_save(); | ||
299 | |||
300 | if (current->state == STATE_BLOCKED_W_TMO) | ||
301 | { | ||
302 | /* Timed out */ | ||
303 | remove_from_list_l(current->bqp, current); | ||
304 | |||
305 | #ifdef HAVE_WAKEUP_EXT_CB | ||
306 | if (current->wakeup_ext_cb != NULL) | ||
307 | current->wakeup_ext_cb(current); | ||
308 | #endif | ||
309 | current->state = STATE_RUNNING; | ||
310 | } | ||
311 | |||
312 | if (result == SDL_MUTEX_TIMEDOUT) | ||
313 | { | ||
314 | /* Other signals from an explicit wake could have been made before | ||
315 | * arriving here if we timed out waiting for the semaphore. Make | ||
316 | * sure the count is reset. */ | ||
317 | while (SDL_SemValue(current->context.s) > 0) | ||
318 | SDL_SemTryWait(current->context.s); | ||
319 | } | ||
320 | |||
321 | restore_irq(oldlevel); | ||
322 | break; | ||
323 | } /* STATE_BLOCKED_W_TMO: */ | ||
324 | |||
325 | case STATE_SLEEPING: | ||
326 | { | ||
327 | SDL_UnlockMutex(m); | ||
328 | SDL_SemWaitTimeout(current->context.s, current->tmo_tick); | ||
329 | SDL_LockMutex(m); | ||
330 | current->state = STATE_RUNNING; | ||
331 | break; | ||
332 | } /* STATE_SLEEPING: */ | ||
333 | } | ||
334 | |||
335 | cores[CURRENT_CORE].running = current; | ||
336 | |||
337 | if (threads_exit) | ||
338 | thread_exit(); | ||
339 | } | ||
340 | |||
341 | void sleep_thread(int ticks) | ||
342 | { | ||
343 | struct thread_entry *current = cores[CURRENT_CORE].running; | ||
344 | int rem; | ||
345 | |||
346 | current->state = STATE_SLEEPING; | ||
347 | |||
348 | rem = (SDL_GetTicks() - start_tick) % (1000/HZ); | ||
349 | if (rem < 0) | ||
350 | rem = 0; | ||
351 | |||
352 | current->tmo_tick = (1000/HZ) * ticks + ((1000/HZ)-1) - rem; | ||
353 | } | ||
354 | |||
355 | void block_thread(struct thread_entry *current) | ||
356 | { | ||
357 | current->state = STATE_BLOCKED; | ||
358 | add_to_list_l(current->bqp, current); | ||
359 | } | ||
360 | |||
361 | void block_thread_w_tmo(struct thread_entry *current, int ticks) | ||
362 | { | ||
363 | current->state = STATE_BLOCKED_W_TMO; | ||
364 | current->tmo_tick = (1000/HZ)*ticks; | ||
365 | add_to_list_l(current->bqp, current); | ||
366 | } | ||
367 | |||
368 | unsigned int wakeup_thread(struct thread_entry **list) | ||
369 | { | ||
370 | struct thread_entry *thread = *list; | ||
371 | |||
372 | if (thread != NULL) | ||
373 | { | ||
374 | switch (thread->state) | ||
375 | { | ||
376 | case STATE_BLOCKED: | ||
377 | case STATE_BLOCKED_W_TMO: | ||
378 | remove_from_list_l(list, thread); | ||
379 | thread->state = STATE_RUNNING; | ||
380 | SDL_SemPost(thread->context.s); | ||
381 | return THREAD_OK; | ||
382 | } | ||
383 | } | ||
384 | |||
385 | return THREAD_NONE; | ||
386 | } | ||
387 | |||
388 | unsigned int thread_queue_wake(struct thread_entry **list) | ||
389 | { | ||
390 | unsigned int result = THREAD_NONE; | ||
391 | |||
392 | for (;;) | ||
393 | { | ||
394 | unsigned int rc = wakeup_thread(list); | ||
395 | |||
396 | if (rc == THREAD_NONE) | ||
397 | break; | ||
398 | |||
399 | result |= rc; | ||
400 | } | ||
401 | |||
402 | return result; | ||
403 | } | ||
404 | |||
405 | void thread_thaw(unsigned int thread_id) | ||
406 | { | ||
407 | struct thread_entry *thread = thread_id_entry(thread_id); | ||
408 | |||
409 | if (thread->id == thread_id && thread->state == STATE_FROZEN) | ||
410 | { | ||
411 | thread->state = STATE_RUNNING; | ||
412 | SDL_SemPost(thread->context.s); | ||
413 | } | ||
414 | } | ||
415 | |||
416 | int runthread(void *data) | ||
417 | { | ||
418 | struct thread_entry *current; | ||
419 | jmp_buf *current_jmpbuf; | ||
420 | |||
421 | /* Cannot access thread variables before locking the mutex as the | ||
422 | data structures may not be filled-in yet. */ | ||
423 | SDL_LockMutex(m); | ||
424 | cores[CURRENT_CORE].running = (struct thread_entry *)data; | ||
425 | current = cores[CURRENT_CORE].running; | ||
426 | current_jmpbuf = &thread_jmpbufs[current - threads]; | ||
427 | |||
428 | /* Setup jump for exit */ | ||
429 | if (setjmp(*current_jmpbuf) == 0) | ||
430 | { | ||
431 | /* Run the thread routine */ | ||
432 | if (current->state == STATE_FROZEN) | ||
433 | { | ||
434 | SDL_UnlockMutex(m); | ||
435 | SDL_SemWait(current->context.s); | ||
436 | SDL_LockMutex(m); | ||
437 | cores[CURRENT_CORE].running = current; | ||
438 | } | ||
439 | |||
440 | if (!threads_exit) | ||
441 | { | ||
442 | current->context.start(); | ||
443 | THREAD_SDL_DEBUGF("Thread Done: %d (%s)\n", | ||
444 | current - threads, THREAD_SDL_GET_NAME(current)); | ||
445 | /* Thread routine returned - suicide */ | ||
446 | } | ||
447 | |||
448 | thread_exit(); | ||
449 | } | ||
450 | else | ||
451 | { | ||
452 | /* Unlock and exit */ | ||
453 | SDL_UnlockMutex(m); | ||
454 | } | ||
455 | |||
456 | return 0; | ||
457 | } | ||
458 | |||
459 | unsigned int create_thread(void (*function)(void), | ||
460 | void* stack, size_t stack_size, | ||
461 | unsigned flags, const char *name) | ||
462 | { | ||
463 | struct thread_entry *thread; | ||
464 | SDL_Thread* t; | ||
465 | SDL_sem *s; | ||
466 | |||
467 | THREAD_SDL_DEBUGF("Creating thread: (%s)\n", name ? name : ""); | ||
468 | |||
469 | thread = find_empty_thread_slot(); | ||
470 | if (thread == NULL) | ||
471 | { | ||
472 | DEBUGF("Failed to find thread slot\n"); | ||
473 | return 0; | ||
474 | } | ||
475 | |||
476 | s = SDL_CreateSemaphore(0); | ||
477 | if (s == NULL) | ||
478 | { | ||
479 | DEBUGF("Failed to create semaphore\n"); | ||
480 | return 0; | ||
481 | } | ||
482 | |||
483 | t = SDL_CreateThread(runthread, thread); | ||
484 | if (t == NULL) | ||
485 | { | ||
486 | DEBUGF("Failed to create SDL thread\n"); | ||
487 | SDL_DestroySemaphore(s); | ||
488 | return 0; | ||
489 | } | ||
490 | |||
491 | thread->stack = stack; | ||
492 | thread->stack_size = stack_size; | ||
493 | thread->name = name; | ||
494 | thread->state = (flags & CREATE_THREAD_FROZEN) ? | ||
495 | STATE_FROZEN : STATE_RUNNING; | ||
496 | thread->context.start = function; | ||
497 | thread->context.t = t; | ||
498 | thread->context.s = s; | ||
499 | |||
500 | THREAD_SDL_DEBUGF("New Thread: %d (%s)\n", | ||
501 | thread - threads, THREAD_SDL_GET_NAME(thread)); | ||
502 | |||
503 | return thread->id; | ||
504 | } | ||
505 | |||
506 | #ifndef ALLOW_REMOVE_THREAD | ||
507 | static void remove_thread(unsigned int thread_id) | ||
508 | #else | ||
509 | void remove_thread(unsigned int thread_id) | ||
510 | #endif | ||
511 | { | ||
512 | struct thread_entry *current = cores[CURRENT_CORE].running; | ||
513 | struct thread_entry *thread = thread_id_entry(thread_id); | ||
514 | |||
515 | SDL_Thread *t; | ||
516 | SDL_sem *s; | ||
517 | |||
518 | if (thread_id != THREAD_ID_CURRENT && thread->id != thread_id) | ||
519 | return; | ||
520 | |||
521 | int oldlevel = disable_irq_save(); | ||
522 | |||
523 | t = thread->context.t; | ||
524 | s = thread->context.s; | ||
525 | thread->context.t = NULL; | ||
526 | |||
527 | if (thread != current) | ||
528 | { | ||
529 | switch (thread->state) | ||
530 | { | ||
531 | case STATE_BLOCKED: | ||
532 | case STATE_BLOCKED_W_TMO: | ||
533 | /* Remove thread from object it's waiting on */ | ||
534 | remove_from_list_l(thread->bqp, thread); | ||
535 | |||
536 | #ifdef HAVE_WAKEUP_EXT_CB | ||
537 | if (thread->wakeup_ext_cb != NULL) | ||
538 | thread->wakeup_ext_cb(thread); | ||
539 | #endif | ||
540 | break; | ||
541 | } | ||
542 | |||
543 | SDL_SemPost(s); | ||
544 | } | ||
545 | |||
546 | THREAD_SDL_DEBUGF("Removing thread: %d (%s)\n", | ||
547 | thread - threads, THREAD_SDL_GET_NAME(thread)); | ||
548 | |||
549 | new_thread_id(thread->id, thread); | ||
550 | thread->state = STATE_KILLED; | ||
551 | thread_queue_wake(&thread->queue); | ||
552 | |||
553 | SDL_DestroySemaphore(s); | ||
554 | |||
555 | if (thread == current) | ||
556 | { | ||
557 | /* Do a graceful exit - perform the longjmp back into the thread | ||
558 | function to return */ | ||
559 | restore_irq(oldlevel); | ||
560 | longjmp(thread_jmpbufs[current - threads], 1); | ||
561 | } | ||
562 | |||
563 | SDL_KillThread(t); | ||
564 | restore_irq(oldlevel); | ||
565 | } | ||
566 | |||
567 | void thread_exit(void) | ||
568 | { | ||
569 | remove_thread(THREAD_ID_CURRENT); | ||
570 | } | ||
571 | |||
572 | void thread_wait(unsigned int thread_id) | ||
573 | { | ||
574 | struct thread_entry *current = cores[CURRENT_CORE].running; | ||
575 | struct thread_entry *thread = thread_id_entry(thread_id); | ||
576 | |||
577 | if (thread_id == THREAD_ID_CURRENT || | ||
578 | (thread->id == thread_id && thread->state != STATE_KILLED)) | ||
579 | { | ||
580 | current->bqp = &thread->queue; | ||
581 | block_thread(current); | ||
582 | switch_thread(); | ||
583 | } | ||
584 | } | ||
585 | |||
586 | int thread_stack_usage(const struct thread_entry *thread) | ||
587 | { | ||
588 | return 50; | ||
589 | (void)thread; | ||
590 | } | ||
591 | |||
592 | /* Return name if one or ID if none */ | ||
593 | void thread_get_name(char *buffer, int size, | ||
594 | struct thread_entry *thread) | ||
595 | { | ||
596 | if (size <= 0) | ||
597 | return; | ||
598 | |||
599 | *buffer = '\0'; | ||
600 | |||
601 | if (thread) | ||
602 | { | ||
603 | /* Display thread name if one or ID if none */ | ||
604 | bool named = thread->name && *thread->name; | ||
605 | const char *fmt = named ? "%s" : "%08lX"; | ||
606 | intptr_t name = named ? | ||
607 | (intptr_t)thread->name : (intptr_t)thread; | ||
608 | snprintf(buffer, size, fmt, name); | ||
609 | } | ||
610 | } | ||
diff --git a/firmware/target/hosted/sdl/thread-sdl.h b/firmware/target/hosted/sdl/thread-sdl.h new file mode 100644 index 0000000000..9384e6060d --- /dev/null +++ b/firmware/target/hosted/sdl/thread-sdl.h | |||
@@ -0,0 +1,32 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 Dan Everton | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #ifndef __THREADSDL_H__ | ||
23 | #define __THREADSDL_H__ | ||
24 | |||
25 | /* extra thread functions that only apply when running on hosting platforms */ | ||
26 | void sim_thread_lock(void *me); | ||
27 | void * sim_thread_unlock(void); | ||
28 | void sim_thread_exception_wait(void); | ||
29 | void sim_thread_shutdown(void); /* Shut down all kernel threads gracefully */ | ||
30 | |||
31 | #endif /* #ifndef __THREADSDL_H__ */ | ||
32 | |||
diff --git a/firmware/target/hosted/sdl/timer-sdl.c b/firmware/target/hosted/sdl/timer-sdl.c new file mode 100644 index 0000000000..369aeab929 --- /dev/null +++ b/firmware/target/hosted/sdl/timer-sdl.c | |||
@@ -0,0 +1,61 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id: timer.h 13806 2007-07-06 21:36:32Z jethead71 $ | ||
9 | * | ||
10 | * Copyright (C) 2005 Kévin Ferrare | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
22 | #include "timer.h" | ||
23 | #include <SDL_timer.h> | ||
24 | |||
25 | static int timer_prio = -1; | ||
26 | void (*global_timer_callback)(void); | ||
27 | SDL_TimerID timerId; | ||
28 | |||
29 | Uint32 SDL_timer_callback(Uint32 interval, void *param){ | ||
30 | (void)param; | ||
31 | global_timer_callback(); | ||
32 | return(interval); | ||
33 | } | ||
34 | |||
35 | #define cycles_to_miliseconds(cycles) \ | ||
36 | ((int)((1000*cycles)/TIMER_FREQ)) | ||
37 | |||
38 | bool timer_register(int reg_prio, void (*unregister_callback)(void), | ||
39 | long cycles, void (*timer_callback)(void)) | ||
40 | { | ||
41 | (void)unregister_callback; | ||
42 | if (reg_prio <= timer_prio || cycles == 0) | ||
43 | return false; | ||
44 | timer_prio=reg_prio; | ||
45 | global_timer_callback=timer_callback; | ||
46 | timerId=SDL_AddTimer(cycles_to_miliseconds(cycles), SDL_timer_callback, 0); | ||
47 | return true; | ||
48 | } | ||
49 | |||
50 | bool timer_set_period(long cycles) | ||
51 | { | ||
52 | SDL_RemoveTimer (timerId); | ||
53 | timerId=SDL_AddTimer(cycles_to_miliseconds(cycles), SDL_timer_callback, 0); | ||
54 | return true; | ||
55 | } | ||
56 | |||
57 | void timer_unregister(void) | ||
58 | { | ||
59 | SDL_RemoveTimer (timerId); | ||
60 | timer_prio = -1; | ||
61 | } | ||