2 * Grand digital clock for curses compatible terminals
3 * Usage: grdc [-st] [n] -- run for n seconds (default infinity)
5 * -t: output time in 12-hour format
8 * modified 10-18-89 for curses (jrl)
9 * 10-18-89 added signal handling
11 * modified 03-25-03 for 12 hour option
12 * - Samy Al Bahra <samy@kerneled.com>
27 static struct timespec now;
30 static short disp[11] = {
31 075557, 011111, 071747, 071717, 055711,
32 074717, 074757, 071111, 075757, 075717, 002020
34 static long old[6], next[6], new[6], mask;
36 static volatile sig_atomic_t sigtermed;
38 static int hascolor = 0;
40 static void set(int, int);
41 static void standt(int);
42 static void movto(int, int);
43 static void sighndl(int);
44 static void usage(void) __dead2;
54 main(int argc, char *argv[])
56 struct timespec delay;
67 while ((ch = getopt(argc, argv, "ts")) != -1)
91 warnx("number of seconds is out of range");
100 signal(SIGINT,sighndl);
101 signal(SIGTERM,sighndl);
102 signal(SIGHUP,sighndl);
108 hascolor = has_colors();
112 init_pair(1, COLOR_BLACK, COLOR_RED);
113 init_pair(2, COLOR_RED, COLOR_BLACK);
114 init_pair(3, COLOR_WHITE, COLOR_BLACK);
115 attrset(COLOR_PAIR(2));
122 attrset(COLOR_PAIR(3));
124 mvaddch(YBASE - 2, XBASE - 3, ACS_ULCORNER);
125 hline(ACS_HLINE, XLENGTH);
126 mvaddch(YBASE - 2, XBASE - 2 + XLENGTH, ACS_URCORNER);
128 mvaddch(YBASE + YDEPTH - 1, XBASE - 3, ACS_LLCORNER);
129 hline(ACS_HLINE, XLENGTH);
130 mvaddch(YBASE + YDEPTH - 1, XBASE - 2 + XLENGTH, ACS_LRCORNER);
132 move(YBASE - 1, XBASE - 3);
133 vline(ACS_VLINE, YDEPTH);
135 move(YBASE - 1, XBASE - 2 + XLENGTH);
136 vline(ACS_VLINE, YDEPTH);
138 attrset(COLOR_PAIR(2));
140 clock_gettime(CLOCK_REALTIME_FAST, &now);
141 prev_sec = now.tv_sec;
144 tm = localtime(&now.tv_sec);
145 set(tm->tm_sec%10, 0);
146 set(tm->tm_sec/10, 4);
147 set(tm->tm_min%10, 10);
148 set(tm->tm_min/10, 14);
151 if (tm->tm_hour < 12) {
152 if (tm->tm_hour == 0)
154 mvaddstr(YBASE + 5, XBASE + 52, "AM");
156 if (tm->tm_hour > 12)
158 mvaddstr(YBASE + 5, XBASE + 52, "PM");
162 set(tm->tm_hour%10, 20);
163 set(tm->tm_hour/10, 24);
169 new[i] = (new[i]&~mask) | (new[i+1]&mask);
170 new[5] = (new[5]&~mask) | (next[k]&mask);
172 new[k] = (new[k]&~mask) | (next[k]&mask);
174 for(s=1; s>=0; s--) {
177 if((a = (new[i]^old[i])&(s ? new : old)[i]) != 0) {
178 for(j=0,t=1<<26; t; t>>=1,j++) {
181 movto(YBASE + i, XBASE + 2*j);
198 clock_gettime(CLOCK_REALTIME_FAST, &now);
199 if (now.tv_sec == prev_sec) {
200 if (delay.tv_nsec > 0) {
202 delay.tv_nsec = 1000000000 - now.tv_nsec;
207 nanosleep(&delay, NULL);
208 clock_gettime(CLOCK_REALTIME_FAST, &now);
210 n -= now.tv_sec - prev_sec;
211 prev_sec = now.tv_sec;
217 errx(1, "terminated by signal %d", (int)sigtermed);
234 next[i] |= ((disp[t]>>(4-i)*3)&07)<<n;
235 mask |= (next[i]^old[i])&m;
246 attron(COLOR_PAIR(1));
252 attron(COLOR_PAIR(2));
260 movto(int line, int col)
269 (void)fprintf(stderr, "usage: grdc [-st] [n]\n");