Added some small boring scripts and programs writen in few last years
[mirrors/Programs.git] / c / aclox.c
1 /*
2 * Compile with:
3 * gcc -lm aclox.c -o aclox; ./aclox
4 * or
5 * CFLAGS='-lm' make aclox; ./aclox
6 */
7
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <unistd.h>
11 #include <math.h>
12 #include <time.h>
13
14 #include <termios.h>
15 #include <sys/ioctl.h>
16
17 //config
18 #define HOUR_NUMBERS 1
19 #define HI_PRECISION 1
20 #define SHOW_DIGITS 1
21 #define MINUTE_DOTS 1
22 #define SMOOTH_MOTION 1
23 #define zoom 2
24
25 //useful macros
26 #define max(a,b) ((a)>=(b)?(a):(b))
27 #define min(a,b) ((a)<=(b)?(a):(b))
28 #define PI 3.141592654
29 #define deg2rad(a) (((a)/180)*PI)
30 //phi = angle, r = length
31 #define polar2x(phi, r) ((r) * cos(deg2rad(phi)))
32 #define polar2y(phi, r) ((r) * sin(deg2rad(phi)))
33 #define cls() printf("\033[2J")
34 #define top() printf("\033[0;0H")
35
36 int llines = -1, lcols = -1;
37 void render_clock(double h, double m, double s) {
38 //colors
39 char color_empty = ' ';
40 char color_center = '+';
41 char color_number = '#';
42 char color_dot = '.';
43 char color_h = 'H';
44 char color_m = 'm';
45 char color_s = '*';
46
47 //convert digital time to "analog" time (enables smooth motion)
48 if(SMOOTH_MOTION) {
49 m += s/(double)60;
50 h += m/(double)60;
51 }
52
53 //get size of terminal
54 int lines = 20;
55 int cols = 20;
56 /*FILE *p;
57 p = popen("stty size", "r");
58 fscanf(p, "%d %d", &lines, &cols);
59 close((int)p);*/
60 struct winsize ws;
61 if ((ioctl(STDOUT_FILENO, TIOCGWINSZ, &ws) == -1 &&
62 ioctl(STDERR_FILENO, TIOCGWINSZ, &ws) == -1 &&
63 ioctl(STDIN_FILENO, TIOCGWINSZ, &ws) == -1) ||
64 ws.ws_col == 0) {
65 lines = 25;
66 cols = 80;
67 } else {
68 lines = ws.ws_row;
69 cols = ws.ws_col;
70 }
71
72 //calculate size
73 int size = 40;
74 size = min(lines,cols/zoom);
75 size = ((size%2)==0?size-1:size); //make size odd
76 //printf("%d\n", size);
77
78 //empty canvas
79 char cifernik[size*zoom][size];
80 int i, x, y;
81 double phi, r;
82 for(y=0;y<size;y++) for(x=0;x<(size*zoom);x++) cifernik[x][y] = color_empty;
83
84 //draw minute dots
85 if(MINUTE_DOTS && size > 40) for(i=1;i<=60;i++) {
86 phi = -90+(i*(360/60));
87 r = size/2;
88 x = round((r+polar2x(phi,r))*zoom);
89 y = round(r+polar2y(phi,r));
90 cifernik[x][y] = color_dot;
91 }
92
93 //draw numbers
94 for(i=1;i<=12;i++) {
95 phi = -90+(i*(360/12));
96 r = size/2;
97 x = round((r+polar2x(phi,r))*zoom);
98 y = round(r+polar2y(phi,r));
99 if(HOUR_NUMBERS) {
100 cifernik[x][y] = '0'+(i%10);
101 if(i>9) cifernik[x-1][y] = '0'+(i/10);
102 } else {
103 cifernik[x][y] = color_number;
104 }
105 }
106
107 //draw minute hand
108 phi = -90+(m*(360/60));
109 for(r=0;r<(size/2);r++) {
110 x = round((size/2+polar2x(phi,r))*zoom);
111 y = round(size/2+polar2y(phi,r));
112 cifernik[x][y] = color_m;
113 }
114
115 //draw hour hand
116 phi = -90+(h*(double)(360/12));
117 for(r=0;r<(size/3);r++) {
118 x = round((size/2+polar2x(phi,r))*zoom);
119 y = round(size/2+polar2y(phi,r));
120 cifernik[x][y] = color_h;
121 }
122
123 //draw seconds hand
124 phi = -90+(s*(360/60));
125 for(r=0;r<(size/2);r++) {
126 x = round((size/2+polar2x(phi,r))*zoom);
127 y = round(size/2+polar2y(phi,r));
128 cifernik[x][y] = color_s;
129 }
130
131 //draw center dot
132 cifernik[(size/2)*zoom][size/2] = color_center;
133
134 //cls when terminal size changes
135 if(lines != llines || cols != lcols) {
136 cls();
137 llines=lines;
138 lcols=cols;
139 }
140
141 //print to terminal
142 for(y=0;y<size;y++) {
143 for(r=0;r<=((cols-(size*zoom))/2);r++) putchar(' ');
144 for(x=0;x<((size*zoom)-(zoom-1));x++) {
145 putchar(cifernik[x][y]);
146 }
147 if(y!=(size-1)) putchar('\n');
148 }
149 }
150
151 int main(void) {
152 int s = -1;
153 time_t cast;
154 struct tm *cas;
155
156 while(1) {
157 cast = time(NULL);
158 cas = localtime(&cast);
159
160 if(cas->tm_sec != s){
161 s = cas->tm_sec;
162 top();
163 render_clock(cas->tm_hour,cas->tm_min,cas->tm_sec); //analog
164 if(SHOW_DIGITS) printf("\r[%.2d:%.2d:%.2d]",cas->tm_hour,cas->tm_min,cas->tm_sec); //digital
165 }
166 if(HI_PRECISION) { usleep(100000); }
167 else { sleep(1); }
168 }
169 }
This page took 0.321425 seconds and 4 git commands to generate.