ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/rxvt-unicode/src/rclock.C
(Generate patch)

Comparing rxvt-unicode/src/rclock.C (file contents):
Revision 1.2 by root, Mon May 10 00:36:58 2021 UTC vs.
Revision 1.6 by root, Sat Jul 17 00:10:15 2021 UTC

1/*--------------------------------*-C-*---------------------------------* 1/*--------------------------------*-C-*---------------------------------*
2 * Copyright 2021 Marc Lehmann <schmorp@schmorp.de>
3 * Copyright Wolfgang Pietsch
2 * Copyright 1997 1998 Oezguer Kesim <kesim@math.fu-berlin.de> 4 * Copyright 1997 1998 Oezguer Kesim <kesim@math.fu-berlin.de>
3 * Copyright 1992, 1993 Robert Nation <nation@rocket.sanders.lockheed.com> 5 * Copyright 1992, 1993 Robert Nation <nation@rocket.sanders.lockheed.com>
4 * 6 *
5 * This program is free software; you can redistribute it and/or modify 7 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by 8 * it under the terms of the GNU General Public License as published by
14 * 16 *
15 * You should have received a copy of the GNU General Public License 17 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software 18 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 *----------------------------------------------------------------------*/ 20 *----------------------------------------------------------------------*/
19#ifdef HAVE_CONFIG_H
20# include <config.h>
21#else
22/* # define STDC_HEADERS */
23# define HAVE_UNISTD_H
24# define TIME_WITH_SYS_TIME
25# define HAVE_SYS_TIME_H
26# ifdef _AIX
27# define HAVE_SYS_SELECT_H
28# endif
29#endif
30
31#include "../src/version.h"
32#include "feature.h"
33
34#include <ctype.h> 21#include <ctype.h>
35/* #ifdef STDC_HEADERS */ 22
36# include <stdarg.h> 23#include <stdarg.h>
37# include <stdio.h> 24#include <stdio.h>
38# include <stdlib.h> 25#include <stdlib.h>
39# include <string.h> 26#include <string.h>
40/* #endif */
41 27
42#ifdef HAVE_UNISTD_H
43# include <unistd.h> 28#include <unistd.h>
44#endif
45 29
46#ifdef TIME_WITH_SYS_TIME
47# include <sys/time.h> 30#include <sys/types.h>
48# include <time.h>
49#else
50# ifdef HAVE_SYS_TIME_H
51# include <sys/time.h>
52# else
53# include <time.h>
54# endif
55#endif
56
57#if defined (__svr4__)
58# include <sys/resource.h> /* for struct rlimit */
59#endif
60
61#ifdef HAVE_SYS_SELECT_H
62# include <sys/select.h> 31#include <sys/select.h>
63#endif
64#include <sys/stat.h> 32#include <sys/stat.h>
65 33
66#ifdef MAIL 34#include <sys/time.h>
35#include <time.h>
36
67#include <dirent.h> 37#include <dirent.h>
68#endif
69 38
70#include <X11/Intrinsic.h> /* Xlib, Xutil, Xresource, Xfuncproto */ 39#include <X11/Xlib.h>
40#include <X11/Xutil.h>
41
42#include "ecb.h"
71 43
72#define APL_CLASS "Clock" 44#define APL_CLASS "Clock"
73#define APL_NAME "rclock" 45#define APL_NAME "rclock"
74#define MSG_CLASS "Appointment" 46#define MSG_CLASS "Appointment"
75#define MSG_NAME "Appointment" 47#define MSG_NAME "Appointment"
76#define CONFIG_FILE ".rclock" 48#define CONFIG_FILE ".rclock"
77 49
78#ifndef EXIT_SUCCESS /* missed from <stdlib.h> ? */ 50#ifndef EXIT_SUCCESS /* missed from <stdlib.h> ? */
79# define EXIT_SUCCESS 0 51# define EXIT_SUCCESS 0
80# define EXIT_FAILURE 1 52# define EXIT_FAILURE 1
81#endif 53#endif
82 54
55#define VERSION "TODO: fetch from urxvt somehow"
56
57/*--------------------------------*-C-*---------------------------------*
58 * Compile-time configuration.
59 *----------------------------------------------------------------------*
60 * Copyright (C) 1997 1998 mj olesen <olesen@me.QueensU.CA>
61 *
62 * This program is free software; you can redistribute it and/or modify
63 * it under the terms of the GNU General Public License as published by
64 * the Free Software Foundation; either version 2 of the License, or
65 * (at your option) any later version.
66 *
67 * This program is distributed in the hope that it will be useful,
68 * but WITHOUT ANY WARRANTY; without even the implied warranty of
69 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
70 * GNU General Public License for more details.
71 *
72 * You should have received a copy of the GNU General Public License
73 * along with this program; if not, write to the Free Software
74 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
75 *----------------------------------------------------------------------*/
76
77/*----------------------------------------------------------------------*
78 * #define ICONWIN
79 * to enable fancy (active) icon
80 *
81 * #define REMINDERS
82 * to enable the appointment reminder functions
83 *
84 * #define NO_REMINDER_EXEC
85 * to disable the execution of a program on an appointment
86 *
87 * #define DATE_ON_CLOCK_FACE
88 * to display today's date on the face of the clock
89 * Note: this requires REMINDERS since it uses the same font
90 *
91 * #define MAIL
92 * to enable xbiff-type mail reminders
93 *
94 * #define MAIL_BELL
95 * to enable xbiff-type mail reminders with a beep
96 *
97 * #define MAIL_SPAWN "xmh\ -font\ 7x14\&"
98 * to define a mail program to run
99 *
100 * #define MAIL_SPOOL "/var/spool/mail/"
101 * to define the mail spool when the $MAIL variable isn't set
102 *
103 * program size approximately doubles from no options to all options
104 *----------------------------------------------------------------------*/
105#define ICONWIN
106#define REMINDERS
107
108/* #define NO_REMINDER_EXEC */
109#define DATE_ON_CLOCK_FACE
110#define MAIL
111
112/* #define MAIL_BELL */ /* TODO: command line switch */
113
114/* #define MAIL_SPAWN "xmh\ -font\ 7x14\&" */ /* TODO: command line switch */
115#define MAIL_SPOOL "/var/spool/mail/"
116
117/*----------------------------------------------------------------------*
118 * #define CLOCKUPDATE 30
119 * to define the frequency (seconds) to update the clock
120 *
121 * #define MAILUPDATE 60
122 * to define the frequency (seconds) to check for new mail
123 *
124 * #define REMINDERS_TIME 10
125 * to define the frequency (minutes) to check ~/.rclock
126 *
127 * #define DEFER_TIME 3
128 * to define the amount (minutes) to defer a message
129 *
130 * #define ADJUST_TIME
131 * to add -adjust command-line option
132 *
133 * #define CENTURY 2000
134 * to set the base century for 2 digit year short-hand
135 *----------------------------------------------------------------------*/
136#define CLOCKUPDATE 30
137#define MAILUPDATE 60
138#define REMINDERS_TIME 10
139#define DEFER_TIME 3
140#define ADJUST_TIME
141
142#define CENTURY 2000 /* TODO: verify */
143
144/*----------------------------------------------------------------------*
145 * #define FONT_NAME "7x14"
146 * to define the font to be used for appointment reminders
147 *
148 * #define FG_COLOR_NAME "black"
149 * #define BG_COLOR_NAME "white"
150 * to define the foreground/background colors to use
151 *----------------------------------------------------------------------*/
152#define FONT_NAME "7x14"
153#define FG_COLOR_NAME "black"
154#define BG_COLOR_NAME "white"
155
156/*----------------------------------------------------------------------*
157 * #define DAY_NAMES "umtwrfs*"
158 * define this string appropriate for any language.
159 *
160 * It starts with a symbol for Sunday, ends with Saturday, then '*'
161 * NOTE: 8 characters total - 7 days of the week plus '*'
162 *----------------------------------------------------------------------*/
163#define DAY_NAMES "umtwrfs*"
164
165/*----------------------------------------------------------------------*
166 * #define SUBTICKS
167 * to show additional minute/second markings
168 *----------------------------------------------------------------------*/
169#define SUBTICKS
170
171/*----------------------------------------------------------------------*
172 * sort out conflicts
173 *----------------------------------------------------------------------*/
174#if defined (MAIL_BELL) || defined (MAIL_SPAWN) || defined (MAIL_SPOOL)
175# ifndef MAIL
176# define MAIL
177# endif
178#endif
179
83/*----------------------------------------------------------------------*/ 180/*----------------------------------------------------------------------*/
181// fourth-order fixed point sine approximation,
182// adapted from https://www.coranac.com/2009/07/sines/
84 183
184static int32_t
185Sin (int32_t arg)
186{
187 int32_t x = (arg - 360) * 16384 / 360;
188
189 int c, x2, y;
190 static const int qN = 13, qA = 12, B = 19900, C = 3516;
191
192 c = x << (30 - qN); // Semi-circle info into carry.
193 x -= 1 << qN; // sine -> cosine calc
194
195 x = x << (31 - qN); // Mask with PI
196 x = x >> (31 - qN); // Note: SIGNED shift! (to qN)
197 x = x * x >> (2 * qN - 14); // x=x^2 To Q14
198
199 y = B - (x * C >> 14); // B - x^2*C
200 y = (1 << qA) - (x * y >> 16); // A - x^2*(B-x^2*C)
201
202 x = c < 0 ? y : -y;
203
204 return x;
205}
206
207/*----------------------------------------------------------------------*/
208
85static Display* Xdisplay; /* X display */ 209static Display *Xdisplay; /* X display */
86static int Xfd; /* file descriptor of server connection */ 210static int Xfd; /* file descriptor of server connection */
87static GC Xgc, Xrvgc; /* normal, reverse video GC */ 211static GC Xgc, Xrvgc; /* normal, reverse video GC */
88 212
89#define Xscreen DefaultScreen (Xdisplay) 213#define Xscreen DefaultScreen (Xdisplay)
90#define Xcmap DefaultColormap (Xdisplay, Xscreen) 214#define Xcmap DefaultColormap (Xdisplay, Xscreen)
91#define Xroot DefaultRootWindow (Xdisplay) 215#define Xroot DefaultRootWindow (Xdisplay)
92 216
93/* windows and their sizes */ 217/* windows and their sizes */
94typedef struct { 218typedef struct
219{
95 Window win; 220 Window win;
96 int width, height; 221 int width, height;
97} mywindow_t; 222} mywindow_t;
98 223
99static mywindow_t Clock = {None, 80, 80}; /* parent window */ 224static mywindow_t Clock = { None, 80, 80 }; /* parent window */
100 225
101#define fgColor 0 226#define fgColor 0
102#define bgColor 1 227#define bgColor 1
103static const char * rs_color [2] = { FG_COLOR_NAME, BG_COLOR_NAME }; 228static const char *rs_color[2] = { FG_COLOR_NAME, BG_COLOR_NAME };
104static Pixel PixColors [2]; 229
230static unsigned long PixColors[2];
105static const char * rs_geometry = NULL; 231static const char *rs_geometry = NULL;
106 232
107#ifdef ICONWIN 233#ifdef ICONWIN
108static const char * rs_iconGeometry = NULL; 234static const char *rs_iconGeometry = NULL;
109static mywindow_t Icon = {None, 65, 65}; /* icon window */ 235static mywindow_t Icon = { None, 65, 65 }; /* icon window */
236
110static int iconic_state = NormalState; /* iconic startup? */ 237static int iconic_state = NormalState; /* iconic startup? */
111#endif 238#endif
112 239
113#ifdef REMINDERS 240#ifdef REMINDERS
114static mywindow_t Msg = {0, 0, 0}; /* message window */ 241static mywindow_t Msg = { 0, 0, 0 }; /* message window */
242
115static struct { 243static struct
244{
116 Window 245 Window
117# ifndef NO_REMINDER_EXEC 246# ifndef NO_REMINDER_EXEC
118 Start, 247 Start,
119# endif 248# endif
120 Dismiss, 249 Dismiss, Defer;
121 Defer;
122 int width, height; 250 int width, height;
123} msgButton; 251} msgButton;
124 252
125static XFontStruct * Xfont; 253static XFontStruct *Xfont;
254
126#define FontHeight() (Xfont->ascent + Xfont->descent) 255# define FontHeight() (Xfont->ascent + Xfont->descent)
127static int Msg_Mapped = 0; /* message window mapped? */ 256static int Msg_Mapped = 0; /* message window mapped? */
128static int reminderTime = -1; 257static int reminderTime = -1;
129static char message [256] = ""; 258static char message[256] = "";
259
130#ifndef NO_REMINDER_EXEC 260# ifndef NO_REMINDER_EXEC
131static char execPrgm [256] = ""; 261static char execPrgm[256] = "";
132#endif 262# endif
133static const char * reminders_file = NULL; /* name of ~/.rclock file */ 263static const char *reminders_file = NULL; /* name of ~/.rclock file */
264
134#ifdef DATE_ON_CLOCK_FACE 265# ifdef DATE_ON_CLOCK_FACE
135static int show_date = 1; /* show date on face of clock */ 266static int show_date = 1; /* show date on face of clock */
136#endif 267# endif
137#endif 268#endif
138 269
139#ifdef ADJUST_TIME 270#ifdef ADJUST_TIME
140static int adjustTime = 0; 271static int adjustTime = 0;
141#else 272#else
142# define adjustTime 0 273# define adjustTime 0
143#endif 274#endif
144 275
145#ifdef CENTURY 276#ifdef CENTURY
146# if (CENTURY < 1900) 277# if (CENTURY < 1900)
147Error, Cenury incorrectly set. 278Error, Century incorrectly set.
148# endif 279# endif
149#else 280#else
150# define CENTURY 1900 281# define CENTURY 1900
151#endif 282#endif
152 283
153static int clockUpdate = CLOCKUPDATE; 284static int clockUpdate = CLOCKUPDATE;
154 285
155#ifdef MAIL 286#ifdef MAIL
156static int mailUpdate = MAILUPDATE; 287static int mailUpdate = MAILUPDATE;
157static char * mail_file = NULL; 288static char *mail_file = NULL;
289
158#ifndef MAIL_SPAWN 290# ifndef MAIL_SPAWN
159static char * mail_spawn = NULL; 291static char *mail_spawn = NULL;
160#endif 292# endif
161static int is_maildir = 0; 293static int is_maildir = 0;
162#endif 294#endif
163 295
164static XSizeHints szHint = { 296static XSizeHints szHint = {
165 PMinSize | PResizeInc | PBaseSize | PWinGravity, 297 PMinSize | PResizeInc | PBaseSize | PWinGravity,
166 0, 0, 80, 80, /* x, y, width and height */ 298 0, 0, 80, 80, /* x, y, width and height */
167 1, 1, /* Min width and height */ 299 1, 1, /* Min width and height */
168 0, 0, /* Max width and height */ 300 0, 0, /* Max width and height */
169 1, 1, /* Width and height increments */ 301 1, 1, /* Width and height increments */
170 {1, 1}, /* x, y increments */ 302 {1, 1}, /* x, y increments */
171 {1, 1}, /* Aspect ratio - not used */ 303 {1, 1}, /* Aspect ratio - not used */
172 0, 0, /* base size */ 304 0, 0, /* base size */
173 NorthWestGravity /* gravity */ 305 NorthWestGravity /* gravity */
174}; 306};
175 307
176/* subroutine declarations */ 308/* subroutine declarations */
177static void geometry2sizehint (mywindow_t * /* win */, 309static void geometry2sizehint (mywindow_t * /* win */ ,
178 const char * /* geom */); 310 const char * /* geom */ );
179static void Create_Windows (int /* argc */, 311static void Create_Windows (int /* argc */ ,
180 char * /* argv */ []); 312 char * /* argv */ []);
181static void getXevent (void); 313static void getXevent ();
182static void print_error (const char * /* fmt */, ...); 314static void print_error (const char * /* fmt */ , ...);
183 315
184static void Draw_Window (mywindow_t * /* this_win */, 316static void Draw_Window (mywindow_t * /* this_win */ ,
185 int /* full_redraw */); 317 int /* full_redraw */ );
186static void Reminder (void); 318static void Reminder ();
187static void Next_Reminder (int /* update_only */); 319static void Next_Reminder (int /* update_only */ );
188 320
189/* Arguments for Next_Reminder() */ 321/* Arguments for Next_Reminder() */
190#define REPLACE 0 322#define REPLACE 0
191#define UPDATE 1 323#define UPDATE 1
192 324
193/*----------------------------------------------------------------------*/ 325/*----------------------------------------------------------------------*/
194 326
195static void 327static void
196usage (void) 328usage ()
197{ 329{
198 int i; 330 int i;
199 struct { 331 struct
332 {
200 const char * const opt; 333 const char *const opt;
201 const char * const desc; 334 const char *const desc;
202 } optList[] = { 335 } optList[] = {
203#define optList_size() (sizeof(optList)/sizeof(optList[0])) 336#define optList_size() (sizeof (optList) / sizeof (optList[0]))
204 { "-display displayname", "X server to contact" }, 337 {"-display displayname", "X server to contact"},
205 { "-geometry geom", "size (in pixels) and position" }, 338 {"-geometry geom", "size (in pixels) and position"},
206 { "-bg color", "background color" }, 339 {"-bg color", "background color"},
207 { "-fg color", "foreground color" }, 340 {"-fg color", "foreground color"},
208#ifdef REMINDERS 341#ifdef REMINDERS
209 { "-fn fontname", "normal font for messages" }, 342 {"-fn fontname", "normal font for messages"},
210#ifdef DATE_ON_CLOCK_FACE 343# ifdef DATE_ON_CLOCK_FACE
211 { "-nodate", "do not display date on the clock face" }, 344 {"-nodate", "do not display date on the clock face"},
212#endif 345# endif
213#endif 346#endif
214#ifdef ICONWIN 347#ifdef ICONWIN
215 { "-iconic", "start iconic" }, 348 {"-iconic", "start iconic"},
216#endif 349#endif
217#ifdef ADJUST_TIME 350#ifdef ADJUST_TIME
218 { "-adjust +/-ddhhmm", "adjust clock time" }, 351 {"-adjust +/-ddhhmm", "adjust clock time"},
219#endif 352#endif
220 { "-update seconds", "clock update interval" }, 353 {"-update seconds", "clock update interval"},
221#ifdef MAIL 354#ifdef MAIL
222 { "-mail seconds", "check $MAIL interval" }, 355 {"-mail seconds", "check $MAIL interval"},
223 { "-mailfile file", "file to use for mail checking" }, 356 {"-mailfile file", "file to use for mail checking"},
224#ifndef MAIL_SPAWN 357# ifndef MAIL_SPAWN
225 { "-mailspawn cmd", "execute `cmd` when clock is clicked" }, 358 {"-mailspawn cmd", "execute `cmd` when clock is clicked"},
226#endif 359# endif
227#endif 360#endif
228 { "#geom", "icon window geometry" } 361 {"#geom", "icon window geometry"}
229 }; 362 };
230 363
231 fprintf (stderr, "\nUsage v" VERSION ":\n " APL_NAME " [options]\n\n" 364 fprintf (stderr, "\nUsage v" VERSION ":\n " APL_NAME " [options]\n\n" "where options include:\n");
232 "where options include:\n");
233 365
234 for (i = 0; i < optList_size(); i++) 366 for (i = 0; i < (int)optList_size (); i++)
235 fprintf (stderr, " %-29s%s\n", optList[i].opt, optList[i].desc); 367 fprintf (stderr, " %-29s%s\n", optList[i].opt, optList[i].desc);
236} 368}
237 369
238 370
239/**************** 371/****************
240 * Check out if we are using a maildir drop (qmail) 372 * Check out if we are using a maildir drop (qmail)
241 * Note: this changes mail_dir to hold the "new" diretory 373 * Note: this changes mail_dir to hold the "new" diretory
242 */ 374 */
243#ifdef MAIL 375#ifdef MAIL
244static void 376static void
245CheckMaildir() 377CheckMaildir ()
246{ 378{
247 struct stat st; 379 struct stat st;
248 char *buf, *p; 380 char *buf, *p;
249 381
250 if( !*mail_file || stat(mail_file, &st) || !S_ISDIR(st.st_mode) ) 382 if (!*mail_file || stat (mail_file, &st) || !S_ISDIR (st.st_mode))
251 return; /* no */ 383 return; /* no */
252 384
253 if( !(buf = malloc(strlen(mail_file)+5)) ) { 385 if (!(buf = (char *) malloc (strlen (mail_file) + 5)))
386 {
254 print_error ("malloc error"); 387 print_error ("malloc error");
255 exit( EXIT_FAILURE ); 388 exit (EXIT_FAILURE);
256 } 389 }
257 strcpy(buf,mail_file); 390 strcpy (buf, mail_file);
258 p = buf+strlen(buf); 391 p = buf + strlen (buf);
259 if( p[-1] != '/' ) 392 if (p[-1] != '/')
260 *p++ = '/'; 393 *p++ = '/';
261 394
262 strcpy(p, "tmp" ); 395 strcpy (p, "tmp");
263 if( stat(buf, &st) || !S_ISDIR(st.st_mode ) ) 396 if (stat (buf, &st) || !S_ISDIR (st.st_mode))
264 goto leave; 397 goto leave;
265 strcpy(p, "cur" ); 398 strcpy (p, "cur");
266 if( stat(buf, &st) || !S_ISDIR(st.st_mode ) ) 399 if (stat (buf, &st) || !S_ISDIR (st.st_mode))
267 goto leave; 400 goto leave;
268 strcpy(p, "new" ); 401 strcpy (p, "new");
269 if( stat(buf, &st) || !S_ISDIR(st.st_mode ) ) 402 if (stat (buf, &st) || !S_ISDIR (st.st_mode))
270 goto leave; 403 goto leave;
271 404
272 mail_file = buf; 405 mail_file = buf;
273 is_maildir = 1; 406 is_maildir = 1;
274 return; 407 return;
275 leave: 408leave:
276 free(buf); 409 free (buf);
277} 410}
278#endif 411#endif
279 412
280/*----------------------------------------------------------------------* 413/*----------------------------------------------------------------------*
281 * rclock - Rob's clock 414 * rclock - Rob's clock
282 * simple X windows clock with appointment reminder 415 * simple X windows clock with appointment reminder
283 *----------------------------------------------------------------------*/ 416 *----------------------------------------------------------------------*/
284int 417int
285main (int argc, char * argv []) 418main (int argc, char *argv[])
286{ 419{
287 int i; 420 int i;
288 char * opt, * val; 421 char *opt, *val;
289 const char * display_name = NULL; 422 const char *display_name = NULL;
290 XGCValues gcv; 423 XGCValues gcv;
291 424
292#ifdef REMINDERS 425#ifdef REMINDERS
293 const char * rs_font = FONT_NAME; 426 const char *rs_font = FONT_NAME;
294 427
295 /* find the ~/.rclock file */ 428 /* find the ~/.rclock file */
296 if ((val = getenv ("HOME")) != NULL) 429 if ((val = getenv ("HOME")) != NULL)
297 { 430 {
298 char * p = malloc (strlen (CONFIG_FILE) + strlen (val) + 2); 431 char *p = (char *) malloc (strlen (CONFIG_FILE) + strlen (val) + 2);
432
299 if (p == NULL) 433 if (p == NULL)
300 goto Malloc_Error; 434 goto Malloc_Error;
301 435
302 strcpy (p, val); 436 strcpy (p, val);
303 strcat (p, "/" CONFIG_FILE); 437 strcat (p, "/" CONFIG_FILE);
304 438
305 reminders_file = p; 439 reminders_file = p;
306 } 440 }
307#endif 441#endif
308#ifdef MAIL 442#ifdef MAIL
309 val = getenv ("MAIL"); /* get the mail spool file name */ 443 val = getenv ("MAIL"); /* get the mail spool file name */
310#ifdef MAIL_SPOOL 444# ifdef MAIL_SPOOL
311 if (val == NULL) /* csh doesn't set $MAIL */ 445 if (val == NULL) /* csh doesn't set $MAIL */
312 { 446 {
313 const char * spool = MAIL_SPOOL; 447 const char *spool = MAIL_SPOOL;
314 char * user = getenv ("USER"); /* assume this works */ 448 char *user = getenv ("USER"); /* assume this works */
449
315 if (user != NULL) { 450 if (user != NULL)
451 {
316 val = malloc (strlen (spool) + strlen (user) + 1); 452 val = (char *) malloc (strlen (spool) + strlen (user) + 1);
317 if (val == NULL) 453 if (val == NULL)
318 goto Malloc_Error; 454 goto Malloc_Error;
319 strcpy (val, spool); 455 strcpy (val, spool);
320 strcat (val, user); 456 strcat (val, user);
321 } 457 }
322 } 458 }
323#endif 459# endif
324 mail_file = val; 460 mail_file = val;
325 if( mail_file ) 461 if (mail_file)
326 CheckMaildir(); 462 CheckMaildir ();
327#endif 463#endif
328 464
329 /* parse the command line */ 465 /* parse the command line */
330 for (i = 1; i < argc; i += 2) 466 for (i = 1; i < argc; i += 2)
331 { 467 {
332 opt = argv [i]; 468 opt = argv[i];
333 val = argv [i+1]; 469 val = argv[i + 1];
334 470
335 switch (*opt++) { 471 switch (*opt++)
336 case '-': 472 {
337 break; 473 case '-':
474 break;
338 475
339 case '#': 476 case '#':
340#ifdef ICONWIN 477#ifdef ICONWIN
341 rs_iconGeometry = opt; /* drop */ 478 rs_iconGeometry = opt; /* drop */
342#endif 479#endif
343 default: 480 default:
344 continue; 481 continue;
345 break; 482 break;
346 } 483 }
347 484
348 if (*opt == 'd' && val) display_name = val; /* "d", "display" */ 485 if (*opt == 'd' && val)
349 else if (*opt == 'g' && val) rs_geometry = val; /* "g", "geometry" */ 486 display_name = val; /* "d", "display" */
487 else if (*opt == 'g' && val)
488 rs_geometry = val; /* "g", "geometry" */
350#ifdef ICONWIN 489#ifdef ICONWIN
351 else if (*opt == 'i') /* "ic", "iconic" */ 490 else if (*opt == 'i') /* "ic", "iconic" */
352 { 491 {
353 iconic_state = IconicState; 492 iconic_state = IconicState;
354 i--; /* no argument */ 493 i--; /* no argument */
355 } 494 }
356#endif 495#endif
357 else if (!strcmp (opt, "fg") && val) rs_color [fgColor] = val; 496 else if (!strcmp (opt, "fg") && val)
358 else if (!strcmp (opt, "bg") && val) rs_color [bgColor] = val; 497 rs_color[fgColor] = val;
498 else if (!strcmp (opt, "bg") && val)
499 rs_color[bgColor] = val;
359#ifdef REMINDERS 500#ifdef REMINDERS
360 else if (!strcmp (opt, "fn") && val) rs_font = val; 501 else if (!strcmp (opt, "fn") && val)
502 rs_font = val;
361#ifdef DATE_ON_CLOCK_FACE 503# ifdef DATE_ON_CLOCK_FACE
362 else if (!strcmp (opt, "nodate")) 504 else if (!strcmp (opt, "nodate"))
363 { 505 {
364 show_date = 0; 506 show_date = 0;
365 i--; /* no argument */ 507 i--; /* no argument */
366 } 508 }
367#endif 509# endif
368#endif 510#endif
369 else if (!strcmp (opt, "update") && val) 511 else if (!strcmp (opt, "update") && val)
370 { 512 {
371 int x = atoi (val); 513 int x = atoi (val);
514
372 if (x < 1 || x > 60) 515 if (x < 1 || x > 60)
373 print_error ("update: %d sec", clockUpdate); 516 print_error ("update: %d sec", clockUpdate);
374 else 517 else
375 clockUpdate = x; 518 clockUpdate = x;
376 } 519 }
377#ifdef MAIL 520#ifdef MAIL
378 else if (!strcmp (opt, "mail") && val) 521 else if (!strcmp (opt, "mail") && val)
379 { 522 {
380 int x = atoi (val); 523 int x = atoi (val);
524
381 if (x < 1) 525 if (x < 1)
382 print_error ("mail update: %d sec", mailUpdate); 526 print_error ("mail update: %d sec", mailUpdate);
383 else 527 else
384 mailUpdate = x; 528 mailUpdate = x;
385 } 529 }
386 else if (!strcmp (opt, "mailfile") && val) 530 else if (!strcmp (opt, "mailfile") && val)
387 { 531 {
388 /* If the mail environment is not set, then mail_file was created 532 /* If the mail environment is not set, then mail_file was created
389 * with a malloc. We need to free it. 533 * with a malloc. We need to free it.
390 */ 534 */
391 if( getenv ("MAIL") == NULL) 535 if (getenv ("MAIL") == NULL)
392 free( mail_file); 536 free (mail_file);
393 /* assume user knows what he's doing, don't check that file is valid...*/ 537 /* assume user knows what he's doing, don't check that file is valid... */
394 mail_file = val; 538 mail_file = val;
395 } 539 }
396#ifndef MAIL_SPAWN 540# ifndef MAIL_SPAWN
397 else if (!strcmp (opt, "mailspawn") && val) 541 else if (!strcmp (opt, "mailspawn") && val)
398 { 542 {
399 mail_spawn = val; 543 mail_spawn = val;
400 } 544 }
401#endif 545# endif
402#endif /* MAIL */ 546#endif /* MAIL */
403#ifdef ADJUST_TIME 547#ifdef ADJUST_TIME
404 else if (!strcmp (opt, "adjust") && val) 548 else if (!strcmp (opt, "adjust") && val)
405 { 549 {
406 /* convert ddhhmm to seconds, minimal error checking */ 550 /* convert ddhhmm to seconds, minimal error checking */
407 int x = atoi (val); 551 int x = atoi (val);
552
408 adjustTime = ((((abs (x) / 10000) % 100) * 24 /* days */ 553 adjustTime = ((((abs (x) / 10000) % 100) * 24 /* days */
409 + ((abs (x) / 100) % 100)) * 60 /* hours */ 554 + ((abs (x) / 100) % 100)) * 60 /* hours */
410 + (abs (x) % 100)) * 60; /* minutes */ 555 + (abs (x) % 100)) * 60; /* minutes */
411 if (x < 0) 556 if (x < 0)
412 adjustTime = -adjustTime; 557 adjustTime = -adjustTime;
413 } 558 }
414#endif /* ADJUST_TIME */ 559#endif /* ADJUST_TIME */
415 else 560 else
416 { 561 {
417 usage (); 562 usage ();
418 goto Abort; 563 goto Abort;
419 } 564 }
420 } 565 }
421 566
422 /* open display */ 567 /* open display */
423 Xdisplay = XOpenDisplay (display_name); 568 Xdisplay = XOpenDisplay (display_name);
424 if (!Xdisplay) 569 if (!Xdisplay)
425 { 570 {
426 print_error ("can't open display %s", display_name?display_name: 571 print_error ("can't open display %s", display_name ? display_name :
427 getenv("DISPLAY")?getenv("DISPLAY"): 572 getenv ("DISPLAY") ? getenv ("DISPLAY") : "as no -d given and DISPLAY not set");
428 "as no -d given and DISPLAY not set");
429 goto Abort; 573 goto Abort;
430 } 574 }
431 575
432 /* get display info */ 576 /* get display info */
433 Xfd = XConnectionNumber (Xdisplay); 577 Xfd = XConnectionNumber (Xdisplay);
434 { 578 {
435 const char * const color_msg = "can't load color \"%s\""; 579 const char *const color_msg = "can't load color \"%s\"";
436 XColor xcol; 580 XColor xcol;
437 581
438 /* allocate foreground/background colors */ 582 /* allocate foreground/background colors */
439 if (!XParseColor (Xdisplay, Xcmap, rs_color [fgColor], &xcol) || 583 if (!XParseColor (Xdisplay, Xcmap, rs_color[fgColor], &xcol) || !XAllocColor (Xdisplay, Xcmap, &xcol))
440 !XAllocColor (Xdisplay, Xcmap, &xcol)) 584 {
441 {
442 print_error (color_msg, rs_color [fgColor]); 585 print_error (color_msg, rs_color[fgColor]);
443 goto Abort; 586 goto Abort;
444 } 587 }
445 PixColors [fgColor] = xcol.pixel; 588 PixColors[fgColor] = xcol.pixel;
446 589
447 if (!XParseColor (Xdisplay, Xcmap, rs_color [bgColor], &xcol) || 590 if (!XParseColor (Xdisplay, Xcmap, rs_color[bgColor], &xcol) || !XAllocColor (Xdisplay, Xcmap, &xcol))
448 !XAllocColor (Xdisplay, Xcmap, &xcol)) 591 {
449 {
450 print_error (color_msg, rs_color [bgColor]); 592 print_error (color_msg, rs_color[bgColor]);
451 goto Abort; 593 goto Abort;
452 }
453 PixColors [bgColor] = xcol.pixel;
454 } 594 }
595 PixColors[bgColor] = xcol.pixel;
596 }
455 597
456#ifdef REMINDERS 598#ifdef REMINDERS
457 /* load the font for messages */ 599 /* load the font for messages */
458 if ((Xfont = XLoadQueryFont (Xdisplay, rs_font)) == NULL) 600 if ((Xfont = XLoadQueryFont (Xdisplay, rs_font)) == NULL)
459 { 601 {
460 print_error ("can't load font \"%s\"", rs_font); 602 print_error ("can't load font \"%s\"", rs_font);
461 goto Abort; 603 goto Abort;
462 } 604 }
463 gcv.font = Xfont->fid; 605 gcv.font = Xfont->fid;
464#endif 606#endif
465 607
466 Create_Windows (argc, argv); 608 Create_Windows (argc, argv);
467 /* Create the graphics contexts */ 609 /* Create the graphics contexts */
468 gcv.foreground = PixColors [fgColor]; 610 gcv.foreground = PixColors[fgColor];
469 gcv.background = PixColors [bgColor]; 611 gcv.background = PixColors[bgColor];
470 612
471 Xgc = XCreateGC (Xdisplay, Clock.win, 613 Xgc = XCreateGC (Xdisplay, Clock.win,
472#ifdef REMINDERS 614#ifdef REMINDERS
473 GCFont | 615 GCFont |
474#endif 616#endif
475 GCForeground | GCBackground, &gcv); 617 GCForeground | GCBackground, &gcv);
476 618
477 gcv.foreground = PixColors [bgColor]; 619 gcv.foreground = PixColors[bgColor];
478 gcv.background = PixColors [fgColor]; 620 gcv.background = PixColors[fgColor];
479 Xrvgc = XCreateGC (Xdisplay, Clock.win, 621 Xrvgc = XCreateGC (Xdisplay, Clock.win,
480#ifdef REMINDERS 622#ifdef REMINDERS
481 GCFont | 623 GCFont |
482#endif 624#endif
483 GCForeground | GCBackground, &gcv); 625 GCForeground | GCBackground, &gcv);
484 626
485 getXevent (); 627 getXevent ();
486 return EXIT_SUCCESS; 628 return EXIT_SUCCESS;
487 629
488 Malloc_Error: 630Malloc_Error:
489 print_error ("malloc error"); 631 print_error ("malloc error");
490 Abort: 632Abort:
491 print_error ("aborting"); 633 print_error ("aborting");
492 return EXIT_FAILURE; 634 return EXIT_FAILURE;
493} 635}
494 636
495/* 637/*
496 * translate geometry string to appropriate sizehint 638 * translate geometry string to appropriate sizehint
497 */ 639 */
498static void 640static void
499geometry2sizehint (mywindow_t * win, const char * geom) 641geometry2sizehint (mywindow_t * win, const char *geom)
500{ 642{
501 int x, y, flags; 643 int x, y, flags;
502 unsigned int width, height; 644 unsigned int width, height;
503 645
504 /* copy in values */ 646 /* copy in values */
505 szHint.width = win->width; 647 szHint.width = win->width;
506 szHint.height = win->height; 648 szHint.height = win->height;
507 649
508 if (geom == NULL) 650 if (geom == NULL)
509 return; 651 return;
510 652
511 flags = XParseGeometry (geom, &x, &y, &width, &height); 653 flags = XParseGeometry (geom, &x, &y, &width, &height);
512 654
513 if (flags & WidthValue) 655 if (flags & WidthValue)
514 { 656 {
515 szHint.width = width + szHint.base_width; 657 szHint.width = width + szHint.base_width;
516 szHint.flags |= USSize; 658 szHint.flags |= USSize;
517 } 659 }
518 if (flags & HeightValue) 660 if (flags & HeightValue)
519 { 661 {
520 szHint.height = height + szHint.base_height; 662 szHint.height = height + szHint.base_height;
521 szHint.flags |= USSize; 663 szHint.flags |= USSize;
522 } 664 }
523 665
524 if (flags & XValue) 666 if (flags & XValue)
525 { 667 {
526 if (flags & XNegative) 668 if (flags & XNegative)
527 { 669 {
528 x += (DisplayWidth (Xdisplay, Xscreen) - szHint.width); 670 x += (DisplayWidth (Xdisplay, Xscreen) - szHint.width);
529 szHint.win_gravity = NorthEastGravity; 671 szHint.win_gravity = NorthEastGravity;
530 } 672 }
531 szHint.x = x; 673 szHint.x = x;
532 szHint.flags |= USPosition; 674 szHint.flags |= USPosition;
533 } 675 }
534 if (flags & YValue) 676 if (flags & YValue)
535 { 677 {
536 if (flags & YNegative) 678 if (flags & YNegative)
537 { 679 {
538 y += (DisplayHeight (Xdisplay, Xscreen) - szHint.height); 680 y += (DisplayHeight (Xdisplay, Xscreen) - szHint.height);
539 szHint.win_gravity = (szHint.win_gravity == NorthEastGravity ? 681 szHint.win_gravity = (szHint.win_gravity == NorthEastGravity ? SouthEastGravity : SouthWestGravity);
540 SouthEastGravity : SouthWestGravity); 682 }
541 }
542 szHint.y = y; 683 szHint.y = y;
543 szHint.flags |= USPosition; 684 szHint.flags |= USPosition;
544 } 685 }
545 686
546 /* copy out values */ 687 /* copy out values */
547 win->width = szHint.width; 688 win->width = szHint.width;
548 win->height = szHint.height; 689 win->height = szHint.height;
549} 690}
550 691
551/* 692/*
552 * Open and map the windows 693 * Open and map the windows
553 */ 694 */
554static void 695static void
555Create_Windows (int argc, char * argv []) 696Create_Windows (int argc, char *argv[])
556{ 697{
557 XClassHint classHint; 698 XClassHint classHint;
558 XWMHints wmHint; 699 XWMHints wmHint;
559 700
560 geometry2sizehint (&Clock, rs_geometry); 701 geometry2sizehint (&Clock, rs_geometry);
561 Clock.win = XCreateSimpleWindow (Xdisplay, Xroot, 702 Clock.win = XCreateSimpleWindow (Xdisplay, Xroot,
562 szHint.x, szHint.y, 703 szHint.x, szHint.y, Clock.width, Clock.height, 0, PixColors[fgColor], PixColors[bgColor]);
563 Clock.width, Clock.height,
564 0,
565 PixColors [fgColor],
566 PixColors [bgColor]);
567 704
568#ifdef ICONWIN 705#ifdef ICONWIN
569 geometry2sizehint (&Icon, rs_iconGeometry); 706 geometry2sizehint (&Icon, rs_iconGeometry);
570 Icon.win = XCreateSimpleWindow (Xdisplay, Xroot, 707 Icon.win = XCreateSimpleWindow (Xdisplay, Xroot, szHint.x, szHint.y, Icon.width, Icon.height, 0, PixColors[fgColor], PixColors[bgColor]);
571 szHint.x, szHint.y,
572 Icon.width, Icon.height,
573 0,
574 PixColors [fgColor],
575 PixColors [bgColor]);
576 wmHint.initial_state = iconic_state; 708 wmHint.initial_state = iconic_state;
577 wmHint.icon_window = Icon.win; 709 wmHint.icon_window = Icon.win;
578 wmHint.flags = InputHint | StateHint | IconWindowHint; 710 wmHint.flags = InputHint | StateHint | IconWindowHint;
579#else 711#else
580 wmHint.flags = InputHint; 712 wmHint.flags = InputHint;
581#endif 713#endif
582 wmHint.input = True; 714 wmHint.input = True;
583 715
584 /* ignore warning about discarded `const' */
585 classHint.res_name = APL_NAME; 716 classHint.res_name = (char *)APL_NAME;
586 classHint.res_class = APL_CLASS; 717 classHint.res_class = (char *)APL_CLASS;
587 XSetWMProperties (Xdisplay, Clock.win, NULL, NULL, argv, argc, 718 XSetWMProperties (Xdisplay, Clock.win, NULL, NULL, argv, argc, &szHint, &wmHint, &classHint);
588 &szHint, &wmHint, &classHint);
589 719
590 XSelectInput (Xdisplay, Clock.win, 720 XSelectInput (Xdisplay, Clock.win, (ExposureMask | StructureNotifyMask | ButtonPressMask));
591 (ExposureMask|StructureNotifyMask|ButtonPressMask));
592 721
593#ifdef ICONWIN 722#ifdef ICONWIN
594 XSelectInput (Xdisplay, Icon.win, 723 XSelectInput (Xdisplay, Icon.win, (ExposureMask | ButtonPressMask));
595 (ExposureMask|ButtonPressMask));
596#endif 724#endif
597 XMapWindow (Xdisplay, Clock.win); 725 XMapWindow (Xdisplay, Clock.win);
598 726
599 /* create, but don't map a window for appointment reminders */ 727 /* create, but don't map a window for appointment reminders */
600#ifdef REMINDERS 728#ifdef REMINDERS
601 Msg.win = XCreateSimpleWindow (Xdisplay, Xroot, 729 Msg.win = XCreateSimpleWindow (Xdisplay, Xroot,
602 szHint.x, szHint.y, 730 szHint.x, szHint.y, szHint.width, szHint.height, 0, PixColors[fgColor], PixColors[bgColor]);
603 szHint.width, szHint.height,
604 0,
605 PixColors [fgColor],
606 PixColors [bgColor]);
607 731
608 szHint.flags |= USPosition; 732 szHint.flags |= USPosition;
609 /* ignore warning about discarded `const' */ 733 /* ignore warning about discarded `const' */
610 classHint.res_name = MSG_NAME; 734 classHint.res_name = (char *)MSG_NAME;
611 classHint.res_class = MSG_CLASS; 735 classHint.res_class = (char *)MSG_CLASS;
612 wmHint.input = True; 736 wmHint.input = True;
613 wmHint.flags = InputHint; 737 wmHint.flags = InputHint;
614 738
615 XSetWMProperties (Xdisplay, Msg.win, NULL, NULL, argv, argc, 739 XSetWMProperties (Xdisplay, Msg.win, NULL, NULL, argv, argc, &szHint, &wmHint, &classHint);
616 &szHint, &wmHint, &classHint); 740
617 { 741 {
618 char * str = MSG_NAME; 742 const char *str = MSG_NAME;
743
619 XStoreName (Xdisplay, Msg.win, str); 744 XStoreName (Xdisplay, Msg.win, str);
620 XSetIconName (Xdisplay, Msg.win, str); 745 XSetIconName (Xdisplay, Msg.win, str);
621 } 746 }
622 747
623 XSelectInput (Xdisplay, Msg.win, 748 XSelectInput (Xdisplay, Msg.win, (ExposureMask | ButtonPressMask | KeyPressMask));
624 (ExposureMask|ButtonPressMask|KeyPressMask));
625 749
626 /* font already loaded */ 750 /* font already loaded */
627 751
628 msgButton.width = 4 + 5 * XTextWidth (Xfont, "M", 1); 752 msgButton.width = 4 + 5 * XTextWidth (Xfont, "M", 1);
629 msgButton.height = 4 + FontHeight (); 753 msgButton.height = 4 + FontHeight ();
630 754
631 msgButton.Dismiss = XCreateSimpleWindow (Xdisplay, Msg.win, 755 msgButton.Dismiss = XCreateSimpleWindow (Xdisplay, Msg.win,
632 0, 0, 756 0, 0, msgButton.width, msgButton.height, 0, PixColors[bgColor], PixColors[fgColor]);
633 msgButton.width, msgButton.height,
634 0,
635 PixColors [bgColor],
636 PixColors [fgColor]);
637 757
638 XMapWindow (Xdisplay, msgButton.Dismiss); 758 XMapWindow (Xdisplay, msgButton.Dismiss);
639 759
640 msgButton.Defer = XCreateSimpleWindow (Xdisplay, Msg.win, 760 msgButton.Defer = XCreateSimpleWindow (Xdisplay, Msg.win,
641 0, 0, 761 0, 0, msgButton.width, msgButton.height, 0, PixColors[bgColor], PixColors[fgColor]);
642 msgButton.width, msgButton.height,
643 0,
644 PixColors [bgColor],
645 PixColors [fgColor]);
646 XMapWindow (Xdisplay, msgButton.Defer); 762 XMapWindow (Xdisplay, msgButton.Defer);
647 763
648#ifndef NO_REMINDER_EXEC 764# ifndef NO_REMINDER_EXEC
649 msgButton.Start = XCreateSimpleWindow (Xdisplay, Msg.win, 765 msgButton.Start = XCreateSimpleWindow (Xdisplay, Msg.win,
650 0, 0, 766 0, 0, msgButton.width, msgButton.height, 0, PixColors[bgColor], PixColors[fgColor]);
651 msgButton.width, msgButton.height,
652 0,
653 PixColors [bgColor],
654 PixColors [fgColor]);
655 XMapWindow (Xdisplay, msgButton.Start); 767 XMapWindow (Xdisplay, msgButton.Start);
656#endif /* NO_REMINDER_EXEC */ 768# endif/* NO_REMINDER_EXEC */
657#endif 769#endif
658} 770}
659 771
660static time_t 772static time_t
661mk_time (struct tm * tmval) 773mk_time (struct tm *tmval)
662{ 774{
663 return (tmval->tm_min 775 return (tmval->tm_min + 60 * (tmval->tm_hour + 24 * (tmval->tm_mday + 31 * ((tmval->tm_mon + 1) + 12 * tmval->tm_year))));
664 + 60 * (tmval->tm_hour
665 + 24 * (tmval->tm_mday
666 + 31 * ((tmval->tm_mon+1)
667 + 12 * tmval->tm_year))));
668} 776}
669
670 777
671#ifdef MAIL 778#ifdef MAIL
672static int 779static int
673MailAvailable() 780MailAvailable ()
674{ 781{
675 struct stat st; 782 struct stat st;
676 783
677 if( is_maildir ) { 784 if (is_maildir)
678 DIR *dirp; 785 {
786 DIR *dirp;
679 struct dirent *d; 787 struct dirent *d;
680 788
681 if( (dirp=opendir( mail_file )) ) { 789 if ((dirp = opendir (mail_file)))
790 {
682 while( (d=readdir(dirp)) ) { 791 while ((d = readdir (dirp)))
683 if( *d->d_name == '.' ) 792 {
684 continue; 793 if (*d->d_name == '.')
685 if( isdigit(*d->d_name) ) { 794 continue;
795 if (isdigit (*d->d_name))
796 {
797 closedir (dirp);
798 return 1;
799 }
800 }
686 closedir(dirp); 801 closedir (dirp);
802 }
687 return 1; 803 return 0;
688 }
689 } 804 }
690 closedir(dirp);
691 }
692 return 0;
693 }
694 else 805 else
695 return !stat(mail_file, &st) && 806 return !stat (mail_file, &st) && (st.st_size > 0) && (st.st_mtime >= st.st_atime);
696 (st.st_size > 0) && (st.st_mtime >= st.st_atime);
697} 807}
698#endif 808#endif
699 809
700/*----------------------------------------------------------------------* 810/*----------------------------------------------------------------------*
701 * Redraw the whole window after an exposure or size change. 811 * Redraw the whole window after an exposure or size change.
703 * Provide reminder if needed. 813 * Provide reminder if needed.
704 *----------------------------------------------------------------------*/ 814 *----------------------------------------------------------------------*/
705static void 815static void
706Draw_Window (mywindow_t * W, int full_redraw) 816Draw_Window (mywindow_t * W, int full_redraw)
707{ 817{
708 /* pre-computed values for sin() x1000, to avoid using floats */
709 static const short Sin [720] = {
710 0,
711 9, 17, 26, 35, 44, 52, 61, 70, 78, 87, 96, 105,
712 113, 122, 131, 139, 148, 156, 165, 174, 182, 191, 199, 208,
713 216, 225, 233, 242, 250, 259, 267, 276, 284, 292, 301, 309,
714 317, 326, 334, 342, 350, 358, 367, 375, 383, 391, 399, 407,
715 415, 423, 431, 438, 446, 454, 462, 469, 477, 485, 492, 500,
716 508, 515, 522, 530, 537, 545, 552, 559, 566, 574, 581, 588,
717 595, 602, 609, 616, 623, 629, 636, 643, 649, 656, 663, 669,
718 676, 682, 688, 695, 701, 707, 713, 719, 725, 731, 737, 743,
719 749, 755, 760, 766, 772, 777, 783, 788, 793, 799, 804, 809,
720 814, 819, 824, 829, 834, 839, 843, 848, 853, 857, 862, 866,
721 870, 875, 879, 883, 887, 891, 895, 899, 903, 906, 910, 914,
722 917, 921, 924, 927, 930, 934, 937, 940, 943, 946, 948, 951,
723 954, 956, 959, 961, 964, 966, 968, 970, 972, 974, 976, 978,
724 980, 982, 983, 985, 986, 988, 989, 990, 991, 993, 994, 995,
725 995, 996, 997, 998, 998, 999, 999, 999, 1000, 1000, 1000, 1000,
726 1000, 1000, 1000, 999, 999, 999, 998, 998, 997, 996, 995, 995,
727 994, 993, 991, 990, 989, 988, 986, 985, 983, 982, 980, 978,
728 976, 974, 972, 970, 968, 966, 964, 961, 959, 956, 954, 951,
729 948, 946, 943, 940, 937, 934, 930, 927, 924, 921, 917, 914,
730 910, 906, 903, 899, 895, 891, 887, 883, 879, 875, 870, 866,
731 862, 857, 853, 848, 843, 839, 834, 829, 824, 819, 814, 809,
732 804, 799, 793, 788, 783, 777, 772, 766, 760, 755, 749, 743,
733 737, 731, 725, 719, 713, 707, 701, 695, 688, 682, 676, 669,
734 663, 656, 649, 643, 636, 629, 623, 616, 609, 602, 595, 588,
735 581, 574, 566, 559, 552, 545, 537, 530, 523, 515, 508, 500,
736 492, 485, 477, 469, 462, 454, 446, 438, 431, 423, 415, 407,
737 399, 391, 383, 375, 367, 358, 350, 342, 334, 326, 317, 309,
738 301, 292, 284, 276, 267, 259, 250, 242, 233, 225, 216, 208,
739 199, 191, 182, 174, 165, 156, 148, 139, 131, 122, 113, 105,
740 96, 87, 78, 70, 61, 52, 44, 35, 26, 17, 9, 0,
741 -9, -17, -26, -35, -44, -52, -61, -70, -78, -87, -96, -105,
742 -113, -122, -131, -139, -148, -156, -165, -174, -182, -191, -199, -208,
743 -216, -225, -233, -242, -250, -259, -267, -276, -284, -292, -301, -309,
744 -317, -326, -334, -342, -350, -358, -366, -375, -383, -391, -399, -407,
745 -415, -423, -431, -438, -446, -454, -462, -469, -477, -485, -492, -500,
746 -508, -515, -522, -530, -537, -545, -552, -559, -566, -574, -581, -588,
747 -595, -602, -609, -616, -623, -629, -636, -643, -649, -656, -663, -669,
748 -676, -682, -688, -695, -701, -707, -713, -719, -725, -731, -737, -743,
749 -749, -755, -760, -766, -772, -777, -783, -788, -793, -799, -804, -809,
750 -814, -819, -824, -829, -834, -839, -843, -848, -853, -857, -862, -866,
751 -870, -875, -879, -883, -887, -891, -895, -899, -903, -906, -910, -914,
752 -917, -921, -924, -927, -930, -934, -937, -940, -943, -946, -948, -951,
753 -954, -956, -959, -961, -964, -966, -968, -970, -972, -974, -976, -978,
754 -980, -982, -983, -985, -986, -988, -989, -990, -991, -993, -994, -995,
755 -995, -996, -997, -998, -998, -999, -999, -999, -1000, -1000, -1000, -1000,
756 -1000, -1000, -1000, -999, -999, -999, -998, -998, -997, -996, -995, -995,
757 -994, -993, -991, -990, -989, -988, -986, -985, -983, -982, -980, -978,
758 -976, -974, -972, -970, -968, -966, -964, -961, -959, -956, -954, -951,
759 -948, -946, -943, -940, -937, -934, -930, -927, -924, -921, -917, -914,
760 -910, -906, -903, -899, -895, -891, -887, -883, -879, -875, -870, -866,
761 -862, -857, -853, -848, -843, -839, -834, -829, -824, -819, -814, -809,
762 -804, -799, -793, -788, -783, -777, -772, -766, -760, -755, -749, -743,
763 -737, -731, -725, -719, -713, -707, -701, -695, -688, -682, -676, -669,
764 -663, -656, -649, -643, -636, -629, -623, -616, -609, -602, -595, -588,
765 -581, -574, -566, -559, -552, -545, -537, -530, -523, -515, -508, -500,
766 -492, -485, -477, -469, -462, -454, -446, -438, -431, -423, -415, -407,
767 -399, -391, -383, -375, -367, -358, -350, -342, -334, -326, -317, -309,
768 -301, -292, -284, -276, -267, -259, -250, -242, -233, -225, -216, -208,
769 -199, -191, -182, -174, -165, -156, -148, -139, -131, -122, -113, -105,
770 -96, -87, -78, -70, -61, -52, -44, -35, -26, -17, -9,
771 };
772
773 static int savedDay = -1; 818 static int savedDay = -1;
774 819
775 time_t currentTime; 820 time_t currentTime;
776 struct tm * tmval; 821 struct tm *tmval;
777 int ctr_x, ctr_y; 822 int ctr_x, ctr_y;
778 823
779 typedef struct { 824 typedef struct
780 int h_x, h_y; /* hour */ 825 {
826 int h_x, h_y; /* hour */
781 int m_x, m_y; /* minute */ 827 int m_x, m_y; /* minute */
782 int s_x, s_y; /* second */ 828 int s_x, s_y; /* second */
783 } hands_t; /* hand positions (x,y) */ 829 } hands_t; /* hand positions (x,y) */
784 830
785 hands_t HandsNow, * pHandsOld; 831 hands_t HandsNow, *pHandsOld;
786 832
787 GC X_gc, X_rvgc; 833 GC X_gc, X_rvgc;
788 834
789 static hands_t HandsOld = { -1 }; 835 static hands_t HandsOld = { -1 };
790#ifdef ICONWIN 836#ifdef ICONWIN
791 static hands_t HandsOld_icon = { -1 }; 837 static hands_t HandsOld_icon = { -1 };
792#endif 838#endif
793#ifdef REMINDERS 839#ifdef REMINDERS
794 static int lastUpdateTime = -10; 840 static int lastUpdateTime = -10;
795#endif 841#endif
796 842
797#ifdef MAIL 843#ifdef MAIL
798 static time_t mailTime = 0; 844 static time_t mailTime = 0;
799 static int MailUp = 0, MailUp_rvideo = 0; 845 static int MailUp = 0, MailUp_rvideo = 0;
846
847# ifdef ICONWIN
848 static int MailUp_icon = 0;
849# endif
850#endif /* MAIL */
851
852 currentTime = time (NULL) + adjustTime; /* get the current time */
853 tmval = localtime (&currentTime);
854
855#ifdef MAIL
856# ifdef REMINDERS
857 if (W->win != Msg.win)
858# endif
859 {
860 int *pMailUp = (
861# ifdef ICONWIN
862 W->win == Icon.win ? &MailUp_icon :
863# endif
864 &MailUp);
865
866 if ((currentTime - mailTime) >= mailUpdate)
867 {
868 if (
869# ifdef ICONWIN
870 MailUp != MailUp_icon ? MailUp :
871# endif
872 ((mail_file != NULL) && MailAvailable ()))
873 {
874 if (!*pMailUp)
875 {
876 *pMailUp = 1;
877 full_redraw = 1;
878 XSetWindowBackground (Xdisplay, W->win, PixColors[fgColor]);
879# ifdef MAIL_BELL
880 XBell (Xdisplay, 0);
881# endif
882 }
883 }
884 else
885 {
886 if (*pMailUp)
887 {
888 *pMailUp = 0;
889 full_redraw = 1;
890 XSetWindowBackground (Xdisplay, W->win, PixColors[bgColor]);
891 }
892 }
893# ifdef ICONWIN
894 if (MailUp == MailUp_icon)
895# endif
896 mailTime = currentTime;
897
898 MailUp_rvideo = *pMailUp;
899 }
900 }
901#endif /* MAIL */
902
903 /* once every day, update the window and icon name */
904 if (tmval->tm_yday != savedDay)
905 {
906 char str[20];
907
908 savedDay = tmval->tm_yday;
909 strftime (str, sizeof (str), "%a %h %d", tmval);
910 XStoreName (Xdisplay, Clock.win, str);
911 XSetIconName (Xdisplay, Clock.win, str);
912 }
913
914 if (full_redraw)
915 XClearWindow (Xdisplay, W->win);
916
917#ifdef REMINDERS
918 /* for a message window, just re-draw the message */
919 if (W->win == Msg.win)
920 {
921 char *beg, *next;
922 int lines;
923
924 for (beg = message, lines = 0; beg; beg = next, lines++)
925 {
926 char *end;
927
928 if ((end = strstr (beg, "\\n")) == NULL)
929 {
930 end = beg + strlen (beg);
931 next = NULL;
932 }
933 else
934 {
935 next = end + 2;
936 }
937
938 XDrawString (Xdisplay, Msg.win,
939 Xgc,
940 (Msg.width -
941 XTextWidth (Xfont, beg, (end - beg))) / 2, 10 + Xfont->ascent + FontHeight () * lines, beg, (end - beg));
942 }
943
944 XDrawString (Xdisplay, msgButton.Dismiss, Xrvgc, (msgButton.width - XTextWidth (Xfont, "Done", 4)) / 2, Xfont->ascent + 2, "Done", 4);
945
946 XDrawString (Xdisplay, msgButton.Defer, Xrvgc, (msgButton.width - XTextWidth (Xfont, "Defer", 5)) / 2, Xfont->ascent + 2, "Defer", 5);
947
948# ifndef NO_REMINDER_EXEC
949 XDrawString (Xdisplay, msgButton.Start, Xrvgc, (msgButton.width - XTextWidth (Xfont, "Start", 5)) / 2, Xfont->ascent + 2, "Start", 5);
950
951 if (strlen (execPrgm) > 1)
952 XMapWindow (Xdisplay, msgButton.Start);
953 else
954 XUnmapWindow (Xdisplay, msgButton.Start);
955# endif /* NO_REMINDER_EXEC */
956 return;
957 }
958
959 /*
960 * Convert multi-field time info to a single integer with a resolution
961 * in minutes.
962 */
963 currentTime = mk_time (tmval);
964
965 /* is there a reminder pending? */
966 if (reminderTime >= 0 && currentTime >= reminderTime)
967 Reminder ();
968
969 /* every 10 minutes, or at start of day, check for revised entries */
970 if (!Msg_Mapped &&
971 (currentTime > lastUpdateTime + REMINDERS_TIME || (currentTime != lastUpdateTime && tmval->tm_hour == 0 && tmval->tm_min == 0)))
972 {
973 Next_Reminder (UPDATE);
974 lastUpdateTime = currentTime;
975 }
976#endif
977
978 /*
979 * draw clock
980 */
981
982 ctr_x = W->width / 2;
983 ctr_y = W->height / 2;
984
985#define XPOS(i,val) (ctr_x + (W->width * Sin (i ) + 4096) / (819200 / (val)))
986#define YPOS(i,val) (ctr_y - (W->height * Sin (i + 180) + 4096) / (819200 / (val)))
987 /*
988 * how to draw the clock face
989 */
990
991 /* calculate the positions of the hands */
992 {
993 int angle = (tmval->tm_hour % 12) * 60 + tmval->tm_min;
994
995 HandsNow.h_x = XPOS (angle, 60);
996 HandsNow.h_y = YPOS (angle, 60);
997 }
998 {
999 int angle = (tmval->tm_min * 12);
1000
1001 HandsNow.m_x = XPOS (angle, 80);
1002 HandsNow.m_y = YPOS (angle, 80);
1003 }
1004 if (clockUpdate == 1)
1005 {
1006 int angle = (tmval->tm_sec * 12);
1007
1008 HandsNow.s_x = XPOS (angle, 85);
1009 HandsNow.s_y = YPOS (angle, 85);
1010 }
1011
1012 pHandsOld = (
800#ifdef ICONWIN 1013#ifdef ICONWIN
801 static int MailUp_icon = 0; 1014 W->win == Icon.win ? &HandsOld_icon :
802#endif 1015#endif
803#endif /* MAIL */ 1016 &HandsOld);
804
805 currentTime = time (NULL) + adjustTime; /* get the current time */
806 tmval = localtime (&currentTime);
807 1017
808#ifdef MAIL 1018#ifdef MAIL
1019 if (MailUp_rvideo)
1020 {
1021 X_gc = Xrvgc;
1022 X_rvgc = Xgc;
1023 }
1024 else
1025#endif
1026 {
1027 X_gc = Xgc;
1028 X_rvgc = Xrvgc;
1029 }
1030
1031 /*
1032 * Draw the date in the lower half of the clock window.
1033 * The code is enclosed in REMINDERS because it uses the same
1034 * font as the reminders code.
1035 * I believe this should be drawn always so it does not get
1036 * "swept away" by the minute hand.
1037 */
1038#if defined(REMINDERS) && defined(DATE_ON_CLOCK_FACE)
1039 if (show_date)
1040 {
1041 char date[10];
1042
1043 currentTime = time (NULL) + adjustTime; /* get the current time */
1044 tmval = localtime (&currentTime);
1045 strftime (date, sizeof (date), "%d", tmval);
1046 XDrawString (Xdisplay, W->win, X_gc,
1047 ctr_x - XTextWidth (Xfont, date, strlen (date)) / 2,
1048 ctr_y + FontHeight () + (ctr_y - FontHeight ()) / 2, date, strlen (date));
1049 }
1050#endif
1051
1052 if (full_redraw)
1053 {
1054 int mintick;
1055
1056 /*
1057 * draw clock face
1058 */
1059#ifdef SUBTICKS
1060 for (mintick = 0; mintick < 60; mintick++)
1061 XDrawPoint (Xdisplay, W->win, X_gc, XPOS ((mintick * 12), 95), YPOS ((mintick * 12), 95));
1062#endif
1063 for (mintick = 0; mintick < 60; mintick += 5)
1064 XDrawLine (Xdisplay, W->win, X_gc,
1065 XPOS ((mintick * 12), 90), YPOS ((mintick * 12), 90), XPOS ((mintick * 12), 100), YPOS ((mintick * 12), 100));
1066 }
1067 else if (memcmp (pHandsOld, &HandsNow, sizeof (hands_t)))
1068 {
1069 int i, j;
1070
1071 /*
1072 * erase old hands
1073 */
1074 for (i = -1; i < 2; i++)
1075 for (j = -1; j < 2; j++)
1076 {
1077 /* hour/minute hands */
1078 XDrawLine (Xdisplay, W->win, X_rvgc, ctr_x + i, ctr_y + j, pHandsOld->h_x, pHandsOld->h_y);
1079 XDrawLine (Xdisplay, W->win, X_rvgc, ctr_x + i, ctr_y + j, pHandsOld->m_x, pHandsOld->m_y);
1080 }
1081
1082 if (clockUpdate == 1) /* seconds hand */
1083 XDrawLine (Xdisplay, W->win, X_rvgc, ctr_x, ctr_y, pHandsOld->s_x, pHandsOld->s_y);
1084 }
1085
1086 if (full_redraw || memcmp (pHandsOld, &HandsNow, sizeof (hands_t)))
1087 {
1088 int i, j;
1089
1090 /*
1091 * draw new hands
1092 */
1093 for (i = -1; i < 2; i++)
1094 for (j = -1; j < 2; j++)
1095 {
1096 /* hour/minute hands */
1097 XDrawLine (Xdisplay, W->win, X_gc, ctr_x + i, ctr_y + j, HandsNow.h_x, HandsNow.h_y);
1098
1099 XDrawLine (Xdisplay, W->win, X_gc, ctr_x + i, ctr_y + j, HandsNow.m_x, HandsNow.m_y);
1100 }
1101 if (clockUpdate == 1) /* seconds hand */
1102 XDrawLine (Xdisplay, W->win, X_gc, ctr_x, ctr_y, HandsNow.s_x, HandsNow.s_y);
1103
1104 *pHandsOld = HandsNow;
1105 }
1106}
1107
809#ifdef REMINDERS 1108#ifdef REMINDERS
810 if (W->win != Msg.win)
811#endif
812 {
813 int * pMailUp = (
814#ifdef ICONWIN
815 W->win == Icon.win ? &MailUp_icon :
816#endif
817 &MailUp);
818 1109
819 if ((currentTime - mailTime) >= mailUpdate)
820 {
821 struct stat st;
822
823 if (
824#ifdef ICONWIN
825 MailUp != MailUp_icon ? MailUp :
826#endif
827 ((mail_file != NULL) && MailAvailable() ) )
828 {
829 if (!*pMailUp)
830 {
831 *pMailUp = 1;
832 full_redraw = 1;
833 XSetWindowBackground (Xdisplay, W->win,
834 PixColors [fgColor]);
835#ifdef MAIL_BELL
836 XBell (Xdisplay, 0);
837#endif
838 }
839 }
840 else
841 {
842 if (*pMailUp)
843 {
844 *pMailUp = 0;
845 full_redraw = 1;
846 XSetWindowBackground (Xdisplay, W->win,
847 PixColors [bgColor]);
848 }
849 }
850#ifdef ICONWIN
851 if (MailUp == MailUp_icon)
852#endif
853 mailTime = currentTime;
854
855 MailUp_rvideo = *pMailUp;
856 }
857 }
858#endif /* MAIL */
859
860 /* once every day, update the window and icon name */
861 if (tmval->tm_yday != savedDay)
862 {
863 char str [20];
864
865 savedDay = tmval->tm_yday;
866 strftime (str, sizeof(str), "%a %h %d", tmval);
867 XStoreName (Xdisplay, Clock.win, str);
868 XSetIconName (Xdisplay, Clock.win, str);
869 }
870
871 if (full_redraw)
872 XClearWindow (Xdisplay, W->win);
873
874#ifdef REMINDERS
875 /* for a message window, just re-draw the message */
876 if (W->win == Msg.win)
877 {
878 char * beg, * next;
879 int lines;
880
881 for (beg = message, lines = 0; beg; beg = next, lines++)
882 {
883 char * end;
884
885 if ((end = strstr (beg, "\\n")) == NULL)
886 {
887 end = beg + strlen (beg);
888 next = NULL;
889 }
890 else
891 {
892 next = end + 2;
893 }
894
895 XDrawString (Xdisplay, Msg.win,
896 Xgc,
897 (Msg.width -
898 XTextWidth (Xfont, beg, (end-beg))) / 2,
899 10 + Xfont->ascent + FontHeight () * lines,
900 beg, (end-beg));
901 }
902
903 XDrawString (Xdisplay, msgButton.Dismiss,
904 Xrvgc,
905 (msgButton.width - XTextWidth (Xfont, "Done", 4)) / 2,
906 Xfont->ascent + 2,
907 "Done", 4);
908
909 XDrawString (Xdisplay, msgButton.Defer,
910 Xrvgc,
911 (msgButton.width - XTextWidth (Xfont, "Defer", 5)) / 2,
912 Xfont->ascent + 2,
913 "Defer", 5);
914
915# ifndef NO_REMINDER_EXEC
916 XDrawString (Xdisplay, msgButton.Start,
917 Xrvgc,
918 (msgButton.width - XTextWidth (Xfont, "Start", 5)) / 2,
919 Xfont->ascent + 2,
920 "Start", 5);
921
922 if (strlen (execPrgm) > 1)
923 XMapWindow (Xdisplay, msgButton.Start);
924 else
925 XUnmapWindow (Xdisplay, msgButton.Start);
926# endif /* NO_REMINDER_EXEC */
927 return;
928 }
929
930 /*
931 * Convert multi-field time info to a single integer with a resolution
932 * in minutes.
933 */
934 currentTime = mk_time (tmval);
935
936 /* is there a reminder pending? */
937 if (reminderTime >= 0 && currentTime >= reminderTime)
938 Reminder ();
939
940 /* every 10 minutes, or at start of day, check for revised entries */
941 if (!Msg_Mapped &&
942 (currentTime > lastUpdateTime + REMINDERS_TIME ||
943 (currentTime != lastUpdateTime &&
944 tmval->tm_hour == 0 && tmval->tm_min == 0)))
945 {
946 Next_Reminder (UPDATE);
947 lastUpdateTime = currentTime;
948 }
949#endif
950
951 /*
952 * draw clock
953 */
954
955 ctr_x = (W->width / 2);
956 ctr_y = (W->height / 2);
957
958#define XPOS(i,val) (ctr_x + (W->width * Sin[i%720] * (val) + 100000) / 200000)
959#define YPOS(i,val) (ctr_y - (W->height * Sin[(i+180)%720] * (val) + 100000) / 200000)
960 /*
961 * how to draw the clock face
962 */
963
964 /* calculate the positions of the hands */
965 {
966 int angle = (tmval->tm_hour % 12) * 60 + tmval->tm_min;
967 HandsNow.h_x = XPOS (angle, 60);
968 HandsNow.h_y = YPOS (angle, 60);
969 }
970 {
971 int angle = (tmval->tm_min * 12);
972 HandsNow.m_x = XPOS (angle, 80);
973 HandsNow.m_y = YPOS (angle, 80);
974 }
975 if (clockUpdate == 1)
976 {
977 int angle = (tmval->tm_sec * 12);
978 HandsNow.s_x = XPOS (angle, 85);
979 HandsNow.s_y = YPOS (angle, 85);
980 }
981
982 pHandsOld = (
983#ifdef ICONWIN
984 W->win == Icon.win ? &HandsOld_icon :
985#endif
986 &HandsOld);
987
988#ifdef MAIL
989 if (MailUp_rvideo)
990 {
991 X_gc = Xrvgc;
992 X_rvgc = Xgc;
993 }
994 else
995#endif
996 {
997 X_gc = Xgc;
998 X_rvgc = Xrvgc;
999 }
1000
1001 /*
1002 * Draw the date in the lower half of the clock window.
1003 * The code is enclosed in REMINDERS because it uses the same
1004 * font as the reminders code.
1005 * I believe this should be drawn always so it does not get
1006 * "swept away" by the minute hand.
1007 */
1008#if defined(REMINDERS) && defined(DATE_ON_CLOCK_FACE)
1009 if( show_date)
1010 {
1011 char date[10];
1012 currentTime = time (NULL) + adjustTime; /* get the current time */
1013 tmval = localtime (&currentTime);
1014 strftime (date, sizeof(date), "%d", tmval);
1015 XDrawString (Xdisplay, W->win, X_gc,
1016 ctr_x - XTextWidth(Xfont, date, strlen(date))/2,
1017 ctr_y + FontHeight() + (ctr_y - FontHeight())/2,
1018 date, strlen(date));
1019 }
1020#endif
1021
1022 if (full_redraw)
1023 {
1024 int mintick;
1025 /*
1026 * draw clock face
1027 */
1028#ifdef SUBTICKS
1029 for (mintick = 0; mintick < 60; mintick++)
1030 XDrawPoint (Xdisplay, W->win, X_gc,
1031 XPOS ((mintick * 12), 95),
1032 YPOS ((mintick * 12), 95));
1033#endif
1034 for (mintick = 0; mintick < 60; mintick += 5)
1035 XDrawLine (Xdisplay, W->win, X_gc,
1036 XPOS ((mintick * 12), 90),
1037 YPOS ((mintick * 12), 90),
1038 XPOS ((mintick * 12), 100),
1039 YPOS ((mintick * 12), 100));
1040 }
1041 else if (memcmp (pHandsOld, &HandsNow, sizeof(hands_t)))
1042 {
1043 int i, j;
1044 /*
1045 * erase old hands
1046 */
1047 for (i = -1; i < 2; i++) for (j = -1; j < 2; j++)
1048 {
1049 /* hour/minute hands */
1050 XDrawLine (Xdisplay, W->win, X_rvgc,
1051 ctr_x + i,
1052 ctr_y + j,
1053 pHandsOld->h_x, pHandsOld->h_y);
1054 XDrawLine (Xdisplay, W->win, X_rvgc,
1055 ctr_x + i,
1056 ctr_y + j,
1057 pHandsOld->m_x, pHandsOld->m_y);
1058 }
1059
1060 if (clockUpdate == 1) /* seconds hand */
1061 XDrawLine (Xdisplay,
1062 W->win, X_rvgc,
1063 ctr_x,
1064 ctr_y,
1065 pHandsOld->s_x, pHandsOld->s_y);
1066 }
1067
1068 if (full_redraw || memcmp (pHandsOld, &HandsNow, sizeof(hands_t)))
1069 {
1070 int i, j;
1071 /*
1072 * draw new hands
1073 */
1074 for (i = -1; i < 2; i++) for (j = -1; j < 2; j++)
1075 {
1076 /* hour/minute hands */
1077 XDrawLine (Xdisplay, W->win, X_gc,
1078 ctr_x + i,
1079 ctr_y + j,
1080 HandsNow.h_x, HandsNow.h_y);
1081
1082 XDrawLine (Xdisplay, W->win, X_gc,
1083 ctr_x + i,
1084 ctr_y + j,
1085 HandsNow.m_x, HandsNow.m_y);
1086 }
1087 if (clockUpdate == 1) /* seconds hand */
1088 XDrawLine (Xdisplay, W->win, X_gc,
1089 ctr_x,
1090 ctr_y,
1091 HandsNow.s_x, HandsNow.s_y);
1092
1093 *pHandsOld = HandsNow;
1094 }
1095}
1096
1097#ifdef REMINDERS
1098/* 1110/*
1099 * Read a single integer from *pstr, returns default value if it finds "*" 1111 * Read a single integer from *pstr, returns default value if it finds "*"
1100 * DELIM = trailing delimiter to skip 1112 * DELIM = trailing delimiter to skip
1101 */ 1113 */
1102static int 1114static int
1103GetOneNum (char ** pstr, int def) 1115GetOneNum (char **pstr, int def)
1104{ 1116{
1105 int num, hit = 0; 1117 int num, hit = 0;
1106 1118
1107 for (num = 0; isdigit (**pstr); (*pstr)++) 1119 for (num = 0; isdigit (**pstr); (*pstr)++)
1108 { 1120 {
1109 num = num * 10 + (**pstr - '0'); 1121 num = num * 10 + (**pstr - '0');
1110 hit = 1; 1122 hit = 1;
1111 } 1123 }
1112 if (!hit) 1124 if (!hit)
1113 { 1125 {
1114 num = def; 1126 num = def;
1115 while (**pstr == '*') (*pstr)++; 1127 while (**pstr == '*')
1128 (*pstr)++;
1116 } 1129 }
1117 return num; 1130 return num;
1118} 1131}
1119 1132
1120/* 1133/*
1121 * find if TODAY is found in PSTR 1134 * find if TODAY is found in PSTR
1122 */ 1135 */
1123static int 1136static int
1124isToday (char ** pstr, int wday) 1137isToday (char **pstr, int wday)
1125{ 1138{
1126 const char * dayNames = DAY_NAMES; 1139 const char *dayNames = DAY_NAMES;
1127 int rval, today; 1140 int rval, today;
1128 1141
1129 today = dayNames [wday]; 1142 today = dayNames[wday];
1130 /* no day specified is same as wildcard */ 1143 /* no day specified is same as wildcard */
1131 if (!strchr (dayNames, tolower (**pstr))) 1144 if (!strchr (dayNames, tolower (**pstr)))
1132 return 1; 1145 return 1;
1133 1146
1134 for (rval = 0; strchr (dayNames, tolower (**pstr)); (*pstr)++) 1147 for (rval = 0; strchr (dayNames, tolower (**pstr)); (*pstr)++)
1135 { 1148 {
1136 if (today == tolower (**pstr) || **pstr == '*') 1149 if (today == tolower (**pstr) || **pstr == '*')
1137 rval = 1; /* found it */ 1150 rval = 1; /* found it */
1138 } 1151 }
1139 return rval; 1152 return rval;
1140} 1153}
1141 1154
1142static char * 1155static char *
1143trim_string (char * str) 1156trim_string (char *str)
1144{ 1157{
1145 if (str && *str) 1158 if (str && *str)
1146 { 1159 {
1147 int n; 1160 int n;
1161
1148 while (*str && isspace (*str)) str++; 1162 while (*str && isspace (*str))
1163 str++;
1149 1164
1150 n = strlen (str) - 1; 1165 n = strlen (str) - 1;
1151 while (n > 0 && isspace (str [n])) n--; 1166 while (n > 0 && isspace (str[n]))
1167 n--;
1152 str [n+1] = '\0'; 1168 str[n + 1] = '\0';
1153 } 1169 }
1154 return str; 1170 return str;
1155} 1171}
1156 1172
1157# ifndef NO_REMINDER_EXEC 1173# ifndef NO_REMINDER_EXEC
1158static char * 1174static char *
1159extract_program (char * text) 1175extract_program (char *text)
1160{ 1176{
1161 char * prgm = text; 1177 char *prgm = text;
1178
1162 while ((prgm = strchr (prgm, ';')) != NULL) 1179 while ((prgm = strchr (prgm, ';')) != NULL)
1163 { 1180 {
1164 if (*(prgm-1) == '\\') /* backslash escaped */ 1181 if (*(prgm - 1) == '\\') /* backslash escaped */
1165 { 1182 {
1166 /* remove backslash - avoid memmove() */ 1183 /* remove backslash - avoid memmove() */
1167 int i, n = strlen (prgm); 1184 int i, n = strlen (prgm);
1185
1168 for (i = 0; i <= n; i++) 1186 for (i = 0; i <= n; i++)
1169 prgm [i - 1] = prgm [i]; 1187 prgm[i - 1] = prgm[i];
1170 } 1188 }
1171 else 1189 else
1172 { 1190 {
1173 *prgm++ = '\0'; 1191 *prgm++ = '\0';
1174 /* remove leading/trailing space */ 1192 /* remove leading/trailing space */
1175 prgm = trim_string (prgm); 1193 prgm = trim_string (prgm);
1176 break; 1194 break;
1177 } 1195 }
1178 } 1196 }
1179 return prgm; 1197 return prgm;
1180} 1198}
1181# endif /* NO_REMINDER_EXEC */ 1199# endif /* NO_REMINDER_EXEC */
1182 1200
1183/* 1201/*
1184 * Read the ~/.rclock file and find the next reminder 1202 * Read the ~/.rclock file and find the next reminder
1185 * 1203 *
1186 * update_only = 1 1204 * update_only = 1
1192 * just went off 1210 * just went off
1193 */ 1211 */
1194static void 1212static void
1195Next_Reminder (int update_only) 1213Next_Reminder (int update_only)
1196{ 1214{
1197 struct tm * tmval; 1215 struct tm *tmval;
1198 char buffer [256]; 1216 char buffer[256];
1217
1199#ifndef INT_MAX 1218# ifndef INT_MAX
1200# define INT_MAX 1e8 1219# define INT_MAX 1e8
1201#endif 1220# endif
1202 time_t currentTime; 1221 time_t currentTime;
1203 int savedTime = INT_MAX; 1222 int savedTime = INT_MAX;
1204 FILE * fd; 1223 FILE *fd;
1205 1224
1206 if (reminders_file == NULL || (fd = fopen (reminders_file, "r")) == NULL) 1225 if (reminders_file == NULL || (fd = fopen (reminders_file, "r")) == NULL)
1207 { 1226 {
1208 reminderTime = -1; /* no config file, no reminders */ 1227 reminderTime = -1; /* no config file, no reminders */
1209 return; 1228 return;
1210 } 1229 }
1211 1230
1212 currentTime = time (NULL) + adjustTime; /* get the current time */ 1231 currentTime = time (NULL) + adjustTime; /* get the current time */
1213 tmval = localtime (&currentTime); 1232 tmval = localtime (&currentTime);
1214 currentTime = mk_time (tmval); 1233 currentTime = mk_time (tmval);
1215 1234
1216 /* initial startup*/ 1235 /* initial startup */
1217 if (reminderTime < 0) 1236 if (reminderTime < 0)
1218 { 1237 {
1219 /* ignore reminders that have already occurred */ 1238 /* ignore reminders that have already occurred */
1220 reminderTime = currentTime; 1239 reminderTime = currentTime;
1221# ifndef NO_REMINDER_EXEC 1240# ifndef NO_REMINDER_EXEC
1222 /* scan for programs run on start-up */ 1241 /* scan for programs run on start-up */
1223 while (fgets (buffer, sizeof(buffer), fd)) 1242 while (fgets (buffer, sizeof (buffer), fd))
1224 { 1243 {
1225 char * prgm, * text; 1244 char *prgm, *text;
1226 1245
1227 text = trim_string (buffer); 1246 text = trim_string (buffer);
1228 if (*text != ';') continue; 1247 if (*text != ';')
1248 continue;
1229 1249
1230 prgm = extract_program (text); 1250 prgm = extract_program (text);
1231 if (prgm != NULL && strlen (prgm) > 1) 1251 if (prgm != NULL && strlen (prgm) > 1)
1232 system (prgm); 1252 system (prgm);
1233 } 1253 }
1234 rewind (fd); 1254 rewind (fd);
1235# endif /* NO_REMINDER_EXEC */ 1255# endif /* NO_REMINDER_EXEC */
1236 } 1256 }
1237 1257
1238 /* now scan for next reminder */ 1258 /* now scan for next reminder */
1239 while (fgets (buffer, sizeof(buffer), fd)) 1259 while (fgets (buffer, sizeof (buffer), fd))
1240 { 1260 {
1241 int testTime, hh, mm, mo, dd, yy; 1261 int testTime, hh, mm, mo, dd, yy;
1242 char * text; 1262 char *text;
1243 1263
1244 text = trim_string (buffer); 1264 text = trim_string (buffer);
1245 if (*text == '#') continue; /* comment */ 1265 if (*text == '#')
1246 if (*text == ';') continue; /* program run on startup */ 1266 continue; /* comment */
1247 /* 1267 if (*text == ';')
1268 continue; /* program run on startup */
1269 /*
1248 * parse the line, format is hh:mm mo/dd/yr message; program 1270 * parse the line, format is hh:mm mo/dd/yr message; program
1249 * any of hh, mm, mo, dd, yr could be a wildcard `*' 1271 * any of hh, mm, mo, dd, yr could be a wildcard `*'
1250 */ 1272 */
1251 hh = GetOneNum (&text, tmval->tm_hour); if (*text == ':') text++; 1273 hh = GetOneNum (&text, tmval->tm_hour);
1274 if (*text == ':')
1275 text++;
1252 mm = GetOneNum (&text, 0); 1276 mm = GetOneNum (&text, 0);
1253 1277
1254 while (isspace (*text)) text++; 1278 while (isspace (*text))
1279 text++;
1255 if (!isToday (&text, tmval->tm_wday)) continue; 1280 if (!isToday (&text, tmval->tm_wday))
1281 continue;
1256 while (isspace (*text)) text++; 1282 while (isspace (*text))
1283 text++;
1257 1284
1258 mo = GetOneNum (&text, tmval->tm_mon+1); if (*text == '/') text++; 1285 mo = GetOneNum (&text, tmval->tm_mon + 1);
1259 dd = GetOneNum (&text, tmval->tm_mday); if (*text == '/') text++; 1286 if (*text == '/')
1287 text++;
1288 dd = GetOneNum (&text, tmval->tm_mday);
1289 if (*text == '/')
1290 text++;
1260 yy = GetOneNum (&text, tmval->tm_year); 1291 yy = GetOneNum (&text, tmval->tm_year);
1261 1292
1262 /* handle 20th/21st centuries */ 1293 /* handle 20th/21st centuries */
1263 if (yy > CENTURY) 1294 if (yy > CENTURY)
1264 yy -= 1900; 1295 yy -= 1900;
1265 else if (yy < CENTURY) 1296 else if (yy < CENTURY)
1266 yy += (CENTURY - 1900); 1297 yy += (CENTURY - 1900);
1267 1298
1268 while (isspace (*text)) text++; 1299 while (isspace (*text))
1269 if (!*text) continue; 1300 text++;
1301 if (!*text)
1302 continue;
1270 1303
1271 testTime = (mm + 60 * (hh + 24 * (dd + 31 * (mo + 12 * yy)))); 1304 testTime = (mm + 60 * (hh + 24 * (dd + 31 * (mo + 12 * yy))));
1272 1305
1273 if (testTime > (update_only ? currentTime : reminderTime)) 1306 if (testTime > (update_only ? currentTime : reminderTime))
1274 { 1307 {
1275#ifndef NO_REMINDER_EXEC 1308# ifndef NO_REMINDER_EXEC
1276 char * prgm = extract_program (text); 1309 char *prgm = extract_program (text);
1277#endif /* NO_REMINDER_EXEC */ 1310# endif/* NO_REMINDER_EXEC */
1278 /* trim leading/trailing space */ 1311 /* trim leading/trailing space */
1279 text = trim_string (text); 1312 text = trim_string (text);
1280 1313
1281 /* 1314 /*
1282 * have a reminder whose time is greater than the last 1315 * have a reminder whose time is greater than the last
1283 * reminder, now make sure it is the smallest available 1316 * reminder, now make sure it is the smallest available
1284 */ 1317 */
1285 if (testTime < savedTime) 1318 if (testTime < savedTime)
1286 { 1319 {
1287 savedTime = testTime; 1320 savedTime = testTime;
1288 strncpy (message, text, sizeof(message)); 1321 strncpy (message, text, sizeof (message));
1289#ifndef NO_REMINDER_EXEC 1322# ifndef NO_REMINDER_EXEC
1290 strncpy (execPrgm, (prgm ? prgm : ""), sizeof(execPrgm)); 1323 strncpy (execPrgm, (prgm ? prgm : ""), sizeof (execPrgm));
1291#endif 1324# endif
1292 } 1325 }
1293 else if (testTime == savedTime) 1326 else if (testTime == savedTime)
1294 { 1327 {
1295 if (strlen (text)) 1328 if (strlen (text))
1296 { 1329 {
1297 int n = (sizeof(message) - strlen (message) - 3); 1330 int n = (sizeof (message) - strlen (message) - 3);
1298 if (n > 0) 1331
1299 { 1332 if (n > 0)
1333 {
1300 /* for co-occurring events */ 1334 /* for co-occurring events */
1301 strcat (message, "\\n"); 1335 strcat (message, "\\n");
1302 strncat (message, text, n); 1336 strncat (message, text, n);
1303 } 1337 }
1304 } 1338 }
1305#ifndef NO_REMINDER_EXEC 1339# ifndef NO_REMINDER_EXEC
1306 if (prgm != NULL) 1340 if (prgm != NULL)
1307 { 1341 {
1308 int n = (sizeof(execPrgm) - strlen (execPrgm) - 2); 1342 int n = (sizeof (execPrgm) - strlen (execPrgm) - 2);
1343
1309 if ((n > 0) && (n >= strlen (prgm))) 1344 if ((n > 0) && (n >= strlen (prgm)))
1310 { 1345 {
1311 /* for co-occurring programs */ 1346 /* for co-occurring programs */
1312 switch (execPrgm[strlen (execPrgm)-1]) 1347 switch (execPrgm[strlen (execPrgm) - 1])
1313 { 1348 {
1314 case '&': 1349 case '&':
1315 case ';': 1350 case ';':
1316 break; 1351 break;
1317 default: 1352 default:
1318 strcat (execPrgm, ";"); 1353 strcat (execPrgm, ";");
1319 break; 1354 break;
1320 } 1355 }
1321 strncat (execPrgm, prgm, n); 1356 strncat (execPrgm, prgm, n);
1322 } 1357 }
1323 } 1358 }
1324#endif /* NO_REMINDER_EXEC */ 1359# endif/* NO_REMINDER_EXEC */
1360 }
1325 } 1361 }
1326 }
1327 } 1362 }
1328 1363
1329 reminderTime = (savedTime < INT_MAX) ? savedTime : -1; 1364 reminderTime = (savedTime < INT_MAX) ? savedTime : -1;
1330 fclose (fd); 1365 fclose (fd);
1331} 1366}
1332 1367
1333/* 1368/*
1334 * Provide reminder by mapping the message window 1369 * Provide reminder by mapping the message window
1335 */ 1370 */
1336static void 1371static void
1337Reminder (void) 1372Reminder ()
1338{ 1373{
1339 char * beg, * next; 1374 char *beg, *next;
1340 int lines; 1375 int lines;
1341 1376
1342 if (Msg_Mapped) 1377 if (Msg_Mapped)
1343 return; 1378 return;
1344 1379
1345#ifndef NO_REMINDER_EXEC 1380# ifndef NO_REMINDER_EXEC
1346 if (strlen (message) == 0) 1381 if (strlen (message) == 0)
1347 { 1382 {
1348 if (strlen (execPrgm) > 1) 1383 if (strlen (execPrgm) > 1)
1349 { 1384 {
1350 system (execPrgm); 1385 system (execPrgm);
1351 Next_Reminder (REPLACE); 1386 Next_Reminder (REPLACE);
1352 } 1387 }
1353 return; /* some sort of error */ 1388 return; /* some sort of error */
1354 } 1389 }
1355#endif 1390# endif
1356 1391
1357 /* compute the window size */ 1392 /* compute the window size */
1358#ifdef NO_REMINDER_EXEC 1393# ifdef NO_REMINDER_EXEC
1359 Msg.width = 10 * XTextWidth (Xfont, "M", 1); 1394 Msg.width = 10 * XTextWidth (Xfont, "M", 1);
1360#else 1395# else
1361 Msg.width = 18 * XTextWidth (Xfont, "M", 1); 1396 Msg.width = 18 * XTextWidth (Xfont, "M", 1);
1362#endif 1397# endif
1363 1398
1364 for (beg = message, lines = 1; beg; beg = next, lines++) 1399 for (beg = message, lines = 1; beg; beg = next, lines++)
1365 { 1400 {
1366 int width; 1401 int width;
1367 char * end; 1402 char *end;
1368 1403
1369 if ((end = strstr (beg, "\\n")) == NULL) 1404 if ((end = strstr (beg, "\\n")) == NULL)
1370 { 1405 {
1371 end = beg + strlen (beg); 1406 end = beg + strlen (beg);
1372 next = NULL; 1407 next = NULL;
1373 } 1408 }
1374 else 1409 else
1375 { 1410 {
1376 next = end + 2; 1411 next = end + 2;
1377 } 1412 }
1378 1413
1379 width = XTextWidth (Xfont, beg, (end-beg)); 1414 width = XTextWidth (Xfont, beg, (end - beg));
1380 if (Msg.width < width) 1415 if (Msg.width < width)
1381 Msg.width = width; 1416 Msg.width = width;
1382 } 1417 }
1383 1418
1384 Msg.width += 30; 1419 Msg.width += 30;
1385 Msg.height = (lines+1) * FontHeight () + 30; 1420 Msg.height = (lines + 1) * FontHeight () + 30;
1386 1421
1387 /* resize and centre the window */ 1422 /* resize and centre the window */
1388 XMoveResizeWindow (Xdisplay, Msg.win, 1423 XMoveResizeWindow (Xdisplay, Msg.win,
1389 (DisplayWidth (Xdisplay, Xscreen) - Msg.width ) / 2, 1424 (DisplayWidth (Xdisplay, Xscreen) - Msg.width) / 2,
1390 (DisplayHeight (Xdisplay, Xscreen) - Msg.height) / 2, 1425 (DisplayHeight (Xdisplay, Xscreen) - Msg.height) / 2, Msg.width, Msg.height);
1391 Msg.width, Msg.height);
1392 1426
1393#define BUTTON_MARGIN 8 1427# define BUTTON_MARGIN 8
1394 1428
1395 XMoveWindow (Xdisplay, msgButton.Dismiss, 1429 XMoveWindow (Xdisplay, msgButton.Dismiss, BUTTON_MARGIN, (Msg.height - msgButton.height - BUTTON_MARGIN));
1396 BUTTON_MARGIN, 1430 XMoveWindow (Xdisplay, msgButton.Defer, (Msg.width - msgButton.width - BUTTON_MARGIN), (Msg.height - msgButton.height - BUTTON_MARGIN));
1397 (Msg.height - msgButton.height - BUTTON_MARGIN));
1398 XMoveWindow (Xdisplay, msgButton.Defer,
1399 (Msg.width - msgButton.width - BUTTON_MARGIN),
1400 (Msg.height - msgButton.height - BUTTON_MARGIN));
1401#ifndef NO_REMINDER_EXEC 1431# ifndef NO_REMINDER_EXEC
1402 XMoveWindow (Xdisplay, msgButton.Start, 1432 XMoveWindow (Xdisplay, msgButton.Start, (Msg.width - msgButton.width) / 2, (Msg.height - msgButton.height - BUTTON_MARGIN));
1403 (Msg.width - msgButton.width) / 2,
1404 (Msg.height - msgButton.height - BUTTON_MARGIN));
1405#endif 1433# endif
1406 1434
1407 XMapRaised (Xdisplay, Msg.win); 1435 XMapRaised (Xdisplay, Msg.win);
1408 XBell (Xdisplay, 0); 1436 XBell (Xdisplay, 0);
1409 Msg_Mapped = 1; 1437 Msg_Mapped = 1;
1410} 1438}
1411#endif /* REMINDERS */ 1439#endif /* REMINDERS */
1412
1413#ifndef _POSIX_VERSION
1414# if defined (__svr4__)
1415static int
1416getdtablesize (void)
1417{
1418 struct rlimit rlim;
1419 getrlimit (RLIMIT_NOFILE, &rlim);
1420 return rlim.rlim_cur;
1421}
1422# endif
1423#endif
1424 1440
1425/* 1441/*
1426 * Loops forever, looking for stuff to do. Sleeps 1 minute if nothing to do 1442 * Loops forever, looking for stuff to do. Sleeps 1 minute if nothing to do
1427 */ 1443 */
1428static void 1444static void
1429getXevent (void) 1445getXevent ()
1430{ 1446{
1431 XEvent ev; 1447 XEvent ev;
1432 int num_fds; /* number of file descriptors being used */ 1448 int num_fds; /* number of file descriptors being used */
1433 struct timeval tm; 1449 struct timeval tm;
1434 struct tm * tmval; 1450 struct tm *tmval;
1435 Atom wmDeleteWindow; 1451 Atom wmDeleteWindow;
1436 fd_set in_fdset; 1452 fd_set in_fdset;
1437 1453
1438 /* Enable delete window protocol */ 1454 /* Enable delete window protocol */
1439 wmDeleteWindow = XInternAtom (Xdisplay, "WM_DELETE_WINDOW", False); 1455 wmDeleteWindow = XInternAtom (Xdisplay, "WM_DELETE_WINDOW", False);
1440 XSetWMProtocols (Xdisplay, Clock.win, &wmDeleteWindow, 1); 1456 XSetWMProtocols (Xdisplay, Clock.win, &wmDeleteWindow, 1);
1441#ifdef ICONWIN 1457#ifdef ICONWIN
1442 XSetWMProtocols (Xdisplay, Icon.win, &wmDeleteWindow, 1); 1458 XSetWMProtocols (Xdisplay, Icon.win, &wmDeleteWindow, 1);
1443#endif 1459#endif
1444#ifdef REMINDERS 1460#ifdef REMINDERS
1445 XSetWMProtocols (Xdisplay, Msg.win, &wmDeleteWindow, 1); 1461 XSetWMProtocols (Xdisplay, Msg.win, &wmDeleteWindow, 1);
1446#endif 1462#endif
1447 1463
1448#ifdef _POSIX_VERSION
1449 num_fds = sysconf (_SC_OPEN_MAX); 1464 num_fds = sysconf (_SC_OPEN_MAX);
1450#else
1451 num_fds = getdtablesize ();
1452#endif
1453#ifdef FD_SETSIZE 1465#ifdef FD_SETSIZE
1454 if (num_fds > FD_SETSIZE) 1466 if (num_fds > FD_SETSIZE)
1455 num_fds = FD_SETSIZE; 1467 num_fds = FD_SETSIZE;
1456#endif 1468#endif
1457 1469
1458 while (1) { 1470 while (1)
1471 {
1459 /* take care of all pending X events */ 1472 /* take care of all pending X events */
1460 while (XPending (Xdisplay)) { 1473 while (XPending (Xdisplay))
1474 {
1461 XNextEvent (Xdisplay, &ev); 1475 XNextEvent (Xdisplay, &ev);
1462 switch (ev.type) { 1476 switch (ev.type)
1477 {
1463 case ClientMessage: 1478 case ClientMessage:
1464 /* check for delete window requests */ 1479 /* check for delete window requests */
1465 if ((ev.xclient.format == 32) && 1480 if ((ev.xclient.format == 32) && (ev.xclient.data.l[0] == (long)wmDeleteWindow))
1466 (ev.xclient.data.l[0] == wmDeleteWindow)) 1481 {
1467 {
1468#ifdef REMINDERS 1482#ifdef REMINDERS
1469 if (ev.xany.window == Msg.win) 1483 if (ev.xany.window == Msg.win)
1470 { 1484 {
1471 XUnmapWindow (Xdisplay, Msg.win); 1485 XUnmapWindow (Xdisplay, Msg.win);
1472 Msg_Mapped = 0; 1486 Msg_Mapped = 0;
1473 Next_Reminder (REPLACE); 1487 Next_Reminder (REPLACE);
1474 } 1488 }
1475 else 1489 else
1476#endif 1490#endif
1477 return; /* delete window is how this terminates */ 1491 return; /* delete window is how this terminates */
1478 } 1492 }
1479 break; 1493 break;
1480 1494
1481 case Expose: 1495 case Expose:
1482 case GraphicsExpose: 1496 case GraphicsExpose:
1483 /* need to re-draw a window */ 1497 /* need to re-draw a window */
1484 if (ev.xany.window == Clock.win) 1498 if (ev.xany.window == Clock.win)
1485 Draw_Window (&Clock, 1); 1499 Draw_Window (&Clock, 1);
1486#ifdef ICONWIN 1500#ifdef ICONWIN
1487 else if (ev.xany.window == Icon.win) 1501 else if (ev.xany.window == Icon.win)
1488 Draw_Window (&Icon, 1); 1502 Draw_Window (&Icon, 1);
1489#endif 1503#endif
1490#ifdef REMINDERS 1504#ifdef REMINDERS
1491 else 1505 else
1492 Draw_Window (&Msg, 1); 1506 Draw_Window (&Msg, 1);
1493#endif 1507#endif
1494 break; 1508 break;
1495 1509
1496 case ConfigureNotify: 1510 case ConfigureNotify:
1497 /* window has been re-sized */ 1511 /* window has been re-sized */
1498 if (ev.xany.window == Clock.win) 1512 if (ev.xany.window == Clock.win)
1499 { 1513 {
1500 Clock.width = ev.xconfigure.width; 1514 Clock.width = ev.xconfigure.width;
1501 Clock.height = ev.xconfigure.height; 1515 Clock.height = ev.xconfigure.height;
1502 } 1516 }
1503 break; 1517 break;
1504 1518
1505#ifdef REMINDERS 1519#ifdef REMINDERS
1506 case KeyPress: 1520 case KeyPress:
1507 /* any key press to dismiss message window */ 1521 /* any key press to dismiss message window */
1508 if (ev.xany.window == Msg.win) 1522 if (ev.xany.window == Msg.win)
1509 { 1523 {
1510 Next_Reminder (REPLACE); 1524 Next_Reminder (REPLACE);
1511 Msg_Mapped = 0; 1525 Msg_Mapped = 0;
1512 XUnmapWindow (Xdisplay, Msg.win); 1526 XUnmapWindow (Xdisplay, Msg.win);
1513 } 1527 }
1514 break; 1528 break;
1515#endif 1529#endif
1516 1530
1517 case ButtonPress: 1531 case ButtonPress:
1518#ifdef REMINDERS 1532#ifdef REMINDERS
1519 /* button press to dismiss message window */ 1533 /* button press to dismiss message window */
1520 if (ev.xany.window == Msg.win) 1534 if (ev.xany.window == Msg.win)
1521 {
1522 if (ev.xbutton.subwindow == msgButton.Dismiss)
1523 {
1524 Next_Reminder (REPLACE);
1525 Msg_Mapped = 0;
1526 XUnmapWindow (Xdisplay, Msg.win);
1527 }
1528 else if (ev.xbutton.subwindow == msgButton.Defer)
1529 {
1530 time_t t = time (NULL) + adjustTime;
1531 tmval = localtime (&t);
1532 reminderTime = mk_time (tmval) + DEFER_TIME;
1533 Msg_Mapped = 0;
1534 XUnmapWindow (Xdisplay, Msg.win);
1535 }
1536#ifndef NO_REMINDER_EXEC
1537 else if (ev.xbutton.subwindow == msgButton.Start)
1538 { 1535 {
1539 system (execPrgm); 1536 if (ev.xbutton.subwindow == msgButton.Dismiss)
1537 {
1540 Next_Reminder (REPLACE); 1538 Next_Reminder (REPLACE);
1541 Msg_Mapped = 0; 1539 Msg_Mapped = 0;
1542 XUnmapWindow (Xdisplay, Msg.win); 1540 XUnmapWindow (Xdisplay, Msg.win);
1541 }
1542 else if (ev.xbutton.subwindow == msgButton.Defer)
1543 {
1544 time_t t = time (NULL) + adjustTime;
1545
1546 tmval = localtime (&t);
1547 reminderTime = mk_time (tmval) + DEFER_TIME;
1548 Msg_Mapped = 0;
1549 XUnmapWindow (Xdisplay, Msg.win);
1550 }
1551# ifndef NO_REMINDER_EXEC
1552 else if (ev.xbutton.subwindow == msgButton.Start)
1553 {
1554 system (execPrgm);
1555 Next_Reminder (REPLACE);
1556 Msg_Mapped = 0;
1557 XUnmapWindow (Xdisplay, Msg.win);
1558 }
1559# endif/* NO_REMINDER_EXEC */
1543 } 1560 }
1544#endif /* NO_REMINDER_EXEC */
1545 }
1546#endif 1561#endif
1547#ifdef MAIL 1562#ifdef MAIL
1548 if (ev.xany.window == Clock.win) 1563 if (ev.xany.window == Clock.win)
1549 { 1564 {
1550#ifdef MAIL_SPAWN 1565# ifdef MAIL_SPAWN
1551 /* left button action - spawn a mail reader */ 1566 /* left button action - spawn a mail reader */
1552 if (ev.xbutton.button == Button1) 1567 if (ev.xbutton.button == Button1)
1553 system (MAIL_SPAWN); 1568 system (MAIL_SPAWN);
1554#else 1569# else
1555 if ( (ev.xbutton.button == Button1) && (mail_spawn != NULL) ) 1570 if ((ev.xbutton.button == Button1) && (mail_spawn != NULL))
1556 system(mail_spawn); 1571 system (mail_spawn);
1557#endif 1572# endif
1558 /* redraw the window */ 1573 /* redraw the window */
1559 Draw_Window (&Clock, 1); 1574 Draw_Window (&Clock, 1);
1560 } 1575 }
1561#endif 1576#endif
1562 break; 1577 break;
1563 } 1578 }
1564 } 1579 }
1565 1580
1566 /* Now wait for time out or new X event */ 1581 /* Now wait for time out or new X event */
1567 FD_ZERO (&in_fdset); 1582 FD_ZERO (&in_fdset);
1568 FD_SET (Xfd, &in_fdset); 1583 FD_SET (Xfd, &in_fdset);
1569 tm.tv_sec = clockUpdate; 1584 tm.tv_sec = clockUpdate;
1572 1587
1573 Draw_Window (&Clock, 0); 1588 Draw_Window (&Clock, 0);
1574#ifdef ICONWIN 1589#ifdef ICONWIN
1575 Draw_Window (&Icon, 0); 1590 Draw_Window (&Icon, 0);
1576#endif 1591#endif
1577 } 1592 }
1578} 1593}
1579 1594
1580/* 1595/*
1581 * Print an error message. 1596 * Print an error message.
1582 */ 1597 */
1583static void 1598static void
1584print_error (const char * fmt, ...) 1599print_error (const char *fmt, ...)
1585{ 1600{
1586 va_list arg_ptr; 1601 va_list arg_ptr;
1587 1602
1588 va_start (arg_ptr, fmt); 1603 va_start (arg_ptr, fmt);
1589 fprintf (stderr, APL_NAME ": "); 1604 fprintf (stderr, APL_NAME ": ");
1590 vfprintf (stderr, fmt, arg_ptr); 1605 vfprintf (stderr, fmt, arg_ptr);
1591 fprintf (stderr,"\n"); 1606 fprintf (stderr, "\n");
1592 va_end (arg_ptr); 1607 va_end (arg_ptr);
1593} 1608}
1609
1594/*----------------------- end-of-file (C source) -----------------------*/ 1610/*----------------------- end-of-file (C source) -----------------------*/

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines