1 /***************************************************************************
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
10 * Copyright (C) 2002 Kjell Ericson
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.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
25 /* variable button definitions */
26 #if CONFIG_KEYPAD == RECORDER_PAD
27 #define CHC_QUIT BUTTON_OFF
28 #define CHC_STARTSTOP BUTTON_PLAY
29 #define CHC_RESET BUTTON_LEFT
30 #define CHC_MENU BUTTON_F1
31 #define CHC_SETTINGS_INC BUTTON_UP
32 #define CHC_SETTINGS_DEC BUTTON_DOWN
33 #define CHC_SETTINGS_OK BUTTON_PLAY
34 #define CHC_SETTINGS_OK2 BUTTON_LEFT
35 #define CHC_SETTINGS_CANCEL BUTTON_OFF
37 #elif CONFIG_KEYPAD == ARCHOS_AV300_PAD
38 #define CHC_QUIT BUTTON_OFF
39 #define CHC_STARTSTOP BUTTON_SELECT
40 #define CHC_RESET BUTTON_LEFT
41 #define CHC_MENU BUTTON_F1
42 #define CHC_SETTINGS_INC BUTTON_UP
43 #define CHC_SETTINGS_DEC BUTTON_DOWN
44 #define CHC_SETTINGS_OK BUTTON_SELECT
45 #define CHC_SETTINGS_OK2 BUTTON_LEFT
46 #define CHC_SETTINGS_CANCEL BUTTON_OFF
48 #elif CONFIG_KEYPAD == ONDIO_PAD
49 #define CHC_QUIT BUTTON_OFF
50 #define CHC_STARTSTOP BUTTON_RIGHT
51 #define CHC_RESET BUTTON_LEFT
52 #define CHC_MENU BUTTON_MENU
53 #define CHC_SETTINGS_INC BUTTON_UP
54 #define CHC_SETTINGS_DEC BUTTON_DOWN
55 #define CHC_SETTINGS_OK BUTTON_RIGHT
56 #define CHC_SETTINGS_OK2 BUTTON_LEFT
57 #define CHC_SETTINGS_CANCEL BUTTON_MENU
59 #elif CONFIG_KEYPAD == PLAYER_PAD
60 #define CHC_QUIT BUTTON_ON
61 #define CHC_STARTSTOP BUTTON_PLAY
62 #define CHC_RESET BUTTON_STOP
63 #define CHC_MENU BUTTON_MENU
64 #define CHC_SETTINGS_INC BUTTON_RIGHT
65 #define CHC_SETTINGS_DEC BUTTON_LEFT
66 #define CHC_SETTINGS_OK BUTTON_PLAY
67 #define CHC_SETTINGS_CANCEL BUTTON_STOP
68 #define CHC_SETTINGS_CANCEL2 BUTTON_MENU
70 #elif (CONFIG_KEYPAD == IRIVER_H100_PAD) || \
71 (CONFIG_KEYPAD == IRIVER_H300_PAD)
72 #define CHC_QUIT BUTTON_SELECT
73 #define CHC_STARTSTOP BUTTON_ON
74 #define CHC_RESET BUTTON_OFF
75 #define CHC_MENU BUTTON_REC
76 #define CHC_SETTINGS_INC BUTTON_RIGHT
77 #define CHC_SETTINGS_DEC BUTTON_LEFT
78 #define CHC_SETTINGS_OK BUTTON_ON
79 #define CHC_SETTINGS_CANCEL BUTTON_OFF
80 #define CHC_SETTINGS_CANCEL2 BUTTON_REC
82 #elif (CONFIG_KEYPAD == IPOD_4G_PAD) || \
83 (CONFIG_KEYPAD == IPOD_3G_PAD) || \
84 (CONFIG_KEYPAD == IPOD_1G2G_PAD)
85 #define CHC_QUIT BUTTON_PLAY
86 #define CHC_STARTSTOP BUTTON_SELECT
87 #define CHC_RESET BUTTON_LEFT
88 #define CHC_MENU BUTTON_MENU
89 #define CHC_SETTINGS_INC BUTTON_SCROLL_FWD
90 #define CHC_SETTINGS_DEC BUTTON_SCROLL_BACK
91 #define CHC_SETTINGS_OK BUTTON_SELECT
92 #define CHC_SETTINGS_CANCEL BUTTON_MENU
94 #elif CONFIG_KEYPAD == IRIVER_IFP7XX_PAD
95 #define CHC_QUIT BUTTON_PLAY
96 #define CHC_STARTSTOP BUTTON_MODE
97 #define CHC_RESET BUTTON_EQ
98 #define CHC_MENU BUTTON_SELECT
99 #define CHC_SETTINGS_INC BUTTON_RIGHT
100 #define CHC_SETTINGS_DEC BUTTON_LEFT
101 #define CHC_SETTINGS_OK BUTTON_SELECT
102 #define CHC_SETTINGS_CANCEL BUTTON_PLAY
104 #elif CONFIG_KEYPAD == IAUDIO_X5M5_PAD
105 #define CHC_QUIT BUTTON_REC
106 #define CHC_STARTSTOP BUTTON_PLAY
107 #define CHC_RESET BUTTON_POWER
108 #define CHC_MENU BUTTON_SELECT
109 #define CHC_SETTINGS_INC BUTTON_RIGHT
110 #define CHC_SETTINGS_DEC BUTTON_LEFT
111 #define CHC_SETTINGS_OK BUTTON_SELECT
112 #define CHC_SETTINGS_CANCEL BUTTON_REC
114 #elif CONFIG_KEYPAD == GIGABEAT_PAD
115 #define CHC_QUIT BUTTON_POWER
116 #define CHC_STARTSTOP BUTTON_SELECT
117 #define CHC_RESET BUTTON_A
118 #define CHC_MENU BUTTON_MENU
119 #define CHC_SETTINGS_INC BUTTON_UP
120 #define CHC_SETTINGS_DEC BUTTON_DOWN
121 #define CHC_SETTINGS_OK BUTTON_SELECT
122 #define CHC_SETTINGS_CANCEL BUTTON_POWER
124 #elif (CONFIG_KEYPAD == SANSA_E200_PAD) || \
125 (CONFIG_KEYPAD == SANSA_C200_PAD)
126 #define CHC_QUIT BUTTON_POWER
127 #define CHC_STARTSTOP BUTTON_SELECT
128 #define CHC_RESET BUTTON_DOWN
129 #define CHC_MENU BUTTON_UP
130 #define CHC_SETTINGS_INC BUTTON_RIGHT
131 #define CHC_SETTINGS_DEC BUTTON_LEFT
132 #define CHC_SETTINGS_OK BUTTON_SELECT
133 #define CHC_SETTINGS_CANCEL BUTTON_POWER
135 #elif CONFIG_KEYPAD == IRIVER_H10_PAD
136 #define CHC_QUIT BUTTON_POWER
137 #define CHC_STARTSTOP BUTTON_PLAY
138 #define CHC_RESET BUTTON_FF
139 #define CHC_MENU BUTTON_REW
140 #define CHC_SETTINGS_INC BUTTON_RIGHT
141 #define CHC_SETTINGS_DEC BUTTON_LEFT
142 #define CHC_SETTINGS_OK BUTTON_PLAY
143 #define CHC_SETTINGS_CANCEL BUTTON_POWER
145 #elif CONFIG_KEYPAD == MROBE500_PAD
146 #define CHC_QUIT BUTTON_POWER
147 #define CHC_STARTSTOP BUTTON_RC_PLAY
148 #define CHC_RESET BUTTON_RC_HEART
149 #define CHC_MENU BUTTON_RC_MODE
150 #define CHC_SETTINGS_INC BUTTON_RC_VOL_UP
151 #define CHC_SETTINGS_DEC BUTTON_RC_VOL_DOWN
152 #define CHC_SETTINGS_OK BUTTON_RC_PLAY
153 #define CHC_SETTINGS_CANCEL BUTTON_POWER
155 #elif CONFIG_KEYPAD == GIGABEAT_S_PAD
156 #define CHC_QUIT BUTTON_BACK
157 #define CHC_STARTSTOP BUTTON_PLAY
158 #define CHC_RESET BUTTON_PREV
159 #define CHC_MENU BUTTON_MENU
160 #define CHC_SETTINGS_INC BUTTON_UP
161 #define CHC_SETTINGS_DEC BUTTON_DOWN
162 #define CHC_SETTINGS_OK BUTTON_SELECT
163 #define CHC_SETTINGS_CANCEL BUTTON_BACK
165 #elif CONFIG_KEYPAD == MROBE100_PAD
166 #define CHC_QUIT BUTTON_POWER
167 #define CHC_STARTSTOP BUTTON_SELECT
168 #define CHC_RESET BUTTON_DISPLAY
169 #define CHC_MENU BUTTON_MENU
170 #define CHC_SETTINGS_INC BUTTON_UP
171 #define CHC_SETTINGS_DEC BUTTON_DOWN
172 #define CHC_SETTINGS_OK BUTTON_SELECT
173 #define CHC_SETTINGS_CANCEL BUTTON_POWER
175 #elif CONFIG_KEYPAD == IAUDIO_M3_PAD
176 #define CHC_QUIT BUTTON_RC_REC
177 #define CHC_STARTSTOP BUTTON_RC_PLAY
178 #define CHC_RESET BUTTON_RC_REW
179 #define CHC_MENU BUTTON_RC_MENU
180 #define CHC_SETTINGS_INC BUTTON_RC_VOL_UP
181 #define CHC_SETTINGS_DEC BUTTON_RC_VOL_DOWN
182 #define CHC_SETTINGS_OK BUTTON_RC_PLAY
183 #define CHC_SETTINGS_CANCEL BUTTON_RC_REC
185 #elif CONFIG_KEYPAD == COWOND2_PAD
186 #define CHC_QUIT BUTTON_POWER
187 #define CHC_RESET (BUTTON_CENTER|BUTTON_MENU)
188 #define CHC_MENU BUTTON_MENU
189 #define CHC_SETTINGS_INC BUTTON_PLUS
190 #define CHC_SETTINGS_DEC BUTTON_MINUS
191 #define CHC_SETTINGS_CANCEL BUTTON_POWER
193 #elif CONFIG_KEYPAD == IAUDIO67_PAD
194 #define CHC_QUIT BUTTON_POWER
195 #define CHC_STARTSTOP BUTTON_PLAY
196 #define CHC_RESET BUTTON_LEFT
197 #define CHC_MENU BUTTON_MENU
198 #define CHC_SETTINGS_INC BUTTON_VOLUP
199 #define CHC_SETTINGS_DEC BUTTON_VOLDOWN
200 #define CHC_SETTINGS_OK BUTTON_PLAY
201 #define CHC_SETTINGS_OK2 BUTTON_LEFT
202 #define CHC_SETTINGS_CANCEL BUTTON_POWER
205 #error No keymap defined!
208 #ifdef HAVE_TOUCHSCREEN
209 #ifndef CHC_SETTINGS_OK
210 #define CHC_SETTINGS_OK BUTTON_CENTER
212 #ifndef CHC_STARTSTOP
213 #define CHC_STARTSTOP BUTTON_CENTER
215 #ifndef CHC_SETTINGS_INC
216 #define CHC_SETTINGS_INC BUTTON_TOPMIDDLE
218 #ifndef CHC_SETTINGS_DEC
219 #define CHC_SETTINGS_DEC BUTTON_BOTTOMMIDDLE
222 #define CHC_RESET BUTTON_TOPLEFT
225 #define CHC_MENU BUTTON_TOPRIGHT
230 /* leave first line blank on bitmap display, for pause icon */
231 #ifdef HAVE_LCD_BITMAP
237 /* here is a global api struct pointer. while not strictly necessary,
238 it's nice not to have to pass the api pointer in all function calls
240 static const struct plugin_api
* rb
;
241 MEM_FUNCTION_WRAPPERS(rb
);
242 #define MAX_PLAYERS 10
254 } timer_holder
[MAX_PLAYERS
];
256 static int run_timer(int nr
);
257 static int chessclock_set_int(char* string
,
263 #define FLAGS_SET_INT_SECONDS 1
265 static char * show_time(int secs
);
266 static int simple_menu(int nr
, unsigned char **strarr
);
270 #define MAX_TIME 7200
272 /* this is the plugin entry point */
273 enum plugin_status
plugin_start(const struct plugin_api
* api
, const void* parameter
)
281 rb
->memset(&settings
, 0, sizeof(settings
));
283 /* now go ahead and have fun! */
284 rb
->splash(HZ
, "Chess Clock");
286 rb
->lcd_clear_display();
292 res
=chessclock_set_int("Number of players",
293 &settings
.nr_timers
, 1, 1,
297 res
=chessclock_set_int("Total time",
298 &settings
.total_time
, 10, 0, MAX_TIME
,
299 FLAGS_SET_INT_SECONDS
);
300 settings
.round_time
=settings
.total_time
;
303 res
=chessclock_set_int("Max round time", &settings
.round_time
,
304 10, 0, settings
.round_time
,
305 FLAGS_SET_INT_SECONDS
);
313 return PLUGIN_USB_CONNECTED
;
325 for (i
=0; i
<settings
.nr_timers
; i
++) {
326 timer_holder
[i
].total_time
=settings
.total_time
;
327 timer_holder
[i
].used_time
=0;
328 timer_holder
[i
].hidden
=false;
331 pause
=true; /* We start paused */
337 for (i
=0; done
&& i
<settings
.nr_timers
; i
++) {
338 if (!timer_holder
[i
].hidden
)
344 if (!timer_holder
[nr
].hidden
) {
353 return PLUGIN_USB_CONNECTED
;
356 if (nr
>=settings
.nr_timers
)
362 nr
=settings
.nr_timers
-1;
369 #ifdef HAVE_LCD_BITMAP
370 static void show_pause_mode(bool enabled
)
372 static const char pause_icon
[] = {0x00,0x7f,0x7f,0x00,0x7f,0x7f,0x00};
375 rb
->lcd_mono_bitmap((unsigned char *)pause_icon
, 52, 0, 7, 8);
378 rb
->lcd_set_drawmode(DRMODE_SOLID
|DRMODE_INVERSEVID
);
379 rb
->lcd_fillrect(52, 0, 7, 8);
380 rb
->lcd_set_drawmode(DRMODE_SOLID
);
391 static int run_timer(int nr
)
394 char player_info
[13];
398 long max_ticks
=timer_holder
[nr
].total_time
*HZ
-timer_holder
[nr
].used_time
;
400 bool round_time
=false;
402 #ifdef HAVE_LCD_CHARCELLS
403 rb
->lcd_icon(ICON_PAUSE
, pause
);
405 show_pause_mode(pause
);
408 if (settings
.round_time
*HZ
<max_ticks
) {
409 max_ticks
=settings
.round_time
*HZ
;
412 rb
->snprintf(player_info
, sizeof(player_info
), "Player %d", nr
+1);
413 rb
->lcd_puts(0, FIRST_LINE
, (unsigned char *)player_info
);
414 last_tick
=*rb
->current_tick
;
419 if (ticks
>max_ticks
) {
421 rb
->lcd_puts(0, FIRST_LINE
+1, (unsigned char *)"ROUND UP!");
423 rb
->lcd_puts(0, FIRST_LINE
+1, (unsigned char *)"TIME OUT!");
427 if (((int)(rb->current_tick - start_ticks)/HZ)&1) {
428 rb->lcd_puts(0, FIRST_LINE, player_info);
430 rb->lcd_puts(0, FIRST_LINE, player_info);
433 rb
->lcd_puts(0, FIRST_LINE
, (unsigned char *)player_info
);
434 now
=*rb
->current_tick
;
436 ticks
+=now
-last_tick
;
437 if ((max_ticks
-ticks
)/HZ
== 10) {
438 /* Backlight on if 10 seconds remain */
444 rb
->snprintf(buf
, sizeof(buf
), "%s/",
445 show_time((max_ticks
-ticks
+HZ
-1)/HZ
));
446 /* Append total time */
447 rb
->strcpy(&buf
[rb
->strlen(buf
)],
448 show_time((timer_holder
[nr
].total_time
*HZ
-
449 timer_holder
[nr
].used_time
-
451 rb
->lcd_puts(0, FIRST_LINE
+1, (unsigned char *)buf
);
453 rb
->lcd_puts(0, FIRST_LINE
+1,
454 (unsigned char *)show_time((max_ticks
-ticks
+HZ
-1)/HZ
));
459 button
= rb
->button_get(false);
461 /* OFF/ON key to exit */
463 return -1; /* Indicate exit */
465 /* PLAY = Stop/Start toggle */
468 #ifdef HAVE_LCD_CHARCELLS
469 rb
->lcd_icon(ICON_PAUSE
, pause
);
471 show_pause_mode(pause
);
475 /* LEFT = Reset timer */
484 char *menu
[]={"Delete player", "Restart round",
485 "Set round time", "Set total time"};
486 ret
=simple_menu(4, (unsigned char **)menu
);
490 } else if (ret
==-2) {
493 timer_holder
[nr
].hidden
=true;
504 int val
=(max_ticks
-ticks
)/HZ
;
505 res
=chessclock_set_int("Round time",
508 FLAGS_SET_INT_SECONDS
);
509 if (res
==-1) { /*usb*/
513 ticks
=max_ticks
-val
*HZ
;
518 int val
=timer_holder
[nr
].total_time
;
519 res
=chessclock_set_int("Total time",
522 FLAGS_SET_INT_SECONDS
);
523 if (res
==-1) { /*usb*/
527 timer_holder
[nr
].total_time
=val
;
533 /* UP (RIGHT/+) = Scroll Lap timer up */
534 case CHC_SETTINGS_INC
:
539 /* DOWN (LEFT/-) = Scroll Lap timer down */
540 case CHC_SETTINGS_DEC
:
546 if (rb
->default_event_handler(button
) == SYS_USB_CONNECTED
) {
547 retval
= 3; /* been in usb mode */
552 rb
->sleep(HZ
/4); /* Sleep 1/4 of a second */
555 timer_holder
[nr
].used_time
+=ticks
;
560 static int chessclock_set_int(char* string
,
570 rb
->lcd_clear_display();
571 rb
->lcd_puts_scroll(0, FIRST_LINE
, (unsigned char *)string
);
575 if (flags
& FLAGS_SET_INT_SECONDS
)
576 rb
->snprintf(str
, sizeof str
,"%s (m:s)", show_time(*variable
));
578 rb
->snprintf(str
, sizeof str
,"%d", *variable
);
579 rb
->lcd_puts(0, FIRST_LINE
+1, (unsigned char *)str
);
582 button
= rb
->button_get(true);
584 case CHC_SETTINGS_INC
:
585 case CHC_SETTINGS_INC
| BUTTON_REPEAT
:
589 case CHC_SETTINGS_DEC
:
590 case CHC_SETTINGS_DEC
| BUTTON_REPEAT
:
594 case CHC_SETTINGS_OK
:
595 #ifdef CHC_SETTINGS_OK2
596 case CHC_SETTINGS_OK2
:
601 case CHC_SETTINGS_CANCEL
:
602 #ifdef CHC_SETTINGS_CANCEL2
603 case CHC_SETTINGS_CANCEL2
:
605 return 0; /* cancel */
609 if (rb
->default_event_handler(button
) == SYS_USB_CONNECTED
)
610 return -1; /* been in usb mode */
621 rb
->lcd_stop_scroll();
626 static char * show_time(int seconds
)
628 static char buf
[]="00:00";
629 rb
->snprintf(buf
, sizeof(buf
), "%02d:%02d", seconds
/60, seconds
%60);
636 static int simple_menu(int nr
, unsigned char **strarr
)
640 rb
->lcd_clear_display();
647 rb
->lcd_puts_scroll(0, FIRST_LINE
, strarr
[show
]);
650 button
= rb
->button_get(true);
652 case CHC_SETTINGS_INC
:
653 case CHC_SETTINGS_INC
| BUTTON_REPEAT
:
657 case CHC_SETTINGS_DEC
:
658 case CHC_SETTINGS_DEC
| BUTTON_REPEAT
:
662 case CHC_SETTINGS_OK
:
663 #ifdef CHC_SETTINGS_OK2
664 case CHC_SETTINGS_OK2
:
669 case CHC_SETTINGS_CANCEL
:
670 #ifdef CHC_SETTINGS_CANCEL2
671 case CHC_SETTINGS_CANCEL2
:
673 return -2; /* cancel */
677 if (rb
->default_event_handler(button
) == SYS_USB_CONNECTED
)
678 return -1; /* been in usb mode */