summaryrefslogtreecommitdiff
path: root/apps/plugins/clock.c
diff options
context:
space:
mode:
Diffstat (limited to 'apps/plugins/clock.c')
-rw-r--r--apps/plugins/clock.c1673
1 files changed, 0 insertions, 1673 deletions
diff --git a/apps/plugins/clock.c b/apps/plugins/clock.c
deleted file mode 100644
index 71415c03d4..0000000000
--- a/apps/plugins/clock.c
+++ /dev/null
@@ -1,1673 +0,0 @@
1/***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
9 *
10 * Copyright (C) 2003 Zakk Roberts
11 *
12 * All files in this archive are subject to the GNU General Public License.
13 * See the file COPYING in the source tree root for full license agreement.
14 *
15 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
16 * KIND, either express or implied.
17 *
18 ****************************************************************************/
19
20/*****************************
21 * RELEASE NOTES
22
23***** VERSION 4.00 **
24New almost entirely bitmap based display. Scales to all resolutions. Combined
25Digital and LCD modes into one. Use Rockbox menu code for the menu. Removed
26count-down option. A couple new options. Source code reworked, improved, cleaned
27up.
28
29***** VERSION 3.10 **
30Drawing now scales for the display - still needs updated bitmaps for the binary
31and plain mode. The Time's Up logo could also be updated.
32
33***** VERSION 3.00 **
34New, simpler UI - every screen can be accessed from the new Main Menu.
35Huge code cleanup - many major functions rewritten and optimized,
36targeting scalability. Number of variables reduced majorly.
37New clock mode: Plain (simple, large text). ON now controls counter
38(press toggle/hold reset). Fancier credits roll. New logo. iRiver and iPod ports
39are working but not yet scaled to fit their LCDs.
40
41***** VERSION 2.60 **
42Fixed general settings typo, split up settings function, added cursor animations,
43and updated cursor look (rounded edges).
44
45***** VERSION 2.51 **
46"Show Counter" option is now saved to disk
47
48***** VERSION 2.50 **
49New general settings mode added, reworked options screen, cleaned up a few
50things and removed redundant code, faster load_settings(), fixed a
51help-screen bug (thanks to zeekoe)
52
53***** VERSION 2.40 **
54Cleaned and optimized code, removed unused code/bitmaps, credits screen updated,
55centered text all over, general settings added at ON+F3,
56new arrow bitmap for general settings and mode selector,
57bugfix: 12:00AM is no longer 00:00AM
58
59***** VERSION 2.31 **
60Fixed credits roll - now displays all names. Features
61improved animations. Also revised release notes.
62
63***** VERSION 2.30 **
64Tab indentation removed, and Counter screen added
65at ON+F2, with countdown options
66
67***** VERSION 2.22 **
68Fixed two bugs:
69Digital settings are now independent of LCD settings
7012/24h "Analog" settings are now displayed correctly.
71
72***** VERSION 2.21 **
73-Changed the behaviour of F2
74
75***** VERSION 2.20 **
76Few small bugs taken care of. New features:
77New binary mode, new mode selector, "counter", and redesigned help screen.
78
79***** VERSION 2.10 **
80New bug fixes, and some new features:
81an LCD imitation mode, and American and European date modes.
82
83***** VERSION 2.00 **
84Major update, lots of bugfixes and new features.
85Fullscreen mode introduced, modes have independent settings, credit roll
86added, options screen reworked, logo selector, and -much- cleaner code.
87
88***** VERSION 1.0 **
89Original release, featuring analog/digital modes and a few options.
90*****************************/
91#include "plugin.h"
92#include "time.h"
93#include "checkbox.h"
94#include "xlcd.h"
95#include "oldmenuapi.h"
96#include "fixedpoint.h"
97#include "pluginlib_actions.h"
98
99PLUGIN_HEADER
100
101/* External bitmap references */
102#include "clock_digits.h"
103#include "clock_smalldigits.h"
104#include "clock_smallsegments.h"
105#include "clock_messages.h"
106#include "clock_logo.h"
107#include "clock_segments.h"
108
109/* Bitmap positions/deltas, per LCD size */
110#if (LCD_WIDTH >= 112) && (LCD_HEIGHT >= 64) && (LCD_DEPTH >= 1) /* Archos */
111#define LCD_OFFSET 1
112#define HAND_W 2
113#else
114#define LCD_OFFSET 1.5
115#define HAND_W 3
116#endif
117
118#define DIGIT_WIDTH BMPWIDTH_clock_digits
119#define DIGIT_HEIGHT (BMPHEIGHT_clock_digits/15)
120#define SMALLDIGIT_WIDTH BMPWIDTH_clock_smalldigits
121#define SMALLDIGIT_HEIGHT (BMPHEIGHT_clock_smalldigits/13)
122#define SMALLSEG_WIDTH BMPWIDTH_clock_smallsegments
123#define SMALLSEG_HEIGHT (BMPHEIGHT_clock_smallsegments/13)
124#define MESSAGE_WIDTH BMPWIDTH_clock_messages
125#define MESSAGE_HEIGHT (BMPHEIGHT_clock_messages/6)
126#define LOGO_WIDTH BMPWIDTH_clock_logo
127#define LOGO_HEIGHT BMPHEIGHT_clock_logo
128
129/* Parts of larger bitmaps */
130#define COLON 10
131#define DOT_FILLED 11
132#define DOT_EMPTY 12
133#define ICON_PM 13
134#define ICON_AM 14
135#define SEGMENT_AM 11
136#define SEGMENT_PM 12
137#define SLASH 11
138#define PERIOD 12
139
140/* Message names/values */
141#define MESSAGE_LOADING 0
142#define MESSAGE_LOADED 1
143#define MESSAGE_ERRLOAD 2
144#define MESSAGE_SAVING 3
145#define MESSAGE_SAVED 4
146#define MESSAGE_ERRSAVE 5
147
148/* Some macros to simplify drawing et al */
149#define draw_digit( num, x, y )\
150 rb->lcd_bitmap_part( clock_digits, 0, num * DIGIT_HEIGHT, \
151 DIGIT_WIDTH, x, y, DIGIT_WIDTH, DIGIT_HEIGHT )
152#define draw_smalldigit( num, x, y )\
153 rb->lcd_bitmap_part( clock_smalldigits, 0, num * SMALLDIGIT_HEIGHT, \
154 SMALLDIGIT_WIDTH, x, y, SMALLDIGIT_WIDTH, SMALLDIGIT_HEIGHT )
155#define draw_segment( num, x, y )\
156 rb->lcd_bitmap_part( clock_segments, 0, num * DIGIT_HEIGHT, \
157 DIGIT_WIDTH, x, y, DIGIT_WIDTH, DIGIT_HEIGHT )
158#define draw_smallsegment( num, x, y )\
159 rb->lcd_bitmap_part( clock_smallsegments, 0, num * SMALLSEG_HEIGHT, \
160 SMALLSEG_WIDTH, x, y, SMALLSEG_WIDTH, SMALLSEG_HEIGHT )
161#define draw_message( msg, ypos )\
162 rb->lcd_bitmap_part( clock_messages, 0, msg*MESSAGE_HEIGHT, MESSAGE_WIDTH, \
163 0, LCD_HEIGHT-(MESSAGE_HEIGHT*ypos), MESSAGE_WIDTH, MESSAGE_HEIGHT )
164#define DIGIT_XOFS(x) (LCD_WIDTH-x*DIGIT_WIDTH)/2
165#define DIGIT_YOFS(x) (LCD_HEIGHT-x*DIGIT_HEIGHT)/2
166#define SMALLDIGIT_XOFS(x) (LCD_WIDTH-x*SMALLDIGIT_WIDTH)/2
167#define SMALLDIGIT_YOFS(x) (LCD_HEIGHT-x*SMALLDIGIT_HEIGHT)/2
168#define SMALLSEG_XOFS(x) (LCD_WIDTH-x*SMALLSEG_WIDTH)/2
169#define SMALLSEG_YOFS(x) (LCD_HEIGHT-x*SMALLSEG_HEIGHT)/2
170
171/* Keymaps */
172const struct button_mapping* plugin_contexts[]={
173 generic_actions,
174 generic_directions
175};
176
177#define ACTION_COUNTER_TOGGLE PLA_FIRE
178#define ACTION_COUNTER_RESET PLA_FIRE_REPEAT
179#define ACTION_MENU PLA_MENU
180#define ACTION_EXIT PLA_QUIT
181#define ACTION_MODE_NEXT PLA_RIGHT
182#define ACTION_MODE_PREV PLA_LEFT
183
184/************
185 * Prototypes
186 ***********/
187void save_settings(bool interface);
188
189/********************
190 * Misc counter stuff
191 *******************/
192int start_tick = 0;
193int passed_time = 0;
194int counter = 0;
195int displayed_value = 0;
196int count_h, count_m, count_s;
197bool counting = false;
198
199/********************
200 * Everything else...
201 *******************/
202bool idle_poweroff = true; /* poweroff activated or not? */
203bool exit_clock = false; /* when true, the main plugin loop will exit */
204
205static struct plugin_api* rb;
206
207/***********************************************************************
208 * Used for hands to define lengths at a given time, analog + fullscreen
209 **********************************************************************/
210unsigned int xminute[61];
211unsigned int yminute[61];
212unsigned int yhour[61];
213unsigned int xhour[61];
214unsigned int xminute_full[61];
215unsigned int yminute_full[61];
216unsigned int xhour_full[61];
217unsigned int yhour_full[61];
218
219/* settings are saved to this location */
220static const char default_filename[] = "/.rockbox/rocks/.clock_settings";
221
222/*********************************************************
223 * Some arrays/definitions for drawing settings/menu text.
224 ********************************************************/
225#define ANALOG 1
226#define FULLSCREEN 2
227#define DIGITAL 3
228#define PLAIN 4
229#define BINARY 5
230#define CLOCK_MODES 5
231
232#define analog_date 0
233#define analog_secondhand 1
234#define analog_time 2
235#define digital_seconds 0
236#define digital_date 1
237#define digital_blinkcolon 2
238#define digital_format 3
239#define fullscreen_border 0
240#define fullscreen_secondhand 1
241#define binary_mode 0
242#define plain_format 0
243#define plain_seconds 1
244#define plain_date 2
245#define plain_blinkcolon 3
246#define general_counter 0
247#define general_savesetting 1
248#define general_backlight 2
249
250/* Option structs (possible selections per each option) */
251static const struct opt_items noyes_text[] = {
252 { "No", -1 },
253 { "Yes", -1 }
254};
255
256static const struct opt_items backlight_settings_text[] = {
257 { "Always Off", -1 },
258 { "Rockbox setting", -1 },
259 { "Always On", -1 }
260};
261static const struct opt_items idle_poweroff_text[] = {
262 { "Disabled", -1 },
263 { "Enabled", -1 }
264};
265static const struct opt_items counting_direction_text[] = {
266 {"Down", -1},
267 {"Up", -1}
268};
269static const struct opt_items date_format_text[] = {
270 { "No", -1 },
271 { "American format", -1 },
272 { "European format", -1 }
273};
274
275static const struct opt_items analog_time_text[] = {
276 { "No", -1 },
277 { "24-hour Format", -1 },
278 { "12-hour Format", -1 }
279};
280
281static const struct opt_items time_format_text[] = {
282 { "24-hour Format", -1 },
283 { "12-hour Format", -1 }
284};
285
286static const struct opt_items binary_mode_text[] = {
287 { "Numbers", -1 },
288 { "Dots", -1 }
289};
290
291/*****************************************
292 * All settings, saved to default_filename
293 ****************************************/
294struct saved_settings
295{
296 int clock; /* clock mode */
297 int general[4]; /* general settings*/
298 int analog[3];
299 int digital[4];
300 int fullscreen[2];
301 int binary[1];
302 int plain[4];
303} clock_settings;
304
305/************************
306 * Setting default values
307 ***********************/
308void reset_settings(void)
309{
310 clock_settings.clock = 1;
311 clock_settings.general[general_counter] = 1;
312 clock_settings.general[general_savesetting] = 1;
313 clock_settings.general[general_backlight] = 2;
314 clock_settings.analog[analog_date] = 0;
315 clock_settings.analog[analog_secondhand] = true;
316 clock_settings.analog[analog_time] = false;
317 clock_settings.digital[digital_seconds] = 1;
318 clock_settings.digital[digital_date] = 1;
319 clock_settings.digital[digital_blinkcolon] = false;
320 clock_settings.digital[digital_format] = true;
321 clock_settings.fullscreen[fullscreen_border] = true;
322 clock_settings.fullscreen[fullscreen_secondhand] = true;
323 clock_settings.plain[plain_format] = true;
324 clock_settings.plain[plain_seconds] = true;
325 clock_settings.plain[plain_date] = 1;
326 clock_settings.plain[plain_blinkcolon] = false;
327}
328
329/**************************************************************
330 * Simple function to check if we're switching to digital mode,
331 * and if so, set bg/fg colors appropriately.
332 *************************************************************/
333void set_digital_colors(void)
334{
335#ifdef HAVE_LCD_COLOR /* color LCDs.. */
336 if(clock_settings.clock == DIGITAL)
337 {
338 rb->lcd_set_foreground(LCD_WHITE);
339 rb->lcd_set_background(LCD_BLACK);
340 }
341 else
342 {
343 rb->lcd_set_foreground(LCD_BLACK);
344 rb->lcd_set_background(LCD_RGBPACK(180,200,230));
345 }
346#elif LCD_DEPTH >= 2
347 if(clock_settings.clock == DIGITAL)
348 {
349 rb->lcd_set_foreground(LCD_WHITE);
350 rb->lcd_set_background(LCD_BLACK);
351 }
352 else
353 {
354 rb->lcd_set_foreground(LCD_BLACK);
355 rb->lcd_set_background(LCD_WHITE);
356 }
357#endif
358}
359
360/*************************************************************
361 * Simple function to set standard black-on-light blue colors.
362 ************************************************************/
363void set_standard_colors(void)
364{
365#ifdef HAVE_LCD_COLOR /* color LCDs only.. */
366 rb->lcd_set_foreground(LCD_BLACK);
367 rb->lcd_set_background(LCD_RGBPACK(180,200,230));
368#elif LCD_DEPTH >= 2
369 rb->lcd_set_foreground(LCD_BLACK);
370 rb->lcd_set_background(LCD_WHITE);
371#endif
372}
373
374/**************************
375 * Cleanup on plugin return
376 *************************/
377void cleanup(void *parameter)
378{
379 (void)parameter;
380
381 if(clock_settings.general[general_savesetting] == 1)
382 save_settings(true);
383
384 /* restore set backlight timeout */
385 rb->backlight_set_timeout(rb->global_settings->backlight_timeout);
386}
387
388/****************
389 * Shows the logo
390 ***************/
391void show_clock_logo(void)
392{
393#ifdef HAVE_LCD_COLOR
394 rb->lcd_set_foreground(LCD_BLACK);
395 rb->lcd_set_background(LCD_RGBPACK(180,200,230));
396#endif
397
398 rb->lcd_clear_display();;
399
400 rb->lcd_bitmap(clock_logo, 0, 0, LOGO_WIDTH, LOGO_HEIGHT);
401
402 rb->lcd_update();
403}
404
405/********************************
406 * Saves "saved_settings" to disk
407 *******************************/
408void save_settings(bool interface)
409{
410 int fd;
411
412 if(interface)
413 {
414 rb->lcd_clear_display();
415 show_clock_logo();
416
417 draw_message(MESSAGE_SAVING, 1);
418
419 rb->lcd_update();
420 }
421
422 fd = rb->creat(default_filename); /* create the settings file */
423
424 if(fd >= 0) /* file exists, save successful */
425 {
426 rb->write (fd, &clock_settings, sizeof(struct saved_settings));
427 rb->close(fd);
428
429 if(interface)
430 {
431 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
432 rb->lcd_fillrect(0, LCD_HEIGHT-MESSAGE_HEIGHT, LCD_WIDTH, MESSAGE_HEIGHT);
433 rb->lcd_set_drawmode(DRMODE_SOLID);
434 draw_message(MESSAGE_SAVED, 1);
435 }
436 }
437 else /* couldn't save for some reason */
438 {
439 if(interface)
440 {
441 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
442 rb->lcd_fillrect(0, LCD_HEIGHT-MESSAGE_HEIGHT, LCD_WIDTH, MESSAGE_HEIGHT);
443 rb->lcd_set_drawmode(DRMODE_SOLID);
444 draw_message(MESSAGE_ERRSAVE, 1);
445 }
446 }
447
448 if(interface)
449 {
450 rb->lcd_update();
451 rb->sleep(HZ); /* pause a second */
452 }
453}
454
455/**********************************
456 * Loads "saved_settings" from disk
457 *********************************/
458void load_settings(void)
459{
460 /* open the settings file */
461 int fd;
462 fd = rb->open(default_filename, O_RDONLY);
463
464 rb->lcd_clear_display();
465 show_clock_logo();
466
467 draw_message(MESSAGE_LOADING, 1);
468
469 rb->lcd_update();
470
471 if(fd >= 0) /* does file exist? */
472 {
473 if(rb->filesize(fd) == sizeof(struct saved_settings)) /* if so, is it the right size? */
474 {
475 rb->read(fd, &clock_settings, sizeof(struct saved_settings));
476 rb->close(fd);
477
478 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
479 rb->lcd_fillrect(0, LCD_HEIGHT-MESSAGE_HEIGHT, LCD_WIDTH, MESSAGE_HEIGHT);
480 rb->lcd_set_drawmode(DRMODE_SOLID);
481 draw_message(MESSAGE_LOADED, 1);
482 }
483 else /* must be invalid, bail out */
484 {
485 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
486 rb->lcd_fillrect(0, LCD_HEIGHT-MESSAGE_HEIGHT, LCD_WIDTH, MESSAGE_HEIGHT);
487 rb->lcd_set_drawmode(DRMODE_SOLID);
488 draw_message(MESSAGE_ERRLOAD, 1);
489
490 reset_settings();
491 }
492 }
493 else /* must be missing, bail out */
494 {
495 rb->lcd_set_drawmode(DRMODE_SOLID|DRMODE_INVERSEVID);
496 rb->lcd_fillrect(0, LCD_HEIGHT-MESSAGE_HEIGHT, LCD_WIDTH, MESSAGE_HEIGHT);
497 rb->lcd_set_drawmode(DRMODE_SOLID);
498 draw_message(MESSAGE_ERRLOAD, 1);
499
500 reset_settings();
501 }
502
503 rb->lcd_update();
504
505#ifndef SIMULATOR
506 rb->ata_sleep();
507#endif
508
509 rb->sleep(HZ);
510}
511
512void polar_to_cartesian(int a, int r, int* x, int* y)
513{
514 *x = (sin_int(a) * r) >> 14;
515 *y = (sin_int(a-90) * r) >> 14;
516}
517
518void polar_to_cartesian_screen_centered(struct screen * display,
519 int a, int r, int* x, int* y)
520{
521 polar_to_cartesian(a, r, x, y);
522 *x+=display->width/2;
523 *y+=display->height/2;
524}
525
526void angle_to_square(struct screen * display,
527 int square_width, int square_height,
528 int a, int* x, int* y)
529{
530 a = (a+360-90)%360;
531 if(a>45 && a<=135){/* top line */
532 a-=45;
533 *x=square_width-(square_width*2*a)/90;
534 *y=square_height;
535 }else if(a>135 && a<=225){/* left line */
536 a-=135;
537 *x=-square_width;
538 *y=square_height-(square_height*2*a)/90;
539 }else if(a>225 && a<=315){/* bottom line */
540 a-=225;
541 *x=(square_width*2*a)/90-square_width;
542 *y=-square_height;
543 }else if(a>315 || a<=45){/* right line */
544 if(a>315)
545 a-=315;
546 else
547 a+=45;
548 *x=square_width;
549 *y=(square_height*2*a)/90-square_height;
550 }
551 /* recenter */
552 *x+=display->width/2;
553 *y+=display->height/2;
554}
555
556/*******************************
557 * Init clock, set up x/y tables
558 ******************************/
559void init_clock(void)
560{
561 #define ANALOG_VALUES 60
562 #define ANALOG_YCENTER (LCD_HEIGHT/2)
563 #define ANALOG_XCENTER (LCD_WIDTH/2)
564 #define ANALOG_MIN_RADIUS MIN(LCD_HEIGHT/2 -10, LCD_WIDTH/2 -10)
565 #define ANALOG_HR_RADIUS ((2 * ANALOG_MIN_RADIUS)/3)
566
567 #define PI 3.141592
568 int i;
569
570 rb->lcd_setfont(FONT_SYSFIXED); /* universal font */
571
572 load_settings();
573
574 /* set backlight timeout */
575 if(clock_settings.general[general_backlight] == 0)
576 rb->backlight_set_timeout(0);
577 else if(clock_settings.general[general_backlight] == 1)
578 rb->backlight_set_timeout(rb->global_settings->backlight_timeout);
579 else if(clock_settings.general[general_backlight] == 2)
580 rb->backlight_set_timeout(1);
581
582 for(i=0; i<ANALOG_VALUES; i++)
583 {
584 int angle=360 * i / ANALOG_VALUES;
585 polar_to_cartesian_screen_centered(
586 rb->screens[0], angle, ANALOG_MIN_RADIUS,
587 &(xminute[i]), &(yminute[i]));
588 polar_to_cartesian_screen_centered(
589 rb->screens[0], angle, ANALOG_HR_RADIUS,
590 &(xhour[i]), &(yhour[i]));
591
592 /* Fullscreen initialization */
593 angle_to_square(rb->screens[0], LCD_WIDTH/2, LCD_HEIGHT/2, angle,
594 &(xminute_full[i]), &(yminute_full[i]));
595 angle_to_square(rb->screens[0], LCD_WIDTH/3, LCD_HEIGHT/3, angle,
596 &(xhour_full[i]), &(yhour_full[i]));
597 }
598}
599
600/*******************
601 * Analog clock mode
602 ******************/
603void analog_clock(int hour, int minute, int second)
604{
605 if(hour >= 12)
606 hour -= 12;
607
608 int i;
609 int hourpos = (hour*5) + (minute/12);
610
611 /* Crappy fake antialiasing (color LCDs only)!
612 * how this works is we draw a large mid-gray hr/min/sec hand,
613 * then the actual (slightly smaller) hand on top of those.
614 * End result: mid-gray edges to the black hands, smooths them out. */
615#ifdef HAVE_LCD_COLOR
616 rb->lcd_set_foreground(LCD_RGBPACK(100,110,125));
617
618 /* second hand */
619 if(clock_settings.analog[analog_secondhand])
620 {
621 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-2, LCD_WIDTH/2, LCD_HEIGHT/2+2,
622 xminute[second], yminute[second]);
623 xlcd_filltriangle(LCD_WIDTH/2-2, LCD_HEIGHT/2, LCD_WIDTH/2+2, LCD_HEIGHT/2,
624 xminute[second], yminute[second]);
625 }
626
627 /* minute hand */
628 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-4, LCD_WIDTH/2, LCD_HEIGHT/2+4,
629 xminute[minute], yminute[minute]);
630 xlcd_filltriangle(LCD_WIDTH/2-4, LCD_HEIGHT/2, LCD_WIDTH/2+4, LCD_HEIGHT/2,
631 xminute[minute], yminute[minute]);
632
633 /* hour hand */
634 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-4, LCD_WIDTH/2, LCD_HEIGHT/2+4,
635 xhour[hourpos], yhour[hourpos]);
636 xlcd_filltriangle(LCD_WIDTH/2-4, LCD_HEIGHT/2, LCD_WIDTH/2+4, LCD_HEIGHT/2,
637 xhour[hourpos], yhour[hourpos]);
638
639 rb->lcd_set_foreground(LCD_BLACK);
640#endif
641
642 /* second hand, if needed */
643 if(clock_settings.analog[analog_secondhand])
644 {
645 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-1, LCD_WIDTH/2, LCD_HEIGHT/2+1,
646 xminute[second], yminute[second]);
647 xlcd_filltriangle(LCD_WIDTH/2-1, LCD_HEIGHT/2, LCD_WIDTH/2+1, LCD_HEIGHT/2,
648 xminute[second], yminute[second]);
649 }
650
651 /* minute hand */
652 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-HAND_W, LCD_WIDTH/2,
653 LCD_HEIGHT/2+HAND_W, xminute[minute], yminute[minute]);
654 xlcd_filltriangle(LCD_WIDTH/2-HAND_W, LCD_HEIGHT/2, LCD_WIDTH/2
655 +HAND_W, LCD_HEIGHT/2, xminute[minute], yminute[minute]);
656
657 /* hour hand */
658 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-HAND_W, LCD_WIDTH/2,
659 LCD_HEIGHT/2+HAND_W, xhour[hourpos], yhour[hourpos]);
660 xlcd_filltriangle(LCD_WIDTH/2-HAND_W, LCD_HEIGHT/2, LCD_WIDTH/2
661 +HAND_W, LCD_HEIGHT/2, xhour[hourpos], yhour[hourpos]);
662
663 /* Draw the circle */
664 for(i=0; i < 60; i+=5)
665 rb->lcd_fillrect(xminute[i]-1, yminute[i]-1, 3, 3);
666
667 /* Draw the cover over the center */
668 rb->lcd_drawline((LCD_WIDTH/2)-1, (LCD_HEIGHT/2)+3,
669 (LCD_WIDTH/2)+1, (LCD_HEIGHT/2)+3);
670 rb->lcd_drawline((LCD_WIDTH/2)-3, (LCD_HEIGHT/2)+2,
671 (LCD_WIDTH/2)+3, (LCD_HEIGHT/2)+2);
672 rb->lcd_drawline((LCD_WIDTH/2)-4, (LCD_HEIGHT/2)+1,
673 (LCD_WIDTH/2)+4, (LCD_HEIGHT/2)+1);
674 rb->lcd_drawline((LCD_WIDTH/2)-4, LCD_HEIGHT/2,
675 (LCD_WIDTH/2)+4, LCD_HEIGHT/2);
676 rb->lcd_drawline((LCD_WIDTH/2)-4, (LCD_HEIGHT/2)-1,
677 (LCD_WIDTH/2)+4, (LCD_HEIGHT/2)-1);
678 rb->lcd_drawline((LCD_WIDTH/2)-3, (LCD_HEIGHT/2)-2,
679 (LCD_WIDTH/2)+3, (LCD_HEIGHT/2)-2);
680 rb->lcd_drawline((LCD_WIDTH/2)-1, (LCD_HEIGHT/2)-3,
681 (LCD_WIDTH/2)+1, (LCD_HEIGHT/2)-3);
682}
683
684/********************
685 * Digital clock mode
686 *******************/
687void digital_clock(int hour, int minute, int second, bool colon)
688{
689 int x_ofs=0;
690
691 /* this basically detects if we draw an AM or PM bitmap.
692 * if we don't, we center the hh:mm display. */
693 if(!clock_settings.digital[digital_format])
694 x_ofs=DIGIT_WIDTH/2;
695
696#if LCD_DEPTH == 1
697 rb->lcd_fillrect(0,0,112,64);
698#endif
699
700 if(clock_settings.digital[digital_format])
701 {
702 /* draw the AM or PM bitmap */
703 if(hour<12)
704 draw_segment(SEGMENT_AM,DIGIT_XOFS(6)+DIGIT_WIDTH*5, 0);
705 else
706 draw_segment(SEGMENT_PM,DIGIT_XOFS(6)+DIGIT_WIDTH*5, 0);
707
708 /* and then readjust the hour to 12-hour format
709 * ( 13:00+ -> 1:00+ ) */
710 if(hour>12)
711 hour -= 12;
712 }
713
714 /* hour */
715 draw_segment(hour/10, DIGIT_XOFS(6)+x_ofs, 0);
716 draw_segment(hour%10, DIGIT_XOFS(6)+DIGIT_WIDTH+x_ofs, 0);
717
718 /* colon */
719 if(colon)
720 draw_segment(COLON, DIGIT_XOFS(6)+2*DIGIT_WIDTH+x_ofs, 0);
721
722 /* minutes */
723 draw_segment(minute/10, DIGIT_XOFS(6)+3*DIGIT_WIDTH+x_ofs, 0);
724 draw_segment(minute%10, DIGIT_XOFS(6)+4*DIGIT_WIDTH+x_ofs, 0);
725
726 if(clock_settings.digital[digital_seconds])
727 {
728 draw_segment(second/10, DIGIT_XOFS(2), DIGIT_HEIGHT);
729 draw_segment(second%10, DIGIT_XOFS(2)+DIGIT_WIDTH, DIGIT_HEIGHT);
730 }
731}
732
733/***********************
734 * Fullscreen clock mode
735 **********************/
736void fullscreen_clock(int hour, int minute, int second)
737{
738 if(hour >= 12)
739 hour -= 12;
740
741 int i;
742 int hourpos = (hour*5) + (minute/12);
743
744 /* Crappy fake antialiasing (color LCDs only)!
745 * how this works is we draw a large mid-gray hr/min/sec hand,
746 * then the actual (slightly smaller) hand on top of those.
747 * End result: mid-gray edges to the black hands, smooths them out. */
748#ifdef HAVE_LCD_COLOR
749 rb->lcd_set_foreground(LCD_RGBPACK(100,110,125));
750
751 /* second hand */
752 if(clock_settings.analog[analog_secondhand])
753 {
754 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-2, LCD_WIDTH/2, LCD_HEIGHT/2+2,
755 xminute_full[second], yminute_full[second]);
756 xlcd_filltriangle(LCD_WIDTH/2-2, LCD_HEIGHT/2, LCD_WIDTH/2+2, LCD_HEIGHT/2,
757 xminute_full[second], yminute_full[second]);
758 }
759
760 /* minute hand */
761 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-4, LCD_WIDTH/2, LCD_HEIGHT/2+4,
762 xminute_full[minute], yminute_full[minute]);
763 xlcd_filltriangle(LCD_WIDTH/2-4, LCD_HEIGHT/2, LCD_WIDTH/2+4, LCD_HEIGHT/2,
764 xminute_full[minute], yminute_full[minute]);
765
766 /* hour hand */
767 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-4, LCD_WIDTH/2, LCD_HEIGHT/2+4,
768 xhour_full[hourpos], yhour_full[hourpos]);
769 xlcd_filltriangle(LCD_WIDTH/2-4, LCD_HEIGHT/2, LCD_WIDTH/2+4, LCD_HEIGHT/2,
770 xhour_full[hourpos], yhour_full[hourpos]);
771
772 rb->lcd_set_foreground(LCD_BLACK);
773#endif
774
775 /* second hand, if needed */
776 if(clock_settings.analog[analog_secondhand])
777 {
778 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-1, LCD_WIDTH/2, LCD_HEIGHT/2+1,
779 xminute_full[second], yminute_full[second]);
780 xlcd_filltriangle(LCD_WIDTH/2-1, LCD_HEIGHT/2, LCD_WIDTH/2+1, LCD_HEIGHT/2,
781 xminute_full[second], yminute_full[second]);
782 }
783
784 /* minute hand */
785 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-3, LCD_WIDTH/2, LCD_HEIGHT/2+3,
786 xminute_full[minute], yminute_full[minute]);
787 xlcd_filltriangle(LCD_WIDTH/2-3, LCD_HEIGHT/2, LCD_WIDTH/2+3, LCD_HEIGHT/2,
788 xminute_full[minute], yminute_full[minute]);
789
790 /* hour hand */
791 xlcd_filltriangle(LCD_WIDTH/2, LCD_HEIGHT/2-3, LCD_WIDTH/2, LCD_HEIGHT/2+3,
792 xhour_full[hourpos], yhour_full[hourpos]);
793 xlcd_filltriangle(LCD_WIDTH/2-3, LCD_HEIGHT/2, LCD_WIDTH/2+3, LCD_HEIGHT/2,
794 xhour_full[hourpos], yhour_full[hourpos]);
795
796 /* Draw the circle */
797 for(i=0; i < 60; i+=5)
798 rb->lcd_fillrect(xminute_full[i]-1, yminute_full[i]-1, 3, 3);
799
800 /* Draw the cover over the center */
801 rb->lcd_drawline((LCD_WIDTH/2)-1, (LCD_HEIGHT/2)+3,
802 (LCD_WIDTH/2)+1, (LCD_HEIGHT/2)+3);
803 rb->lcd_drawline((LCD_WIDTH/2)-3, (LCD_HEIGHT/2)+2,
804 (LCD_WIDTH/2)+3, (LCD_HEIGHT/2)+2);
805 rb->lcd_drawline((LCD_WIDTH/2)-4, (LCD_HEIGHT/2)+1,
806 (LCD_WIDTH/2)+4, (LCD_HEIGHT/2)+1);
807 rb->lcd_drawline((LCD_WIDTH/2)-4, LCD_HEIGHT/2,
808 (LCD_WIDTH/2)+4, LCD_HEIGHT/2);
809 rb->lcd_drawline((LCD_WIDTH/2)-4, (LCD_HEIGHT/2)-1,
810 (LCD_WIDTH/2)+4, (LCD_HEIGHT/2)-1);
811 rb->lcd_drawline((LCD_WIDTH/2)-3, (LCD_HEIGHT/2)-2,
812 (LCD_WIDTH/2)+3, (LCD_HEIGHT/2)-2);
813 rb->lcd_drawline((LCD_WIDTH/2)-1, (LCD_HEIGHT/2)-3,
814 (LCD_WIDTH/2)+1, (LCD_HEIGHT/2)-3);
815}
816
817/*******************
818 * Binary clock mode
819 ******************/
820void binary_clock(int hour, int minute, int second)
821{
822 int i, xpos=0;
823 int mode_var[3]; /* pointers to h, m, s arguments */
824 int mode; /* 0 = hour, 1 = minute, 2 = second */
825
826 mode_var[0] = hour;
827 mode_var[1] = minute;
828 mode_var[2] = second;
829
830 for(mode = 0; mode < 3; mode++)
831 {
832 for(i = 32; i > 0; i /= 2)
833 {
834 if(mode_var[mode] >= i)
835 {
836 if(clock_settings.binary[binary_mode])
837 draw_digit(DOT_FILLED, xpos*DIGIT_WIDTH+DIGIT_XOFS(6), DIGIT_HEIGHT*mode+DIGIT_YOFS(3));
838 else
839 draw_digit(1, xpos*DIGIT_WIDTH+DIGIT_XOFS(6), DIGIT_HEIGHT*mode+DIGIT_YOFS(3));
840 mode_var[mode] -= i;
841 }
842 else
843 {
844 if(clock_settings.binary[binary_mode])
845 draw_digit(DOT_EMPTY, xpos*DIGIT_WIDTH+DIGIT_XOFS(6), DIGIT_HEIGHT*mode+DIGIT_YOFS(3));
846 else
847 draw_digit(0, xpos*DIGIT_WIDTH+DIGIT_XOFS(6), DIGIT_HEIGHT*mode+DIGIT_YOFS(3));
848 }
849
850 xpos++;
851 }
852
853 xpos=0; /* reset the x-pos for next mode */
854 }
855}
856
857/******************
858 * Plain clock mode
859 *****************/
860void plain_clock(int hour, int minute, int second, bool colon)
861{
862
863 int x_ofs=0;
864
865 /* this basically detects if we draw an AM or PM bitmap.
866 * if we don't, we center the hh:mm display. */
867 if(!clock_settings.plain[plain_format])
868 x_ofs=DIGIT_WIDTH/2;
869
870 if(clock_settings.plain[plain_format])
871 {
872 /* draw the AM or PM bitmap */
873 if(hour<12)
874 draw_digit(ICON_AM, DIGIT_XOFS(6)+(DIGIT_WIDTH*5)+x_ofs, 0);
875 else
876 draw_digit(ICON_PM, DIGIT_XOFS(6)+(DIGIT_WIDTH*5)+x_ofs, 0);
877
878 /* and then readjust the hour to 12-hour format
879 * ( 13:00+ -> 1:00+ ) */
880 if(hour>12)
881 hour -= 12;
882 }
883
884
885 draw_digit(hour/10, DIGIT_XOFS(6)+(DIGIT_WIDTH*0)+x_ofs, 0);
886 draw_digit(hour%10, DIGIT_XOFS(6)+(DIGIT_WIDTH*1)+x_ofs, 0);
887
888 if(colon)
889 draw_digit(COLON, DIGIT_XOFS(6)+(DIGIT_WIDTH*2)+x_ofs, 0);
890
891 draw_digit(minute/10, DIGIT_XOFS(6)+(DIGIT_WIDTH*3)+x_ofs, 0);
892 draw_digit(minute%10, DIGIT_XOFS(6)+(DIGIT_WIDTH*4)+x_ofs, 0);
893
894 if(clock_settings.plain[plain_seconds])
895 {
896 draw_digit(second/10, DIGIT_XOFS(2), DIGIT_HEIGHT);
897 draw_digit(second%10, DIGIT_XOFS(2)+(DIGIT_WIDTH), DIGIT_HEIGHT);
898 }
899}
900
901
902
903/****************************************
904 * Draws the extras, IE border, digits...
905 ***************************************/
906void draw_extras(int year, int day, int month, int hour, int minute, int second)
907{
908 int i;
909
910 struct tm* current_time = rb->get_time();
911
912 char moday[8];
913 char dateyr[6];
914 char tmhrmin[7];
915 char tmsec[3];
916
917 /* american date readout */
918 if(clock_settings.analog[analog_date] == 1)
919 rb->snprintf(moday, sizeof(moday), "%02d/%02d", month, day);
920 else
921 rb->snprintf(moday, sizeof(moday), "%02d.%02d", day, month);
922 rb->snprintf(dateyr, sizeof(dateyr), "%d", year);
923 rb->snprintf(tmhrmin, sizeof(tmhrmin), "%02d:%02d", hour, minute);
924 rb->snprintf(tmsec, sizeof(tmsec), "%02d", second);
925
926 /* Analog Extras */
927 if(clock_settings.clock == ANALOG)
928 {
929 if(clock_settings.analog[analog_time] != 0) /* Digital readout */
930 {
931 draw_smalldigit(hour/10, SMALLDIGIT_WIDTH*0, 0);
932 draw_smalldigit(hour%10, SMALLDIGIT_WIDTH*1, 0);
933 draw_smalldigit(COLON, SMALLDIGIT_WIDTH*2, 0);
934 draw_smalldigit(minute/10, SMALLDIGIT_WIDTH*3, 0);
935 draw_smalldigit(minute%10, SMALLDIGIT_WIDTH*4, 0);
936
937 draw_smalldigit(second/10, SMALLDIGIT_WIDTH*1.5, SMALLDIGIT_HEIGHT);
938 draw_smalldigit(second%10, SMALLDIGIT_WIDTH*2.5, SMALLDIGIT_HEIGHT);
939
940 /* AM/PM indicator */
941 if(clock_settings.analog[analog_time] == 2)
942 {
943 if(current_time->tm_hour > 12) /* PM */
944 draw_digit(ICON_PM, LCD_WIDTH-DIGIT_WIDTH, DIGIT_HEIGHT/2-DIGIT_HEIGHT);
945 else /* AM */
946 draw_digit(ICON_AM, LCD_WIDTH-DIGIT_WIDTH, DIGIT_HEIGHT/2-DIGIT_HEIGHT);
947 }
948 }
949 if(clock_settings.analog[analog_date] != 0) /* Date readout */
950 {
951 if(clock_settings.analog[analog_date] == 1)
952 {
953 draw_smalldigit(month/10, SMALLDIGIT_WIDTH*0,
954 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
955 draw_smalldigit(month%10, SMALLDIGIT_WIDTH*1,
956 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
957 draw_smalldigit(SLASH, SMALLDIGIT_WIDTH*2,
958 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
959 draw_smalldigit(day/10, SMALLDIGIT_WIDTH*3,
960 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
961 draw_smalldigit(day%10, SMALLDIGIT_WIDTH*4,
962 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
963 draw_smalldigit(year/1000, SMALLDIGIT_WIDTH*0.5,
964 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
965 draw_smalldigit(year%1000/100, SMALLDIGIT_WIDTH*1.5,
966 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
967 draw_smalldigit(year%100/10, SMALLDIGIT_WIDTH*2.5,
968 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
969 draw_smalldigit(year%10, SMALLDIGIT_WIDTH*3.5,
970 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
971 }
972 else if(clock_settings.analog[analog_date] == 2)
973 {
974
975 draw_smalldigit(day/10, SMALLDIGIT_WIDTH*0,
976 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
977 draw_smalldigit(day%10, SMALLDIGIT_WIDTH*1,
978 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
979 draw_smalldigit(PERIOD, SMALLDIGIT_WIDTH*2,
980 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
981 draw_smalldigit(month/10, SMALLDIGIT_WIDTH*3,
982 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
983 draw_smalldigit(month%10, SMALLDIGIT_WIDTH*4,
984 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
985 draw_smalldigit(year/1000, SMALLDIGIT_WIDTH*0.5,
986 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
987 draw_smalldigit(year%1000/100, SMALLDIGIT_WIDTH*1.5,
988 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
989 draw_smalldigit(year%100/10, SMALLDIGIT_WIDTH*2.5,
990 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
991 draw_smalldigit(year%10, SMALLDIGIT_WIDTH*3.5,
992 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
993 }
994 }
995 }
996 else if(clock_settings.clock == DIGITAL)
997 {
998 /* Date readout */
999 if(clock_settings.digital[digital_date] == 1) /* american mode */
1000 {
1001 draw_smallsegment(month/10, SMALLSEG_WIDTH*0+SMALLSEG_XOFS(10),
1002 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1003 draw_smallsegment(month%10, SMALLSEG_WIDTH*1+SMALLSEG_XOFS(10),
1004 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1005 draw_smallsegment(SLASH, SMALLSEG_WIDTH*2+SMALLSEG_XOFS(10),
1006 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1007 draw_smallsegment(day/10, SMALLSEG_WIDTH*3+SMALLSEG_XOFS(10),
1008 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1009 draw_smallsegment(day%10, SMALLSEG_WIDTH*4+SMALLSEG_XOFS(10),
1010 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1011 draw_smallsegment(SLASH, SMALLSEG_WIDTH*5+SMALLSEG_XOFS(10),
1012 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1013 draw_smallsegment(year/1000, SMALLSEG_WIDTH*6+SMALLSEG_XOFS(10),
1014 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1015 draw_smallsegment(year%1000/100, SMALLSEG_WIDTH*7+SMALLSEG_XOFS(10),
1016 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1017 draw_smallsegment(year%100/10, SMALLSEG_WIDTH*8+SMALLSEG_XOFS(10),
1018 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1019 draw_smallsegment(year%10, SMALLSEG_WIDTH*9+SMALLSEG_XOFS(10),
1020 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1021 }
1022 else if(clock_settings.digital[digital_date] == 2) /* european mode */
1023 {
1024 draw_smallsegment(day/10, SMALLSEG_WIDTH*0+SMALLSEG_XOFS(10),
1025 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1026 draw_smallsegment(day%10, SMALLSEG_WIDTH*1+SMALLSEG_XOFS(10),
1027 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1028 draw_smallsegment(PERIOD, SMALLSEG_WIDTH*2+SMALLSEG_XOFS(10),
1029 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1030 draw_smallsegment(month/10, SMALLSEG_WIDTH*3+SMALLSEG_XOFS(10),
1031 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1032 draw_smallsegment(month%10, SMALLSEG_WIDTH*4+SMALLSEG_XOFS(10),
1033 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1034 draw_smallsegment(PERIOD, SMALLSEG_WIDTH*5+SMALLSEG_XOFS(10),
1035 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1036 draw_smallsegment(year/1000, SMALLSEG_WIDTH*6+SMALLSEG_XOFS(10),
1037 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1038 draw_smallsegment(year%1000/100, SMALLSEG_WIDTH*7+SMALLSEG_XOFS(10),
1039 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1040 draw_smallsegment(year%100/10, SMALLSEG_WIDTH*8+SMALLSEG_XOFS(10),
1041 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1042 draw_smallsegment(year%10, SMALLSEG_WIDTH*9+SMALLSEG_XOFS(10),
1043 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET*2);
1044 }
1045 }
1046 else if(clock_settings.clock == FULLSCREEN) /* Fullscreen mode */
1047 {
1048 if(clock_settings.fullscreen[fullscreen_border])
1049 {
1050 for(i=0; i < 60; i+=5) /* Draw the circle */
1051 rb->lcd_fillrect(xminute_full[i]-1, yminute_full[i]-1, 3, 3);
1052 }
1053 }
1054 else if(clock_settings.clock == PLAIN) /* Plain mode */
1055 {
1056 /* Date readout */
1057 if(clock_settings.plain[plain_date] == 1) /* american mode */
1058 {
1059 draw_smalldigit(month/10, SMALLDIGIT_WIDTH*0+SMALLDIGIT_XOFS(10),
1060 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1061 draw_smalldigit(month%10, SMALLDIGIT_WIDTH*1+SMALLDIGIT_XOFS(10),
1062 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1063 draw_smalldigit(SLASH, SMALLDIGIT_WIDTH*2+SMALLDIGIT_XOFS(10),
1064 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1065 draw_smalldigit(day/10, SMALLDIGIT_WIDTH*3+SMALLDIGIT_XOFS(10),
1066 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1067 draw_smalldigit(day%10, SMALLDIGIT_WIDTH*4+SMALLDIGIT_XOFS(10),
1068 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1069 draw_smalldigit(SLASH, SMALLDIGIT_WIDTH*5+SMALLDIGIT_XOFS(10),
1070 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1071 draw_smalldigit(year/1000, SMALLDIGIT_WIDTH*6+SMALLDIGIT_XOFS(10),
1072 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1073 draw_smalldigit(year%1000/100, SMALLDIGIT_WIDTH*7+SMALLDIGIT_XOFS(10),
1074 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1075 draw_smalldigit(year%100/10, SMALLDIGIT_WIDTH*8+SMALLDIGIT_XOFS(10),
1076 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1077 draw_smalldigit(year%10, SMALLDIGIT_WIDTH*9+SMALLDIGIT_XOFS(10),
1078 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1079 }
1080 else if(clock_settings.plain[plain_date] == 2) /* european mode */
1081 {
1082 draw_smalldigit(day/10, SMALLDIGIT_WIDTH*0+SMALLDIGIT_XOFS(10),
1083 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1084 draw_smalldigit(day%10, SMALLDIGIT_WIDTH*1+SMALLDIGIT_XOFS(10),
1085 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1086 draw_smalldigit(PERIOD, SMALLDIGIT_WIDTH*2+SMALLDIGIT_XOFS(10),
1087 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1088 draw_smalldigit(month/10, SMALLDIGIT_WIDTH*3+SMALLDIGIT_XOFS(10),
1089 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1090 draw_smalldigit(month%10, SMALLDIGIT_WIDTH*4+SMALLDIGIT_XOFS(10),
1091 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1092 draw_smalldigit(PERIOD, SMALLDIGIT_WIDTH*5+SMALLDIGIT_XOFS(10),
1093 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1094 draw_smalldigit(year/1000, SMALLDIGIT_WIDTH*6+SMALLDIGIT_XOFS(10),
1095 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1096 draw_smalldigit(year%1000/100, SMALLDIGIT_WIDTH*7+SMALLDIGIT_XOFS(10),
1097 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1098 draw_smalldigit(year%100/10, SMALLDIGIT_WIDTH*8+SMALLDIGIT_XOFS(10),
1099 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1100 draw_smalldigit(year%10, SMALLDIGIT_WIDTH*9+SMALLDIGIT_XOFS(10),
1101 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET*2);
1102 }
1103 }
1104}
1105
1106/*********************
1107 * Display the counter
1108 ********************/
1109void show_counter(void)
1110{
1111
1112 /* increment counter */
1113 if(counting)
1114 passed_time = *rb->current_tick - start_tick;
1115 else
1116 passed_time = 0;
1117
1118 displayed_value = counter + passed_time;
1119 displayed_value = displayed_value / HZ;
1120
1121 /* these are the REAL displayed values */
1122 count_s = displayed_value % 60;
1123 count_m = displayed_value % 3600 / 60;
1124 count_h = displayed_value / 3600;
1125
1126 if(clock_settings.general[general_counter])
1127 {
1128 if(clock_settings.clock == ANALOG)
1129 {
1130 draw_smalldigit(count_h/10, LCD_WIDTH-SMALLDIGIT_WIDTH*5,
1131 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
1132 draw_smalldigit(count_h%10, LCD_WIDTH-SMALLDIGIT_WIDTH*4,
1133 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
1134 draw_smalldigit(COLON, LCD_WIDTH-SMALLDIGIT_WIDTH*3,
1135 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
1136 draw_smalldigit(count_m/10, LCD_WIDTH-SMALLDIGIT_WIDTH*2,
1137 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
1138 draw_smalldigit(count_m%10, LCD_WIDTH-SMALLDIGIT_WIDTH,
1139 LCD_HEIGHT-SMALLDIGIT_HEIGHT*2);
1140 draw_smalldigit(count_s/10, LCD_WIDTH-SMALLDIGIT_WIDTH*3.5,
1141 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
1142 draw_smalldigit(count_s%10, LCD_WIDTH-SMALLDIGIT_WIDTH*2.5,
1143 LCD_HEIGHT-SMALLDIGIT_HEIGHT);
1144 }
1145 else if(clock_settings.clock == DIGITAL)
1146 {
1147 draw_smallsegment(count_h/10, SMALLSEG_WIDTH*0+SMALLSEG_XOFS(8),
1148 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1149 draw_smallsegment(count_h%10, SMALLSEG_WIDTH*1+SMALLSEG_XOFS(8),
1150 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1151 draw_smallsegment(COLON, SMALLSEG_WIDTH*2+SMALLSEG_XOFS(8),
1152 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1153 draw_smallsegment(count_m/10, SMALLSEG_WIDTH*3+SMALLSEG_XOFS(8),
1154 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1155 draw_smallsegment(count_m%10, SMALLSEG_WIDTH*4+SMALLSEG_XOFS(8),
1156 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1157 draw_smallsegment(COLON, SMALLSEG_WIDTH*5+SMALLSEG_XOFS(8),
1158 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1159 draw_smallsegment(count_s/10, SMALLSEG_WIDTH*6+SMALLSEG_XOFS(8),
1160 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1161 draw_smallsegment(count_s%10, SMALLSEG_WIDTH*7+SMALLSEG_XOFS(8),
1162 LCD_HEIGHT-SMALLSEG_HEIGHT*LCD_OFFSET);
1163 }
1164 else if(clock_settings.clock == FULLSCREEN)
1165 {
1166
1167 draw_smalldigit(count_h/10, SMALLDIGIT_WIDTH*0+SMALLDIGIT_XOFS(8),
1168 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1169 draw_smalldigit(count_h%10, SMALLDIGIT_WIDTH*1+SMALLDIGIT_XOFS(8),
1170 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1171 draw_smalldigit(COLON, SMALLDIGIT_WIDTH*2+SMALLDIGIT_XOFS(8),
1172 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1173 draw_smalldigit(count_m/10, SMALLDIGIT_WIDTH*3+SMALLDIGIT_XOFS(8),
1174 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1175 draw_smalldigit(count_m%10, SMALLDIGIT_WIDTH*4+SMALLDIGIT_XOFS(8),
1176 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1177 draw_smalldigit(COLON, SMALLDIGIT_WIDTH*5+SMALLDIGIT_XOFS(8),
1178 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1179 draw_smalldigit(count_s/10, SMALLDIGIT_WIDTH*6+SMALLDIGIT_XOFS(8),
1180 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1181 draw_smalldigit(count_s%10, SMALLDIGIT_WIDTH*7+SMALLDIGIT_XOFS(8),
1182 LCD_HEIGHT-SMALLDIGIT_HEIGHT*1.5);
1183 }
1184 else if(clock_settings.clock == PLAIN)
1185 {
1186 draw_smalldigit(count_h/10, SMALLDIGIT_WIDTH*0+SMALLDIGIT_XOFS(8),
1187 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1188 draw_smalldigit(count_h%10, SMALLDIGIT_WIDTH*1+SMALLDIGIT_XOFS(8),
1189 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1190 draw_smalldigit(COLON, SMALLDIGIT_WIDTH*2+SMALLDIGIT_XOFS(8),
1191 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1192 draw_smalldigit(count_m/10, SMALLDIGIT_WIDTH*3+SMALLDIGIT_XOFS(8),
1193 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1194 draw_smalldigit(count_m%10, SMALLDIGIT_WIDTH*4+SMALLDIGIT_XOFS(8),
1195 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1196 draw_smalldigit(COLON, SMALLDIGIT_WIDTH*5+SMALLDIGIT_XOFS(8),
1197 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1198 draw_smalldigit(count_s/10, SMALLDIGIT_WIDTH*6+SMALLDIGIT_XOFS(8),
1199 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1200 draw_smalldigit(count_s%10, SMALLDIGIT_WIDTH*7+SMALLDIGIT_XOFS(8),
1201 LCD_HEIGHT-SMALLDIGIT_HEIGHT*LCD_OFFSET);
1202 }
1203 }
1204}
1205
1206/* Menus */
1207
1208/***************
1209 * Select a mode
1210 **************/
1211bool menu_mode_selector(void)
1212{
1213 int selection=clock_settings.clock-1;
1214
1215 set_standard_colors();
1216
1217 MENUITEM_STRINGLIST(menu,"Mode Selector",NULL, "Analog", "Full-screen",
1218 "Digital/LCD","Plain","Binary");
1219
1220 /* check for this, so if the user exits the menu without
1221 * making a selection, it won't change to some weird value. */
1222 if(rb->do_menu(&menu, &selection) >=0){
1223 clock_settings.clock = selection+1;
1224 return(true);
1225 }
1226 return(false);
1227}
1228
1229/**********************
1230 * Analog settings menu
1231 *********************/
1232void menu_analog_settings(void)
1233{
1234 int selection=0, result=0;
1235
1236 MENUITEM_STRINGLIST(menu,"Analog Mode Settings",NULL,"Show Date",
1237 "Show Second Hand","Show Time Readout");
1238
1239 while(result>=0)
1240 {
1241 result=rb->do_menu(&menu, &selection);
1242 switch(result)
1243 {
1244 case 0:
1245 rb->set_option("Show Date", &clock_settings.analog[analog_date],
1246 INT, date_format_text, 3, NULL);
1247 break;
1248 case 1:
1249 rb->set_option("Show Second Hand", &clock_settings.analog[analog_secondhand],
1250 INT, noyes_text, 2, NULL);
1251 break;
1252 case 2:
1253 rb->set_option("Show Time", &clock_settings.analog[analog_time],
1254 INT, analog_time_text, 3, NULL);
1255 break;
1256 }
1257 }
1258}
1259
1260/***********************
1261 * Digital settings menu
1262 **********************/
1263void menu_digital_settings(void)
1264{
1265 int selection=0, result=0;
1266
1267 MENUITEM_STRINGLIST(menu,"Digital/LCD Mode Settings",NULL,"Show Date",
1268 "Show Seconds","Blinking Colon","Time Format");
1269
1270 while(result>=0)
1271 {
1272 result=rb->do_menu(&menu, &selection);
1273 switch(result)
1274 {
1275 case 0:
1276 rb->set_option("Show Date", &clock_settings.digital[digital_date],
1277 INT, date_format_text, 3, NULL);
1278 break;
1279 case 1:
1280 rb->set_option("Show Seconds", &clock_settings.digital[digital_seconds],
1281 INT, noyes_text, 2, NULL);
1282 break;
1283 case 2:
1284 rb->set_option("Blinking Colon", &clock_settings.digital[digital_blinkcolon],
1285 INT, noyes_text, 2, NULL);
1286 break;
1287 case 3:
1288 rb->set_option("Time Format", &clock_settings.digital[digital_format],
1289 INT, time_format_text, 2, NULL);
1290 break;
1291 }
1292 }
1293}
1294
1295/**************************
1296 * Fullscreen settings menu
1297 *************************/
1298void menu_fullscreen_settings(void)
1299{
1300 int selection=0, result=0;
1301
1302 MENUITEM_STRINGLIST(menu,"Fullscreen Mode Settings",NULL,
1303 "Show Border","Show Second Hand");
1304
1305 while(result>=0)
1306 {
1307 result=rb->do_menu(&menu, &selection);
1308 switch(result)
1309 {
1310 case 0:
1311 rb->set_option("Show Border", &clock_settings.fullscreen[fullscreen_border],
1312 INT, noyes_text, 2, NULL);
1313 break;
1314 case 1:
1315 rb->set_option("Show Second Hand", &clock_settings.fullscreen[fullscreen_secondhand],
1316 INT, noyes_text, 2, NULL);
1317 break;
1318 }
1319 }
1320}
1321
1322/**********************
1323 * Binary settings menu
1324 *********************/
1325void menu_binary_settings(void)
1326{
1327 int selection=0, result=0;
1328
1329 MENUITEM_STRINGLIST(menu,"Binary Mode Settings",NULL,"Display Mode");
1330
1331 while(result>=0)
1332 {
1333 result=rb->do_menu(&menu, &selection);
1334 switch(result)
1335 {
1336 case 0:
1337 rb->set_option("Display Mode", &clock_settings.binary[binary_mode],
1338 INT, binary_mode_text, 2, NULL);
1339 }
1340
1341 }
1342}
1343
1344/*********************
1345 * Plain settings menu
1346 ********************/
1347void menu_plain_settings(void)
1348{
1349 int selection=0, result=0;
1350
1351 MENUITEM_STRINGLIST(menu,"Plain Mode Settings",NULL,"Show Date",
1352 "Show Seconds","Blinking Colon","Time Format");
1353
1354 while(result>=0)
1355 {
1356 result=rb->do_menu(&menu, &selection);
1357 switch(result)
1358 {
1359 case 0:
1360 rb->set_option("Show Date", &clock_settings.plain[plain_date],
1361 INT, date_format_text, 3, NULL);
1362 break;
1363 case 1:
1364 rb->set_option("Show Seconds", &clock_settings.plain[plain_seconds],
1365 INT, noyes_text, 2, NULL);
1366 break;
1367 case 2:
1368 rb->set_option("Blinking Colon", &clock_settings.plain[plain_blinkcolon],
1369 INT, noyes_text, 2, NULL);
1370 break;
1371 case 3:
1372 rb->set_option("Time Format", &clock_settings.plain[plain_format],
1373 INT, time_format_text, 2, NULL);
1374 break;
1375 }
1376 }
1377}
1378
1379/***********************************************************
1380 * Confirm resetting of settings, used in general_settings()
1381 **********************************************************/
1382void confirm_reset(void)
1383{
1384 int result=0;
1385
1386 rb->set_option("Reset all settings?", &result, INT, noyes_text, 2, NULL);
1387
1388 if(result == 1) /* reset! */
1389 {
1390 reset_settings();
1391 rb->splash(HZ, "Settings reset!");
1392 }
1393 else
1394 rb->splash(HZ, "Settings NOT reset.");
1395}
1396
1397/************************************
1398 * General settings. Reset, save, etc
1399 ***********************************/
1400void menu_general_settings(void)
1401{
1402 int selection=0, result=0;
1403
1404 MENUITEM_STRINGLIST(menu,"General Settings",NULL,"Reset Settings",
1405 "Save Settings Now","Save On Exit","Show Counter",
1406 "Backlight Settings","Idle Poweroff (temporary)");
1407
1408 while(result>=0)
1409 {
1410 result=rb->do_menu(&menu, &selection);
1411 switch(result)
1412 {
1413 case 0:
1414 confirm_reset();
1415 break;
1416
1417 case 1:
1418 save_settings(false);
1419 rb->splash(HZ, "Settings saved");
1420 break;
1421
1422 case 2:
1423 rb->set_option("Save On Exit", &clock_settings.general[general_savesetting],
1424 INT, noyes_text, 2, NULL);
1425
1426 /* if we no longer save on exit, we better save now to remember that */
1427 if(clock_settings.general[general_savesetting] == 0)
1428 save_settings(false);
1429 break;
1430
1431 case 3:
1432 rb->set_option("Show Counter", &clock_settings.general[general_counter],
1433 INT, noyes_text, 2, NULL);
1434 break;
1435
1436 case 4:
1437 rb->set_option("Backlight Settings", &clock_settings.general[general_backlight],
1438 INT, backlight_settings_text, 3, NULL);
1439 break;
1440
1441 case 5:
1442 rb->set_option("Idle Poweroff (temporary)", &idle_poweroff,
1443 BOOL, idle_poweroff_text, 2, NULL);
1444 break;
1445 }
1446
1447 }
1448}
1449
1450/***********
1451 * Main menu
1452 **********/
1453void main_menu(void)
1454{
1455 int selection=0;
1456 bool done = false;
1457
1458 set_standard_colors();
1459
1460 MENUITEM_STRINGLIST(menu,"Clock Menu",NULL,"View Clock","Mode Selector",
1461 "Mode Settings","General Settings","Quit");
1462
1463 while(!done)
1464 {
1465 switch(rb->do_menu(&menu, &selection))
1466 {
1467 case 0:
1468 rb->lcd_setfont(FONT_SYSFIXED);
1469 done = true;
1470 break;
1471
1472 case 1:
1473 done=menu_mode_selector();
1474 break;
1475
1476 case 2:
1477 switch(clock_settings.clock)
1478 {
1479 case ANALOG: menu_analog_settings();break;
1480 case DIGITAL: menu_digital_settings();break;
1481 case FULLSCREEN: menu_fullscreen_settings();break;
1482 case BINARY: menu_binary_settings();break;
1483 case PLAIN: menu_plain_settings();break;
1484 }
1485 break;
1486
1487 case 3:
1488 menu_general_settings();
1489 break;
1490
1491 case 4:
1492 exit_clock = true;
1493 done = true;
1494 break;
1495
1496 default:
1497 done=true;
1498 break;
1499 }
1500 }
1501
1502 rb->lcd_setfont(FONT_SYSFIXED);
1503 set_digital_colors();
1504}
1505
1506/**********************************************************************
1507 * Plugin starts here
1508 **********************************************************************/
1509enum plugin_status plugin_start(struct plugin_api* api, void* parameter)
1510{
1511 int button;
1512
1513 /* time/date ints */
1514 int hour, minute, second;
1515 int temphour;
1516 int last_second = -1;
1517 int year, day, month;
1518
1519 bool counter_btn_held = false;
1520
1521 struct tm* current_time;
1522
1523 (void)parameter;
1524 rb = api;
1525
1526#if LCD_DEPTH > 1
1527 rb->lcd_set_backdrop(NULL);
1528#endif
1529
1530 init_clock();
1531
1532 /* init xlcd functions */
1533 xlcd_init(rb);
1534
1535 set_digital_colors();
1536
1537 while(!exit_clock)
1538 {
1539 /*********************
1540 * Time info
1541 *********************/
1542 current_time = rb->get_time();
1543 hour = current_time->tm_hour;
1544 minute = current_time->tm_min;
1545 second = current_time->tm_sec;
1546 temphour = current_time->tm_hour;
1547
1548 /*********************
1549 * Date info
1550 *********************/
1551 year = current_time->tm_year + 1900;
1552 day = current_time->tm_mday;
1553 month = current_time->tm_mon + 1;
1554
1555 if(second != last_second)
1556 {
1557 rb->lcd_clear_display();
1558
1559 /* Analog mode */
1560 if(clock_settings.clock == ANALOG)
1561 analog_clock(hour, minute, second);
1562 /* Digital mode */
1563 else if(clock_settings.clock == DIGITAL)
1564 {
1565 if(clock_settings.digital[digital_blinkcolon])
1566 digital_clock(hour, minute, second, second & 1);
1567 else
1568 digital_clock(hour, minute, second, true);
1569 }
1570 /* Fullscreen mode */
1571 else if(clock_settings.clock == FULLSCREEN)
1572 fullscreen_clock(hour, minute, second);
1573 /* Binary mode */
1574 else if(clock_settings.clock == BINARY)
1575 binary_clock(hour, minute, second);
1576 /* Plain mode */
1577 else if(clock_settings.clock == PLAIN)
1578 {
1579 if(clock_settings.plain[plain_blinkcolon])
1580 plain_clock(hour, minute, second, second & 1);
1581 else
1582 plain_clock(hour, minute, second, true);
1583 }
1584
1585 /* show counter */
1586 show_counter();
1587 }
1588
1589 if(clock_settings.analog[analog_time] == 2 && temphour == 0)
1590 temphour = 12;
1591 if(clock_settings.analog[analog_time] == 2 && temphour > 12)
1592 temphour -= 12;
1593
1594 /* all the "extras" - readouts/displays */
1595 draw_extras(year, day, month, temphour, minute, second);
1596
1597 if(!idle_poweroff)
1598 rb->reset_poweroff_timer();
1599
1600 rb->lcd_update();
1601
1602 /*************************
1603 * Scan for button presses
1604 ************************/
1605 button = pluginlib_getaction(rb, HZ/10, plugin_contexts, 2);
1606 switch (button)
1607 {
1608 case ACTION_COUNTER_TOGGLE: /* start/stop counter */
1609 if(clock_settings.general[general_counter])
1610 {
1611 if(!counter_btn_held) /* Ignore if the counter was reset */
1612 {
1613 if(counting)
1614 {
1615 counting = false;
1616 counter += passed_time;
1617 }
1618 else
1619 {
1620 counting = true;
1621 start_tick = *rb->current_tick;
1622 }
1623 }
1624 counter_btn_held = false;
1625 }
1626 break;
1627
1628 case ACTION_COUNTER_RESET: /* reset counter */
1629 if(clock_settings.general[general_counter])
1630 {
1631 counter_btn_held = true; /* Ignore the release event */
1632 counter = 0;
1633 start_tick = *rb->current_tick;
1634 }
1635 break;
1636
1637 case ACTION_MODE_NEXT:
1638 if(clock_settings.clock < CLOCK_MODES)
1639 clock_settings.clock++;
1640 else
1641 clock_settings.clock = 1;
1642
1643 set_digital_colors();
1644 break;
1645
1646 case ACTION_MODE_PREV:
1647 if(clock_settings.clock > 1)
1648 clock_settings.clock--;
1649 else
1650 clock_settings.clock = CLOCK_MODES;
1651
1652 set_digital_colors();
1653 break;
1654
1655 case ACTION_MENU:
1656 main_menu();
1657 break;
1658
1659 case ACTION_EXIT:
1660 exit_clock=true;
1661 break;
1662
1663 default:
1664 if(rb->default_event_handler_ex(button, cleanup, NULL)
1665 == SYS_USB_CONNECTED)
1666 return PLUGIN_USB_CONNECTED;
1667 break;
1668 }
1669 }
1670
1671 cleanup(NULL);
1672 return PLUGIN_OK;
1673}