]> andersk Git - moira.git/blame - clients/userreg/display.c
second code style cleanup: void/void * usage, proper #includes. try to
[moira.git] / clients / userreg / display.c
CommitLineData
7ac48069 1/* $Id $
7189310c 2 *
7ac48069 3 * Display function for userreg client
4 *
5 * Copyright (C) 1988-1998 by the Massachusetts Institute of Technology.
6 * For copying and distribution information, please see the file
7 * <mit-copyright.h>.
989a2c2c 8 */
9
7189310c 10#include <mit-copyright.h>
7ac48069 11#include <moira.h>
12
989a2c2c 13#include <curses.h>
7ac48069 14#include <stdio.h>
15#include <time.h>
16#include <unistd.h>
17
989a2c2c 18#include "userreg.h"
19
7ac48069 20RCSID("$Header$");
21
22void make_border(int l);
23void query_user(char *prompt, char *buf, int maxsize, int timeout,
24 int echop, int emptyok, int valuep);
25
989a2c2c 26#define DESC_WIDTH 18
a2b4a2ee 27#define HEADER "*** Athena User Account Registration ***"
a2b4a2ee 28#define HELP " Press backspace to delete a character. Press Ctrl-C to start over."
989a2c2c 29#define BORDER_CHAR '-'
30#define MIN_COLS 80
31#define MIN_LINES 24
32
7ac48069 33WINDOW *displayw, *queryw;
34WINDOW *dataw, *helpw;
35WINDOW *fnamew, *midw, *lnamew, *idw, *loginw;
7ff930df 36extern char typed_mit_id[100];
989a2c2c 37
38/* Set up the windows and subwindows on the display */
7ac48069 39void setup_display(void)
5eaef520 40{
5eaef520 41 initscr(); /* Start up curses */
989a2c2c 42
5eaef520 43 if (COLS < MIN_COLS || LINES < MIN_LINES)
44 {
45 fprintf(stderr, "Screen must be at least %d x %d\n",
46 MIN_LINES, MIN_COLS);
47 exit(1);
48 }
94464a85 49
5eaef520 50 noecho(); /* And the tty input */
51 raw();
52 freopen("/dev/null", "w", stderr);/* Toss the standard error output */
989a2c2c 53
5eaef520 54 /* Make sure the place is clean */
55 clear();
989a2c2c 56
5eaef520 57 /* Set up the top-level windows */
58 /* First line is the header */
59 displayw = subwin(stdscr, 12, 0, 2, 0);/* Lines 2-13 */
60 scrollok(displayw, TRUE);
989a2c2c 61
5eaef520 62 queryw = subwin(stdscr, 1, 0, 15, 0);/* Line 15 */
63 scrollok(queryw, TRUE);
989a2c2c 64
5eaef520 65 dataw = subwin(stdscr, 5, 0, 17, 0);/* Lines 17-21 */
989a2c2c 66
5eaef520 67 /* Set up the data windows */
68 fnamew = subwin(stdscr, 1, 0, 17, DESC_WIDTH);
69 midw = subwin(stdscr, 1, 0, 18, DESC_WIDTH);
70 lnamew = subwin(stdscr, 1, 0, 19, DESC_WIDTH);
71 idw = subwin(stdscr, 1, 0, 20, DESC_WIDTH);
72 loginw = subwin(stdscr, 1, 0, 21, DESC_WIDTH);
989a2c2c 73}
74
75/* Clear and restore the display */
7ac48069 76void reset_display(void)
5eaef520 77{
78 clear();
79
80 /* Put back the borders */
81 make_border(1);
82 make_border(14);
83 make_border(16);
84 make_border(22);
85
86 /* Put in the window dressing */
87 wmove(dataw, 0, 0);
88 waddstr(dataw, "First Name:\n");
89 waddstr(dataw, "Middle Initial:\n");
90 waddstr(dataw, "Family Name:\n");
91 waddstr(dataw, "MIT ID #:\n\n");
92 waddstr(dataw, "Username:\n");
93 wclrtoeol(dataw);
94
95 /* Set up the header */
96 mvaddstr(0, (COLS - strlen (HEADER)) / 2, HEADER);
97 mvaddstr(23, 0, HELP);
98
99 /* Put it all up */
100 refresh();
989a2c2c 101}
102
103
104/* Make a one-line border on line l of stdscr */
7ac48069 105void make_border(int l)
989a2c2c 106{
5eaef520 107 int i;
989a2c2c 108
5eaef520 109 move(l, 0);
110 for(i = 0; i < COLS - 1; i++)
111 addch(BORDER_CHAR);
989a2c2c 112}
113
114/* This replaces several "useful" display functions in the old userreg */
7ac48069 115void redisp(void)
5eaef520 116{
117 mvwprintw(fnamew, 0, 0, "%-24s", user.u_first);
e6b3a349 118 wrefresh(fnamew);
5eaef520 119 mvwprintw(midw, 0, 0, "%-24s", user.u_mid_init);
e6b3a349 120 wrefresh(midw);
5eaef520 121 mvwprintw(lnamew, 0, 0, "%-24s", user.u_last);
e6b3a349 122 wrefresh(lnamew);
5eaef520 123 mvwprintw(idw, 0, 0, "%-24s", typed_mit_id);
e6b3a349 124 wrefresh(idw);
5eaef520 125 mvwprintw(loginw, 0, 0, "%-24s", user.u_login);
e6b3a349 126 wrefresh(loginw);
989a2c2c 127}
128
129
130/* Input and input_no_echo exist only to save on retyping */
7ac48069 131void input(char *prompt, char *buf, int maxsize, int timeout, int emptyok)
989a2c2c 132{
5eaef520 133 query_user(prompt, buf, maxsize, timeout, TRUE, emptyok, TRUE);
989a2c2c 134}
135
7ac48069 136void input_no_echo(char *prompt, char *buf, int maxsize, int timeout)
989a2c2c 137{
5eaef520 138 query_user(prompt, buf, maxsize, timeout, FALSE, FALSE, TRUE);
989a2c2c 139}
140
141
4127ae1e 142/* make the user press any key to continue */
7ac48069 143void wait_for_user(void)
4127ae1e 144{
5eaef520 145 char buf[BUFSIZ];
4127ae1e 146
5eaef520 147 redisp();
148 query_user("Press RETURN or ENTER to continue", buf, 1,
149 15 * 60, FALSE, TRUE, FALSE);
4127ae1e 150}
151
989a2c2c 152
153/* Gets input through the query buffer */
154/* Exit(1)'s on read errors */
155/* Signals SIGALRM after 'timeout' seconds */
7ac48069 156void query_user(char *prompt, char *buf, int maxsize, int timeout,
157 int echop, int emptyok, int valuep)
989a2c2c 158{
5eaef520 159 int c;
160 int i;
989a2c2c 161 struct itimerval it;
162
163retry:
164 /* Set up interval timer */
165 it.it_interval.tv_sec = 0;
166 it.it_interval.tv_usec = 0;
167 it.it_value.tv_sec = timeout;
168 it.it_value.tv_usec = 0;
5eaef520 169 setitimer(ITIMER_REAL, &it, NULL);
989a2c2c 170
171 /* Erase the query window and put up a prompt */
5eaef520 172 werase(queryw);
173 mvwaddstr(queryw, 0, 0, prompt);
174 waddch(queryw, ' '); /* Put in a space, as Blox does */
175 wrefresh(queryw);
989a2c2c 176
177 i = 0;
5eaef520 178 while ((c = getchar()) != '\r' && c != '\n')
179 {
180 switch (c)
181 {
182 case '\025': /* Ctl-U */
183 goto retry;
184 case EOF:
185 /* We're in raw mode, so EOF means disaster */
186 exit(1);
187 break;
188 delchar:
189 case '\177': /* Delete */
190 case '\010': /* Backspace */
191 if (i)
192 {
193 i--;
194 if (echop)
195 {
196 int x, y;
197 getyx(queryw, y, x);
198 wmove(queryw, y, x - 1);
199 wclrtoeol(queryw);
200 wrefresh(queryw);
201 }
202 }
203 break;
204 case '\003': /* Ctrl-C */
205 clear();
206 restore_display();
207 exit(0);
208 break;
209 default:
210 if (c >= ' ') /* Ignore all other control chars */
211 {
212 buf[i++] = c;
213 if (echop)
214 {
215 waddch(queryw, c);
216 wrefresh(queryw);
217 }
218 }
219 break;
989a2c2c 220 }
5eaef520 221 if (valuep && i >= maxsize)
222 {
223 wfeep();
224 wprintw(displayw, "You are not allowed to type more than %d "
225 "characters for this answer.\n", maxsize - 1);
226 wrefresh(displayw);
227 goto delchar;
989a2c2c 228 }
989a2c2c 229 }
989a2c2c 230
5eaef520 231 if (i == 0)
232 {
4127ae1e 233 if (emptyok && valuep &&
234 (askyn("Do you really want this field left blank (y/n)? ") == NO))
235 goto retry;
5eaef520 236 if (!emptyok)
237 {
4127ae1e 238 wprintw(displayw, "You must enter something here.\n");
239 wrefresh(displayw);
240 goto retry;
5eaef520 241 }
242 }
243
989a2c2c 244
245 /* Input is complete so disable interval timer. */
246 it.it_interval.tv_sec = 0;
247 it.it_interval.tv_usec = 0;
248 it.it_value.tv_sec = 0;
249 it.it_value.tv_usec = 0;
5eaef520 250 setitimer(ITIMER_REAL, &it, NULL);
989a2c2c 251
252 buf[i] = '\0'; /* Put a null on the end */
253
5eaef520 254 werase(queryw); /* Clean up the query window */
255 wrefresh(queryw);
989a2c2c 256
257 return; /* And get out of here. */
258}
259
5eaef520 260int askyn(char *prompt)
989a2c2c 261{
262 int ypos, xpos;
263 int answer;
264 struct itimerval it;
8b2d95d4 265 int c;
989a2c2c 266
5eaef520 267start:
268 werase(queryw);
269 mvwaddstr(queryw, 0, 0, prompt);
270 wrefresh(queryw);
989a2c2c 271
7ff930df 272 getyx(queryw, ypos, xpos);
989a2c2c 273 answer = 2; /* No answer. */
5eaef520 274
989a2c2c 275 /* Reset interval timer for y/n question. */
276 it.it_interval.tv_sec = 0;
277 it.it_interval.tv_usec = 0;
278 it.it_value.tv_sec = YN_TIMEOUT;
279 it.it_value.tv_usec = 0;
5eaef520 280 setitimer(ITIMER_REAL, &it, NULL);
281
282 while ((c = getchar ()) != '\r' && c != '\n') /* Wait for CR. */
283 {
284 switch (c)
285 {
286 case 'n': /* No. */
287 case 'N':
288 wmove(queryw, ypos, xpos);
289 wclrtoeol(queryw);
290 waddstr(queryw, "no");
291 wrefresh(queryw);
292 answer = NO;
293 continue;
294 case 'y': /* Yes. */
295 case 'Y':
296 wmove(queryw, ypos, xpos);
297 wclrtoeol(queryw);
298 waddstr(queryw, "yes");
299 wrefresh(queryw);
300 answer = YES;
301 continue;
302 case '\177': /* Delete */
303 case '\010': /* Backspace */
304 case '\025': /* Ctl-U */
305 wmove(queryw, ypos, xpos);
306 wclrtoeol(queryw);
307 wrefresh(queryw);
308 answer = 2; /* No answer. */
309 break;
310 case EOF:
311 /* We're in raw mode, so EOF means disaster */
312 exit(1);
313 break;
314 case '\003': /* Ctrl-C */
315 clear();
316 restore_display();
317 exit(0);
318 break;
319 default: /* Ignore everything else. */
320 break;
321 }
989a2c2c 322 }
323
324 if (answer == 2) /* No answer. */
5eaef520 325 {
326 display_text_line(0);
989a2c2c 327 display_text_line("Please answer y or n.");
328 goto start;
329 }
5eaef520 330
331 return answer;
989a2c2c 332}
333
334/* Display_text_line puts up a line of text in the display window */
335/* Special case: if line is 0, clear the display area */
7ac48069 336void display_text_line(char *line)
989a2c2c 337{
5eaef520 338 if (line)
339 {
340 waddstr(displayw, line);
341 waddch(displayw, '\n');
342 }
343 else
344 werase(displayw);
345 wrefresh(displayw);
989a2c2c 346}
347
a2b4a2ee 348/* Display_text displays a canned message from a file. The string
349 * will get imbedded in any %s's in the text.
350 */
7ac48069 351void display_text(char *filename, char *string)
989a2c2c 352{
353 FILE * fp;
5eaef520 354 char buf[100], buf1[110];
989a2c2c 355
5eaef520 356 werase(displayw);
357 if (!(fp = fopen (filename, "r")))
358 {
359 wprintw (displayw, "Can't open file %s for reading.\n", filename);
360 return;
361 }
989a2c2c 362
5eaef520 363 while (fgets (buf, 100, fp))
364 {
a2b4a2ee 365 /* get rid of the newline */
5eaef520 366 buf[strlen(buf) - 1] = '\0';
a2b4a2ee 367 sprintf(buf1, buf, string);
368 waddstr(displayw, buf1);
369 waddch(displayw, '\n');
5eaef520 370 }
989a2c2c 371
a2b4a2ee 372 wrefresh(displayw);
5eaef520 373 fclose(fp);
989a2c2c 374}
375
376/* Clear_display wipes the display and turns off curses */
7ac48069 377void restore_display(void)
989a2c2c 378{
379 clear();
380 refresh();
381 noraw();
382 echo();
383 endwin();
384}
385
7ac48069 386void timer_on(void)
989a2c2c 387{
388 struct itimerval it;
389
390 it.it_interval.tv_sec = 0;
391 it.it_interval.tv_usec = 0;
392 it.it_value.tv_sec = TIMER_TIMEOUT;
393 it.it_value.tv_usec = 0;
5eaef520 394 setitimer(ITIMER_REAL, &it, NULL);
989a2c2c 395}
396
7ac48069 397void timer_off(void)
989a2c2c 398{
399 struct itimerval it;
400
401 it.it_interval.tv_sec = 0;
402 it.it_interval.tv_usec = 0;
403 it.it_value.tv_sec = 0;
404 it.it_value.tv_usec = 0;
5eaef520 405 setitimer(ITIMER_REAL, &it, NULL);
989a2c2c 406}
407
4127ae1e 408
7ac48069 409void wfeep(void)
4127ae1e 410{
5eaef520 411 char buf = '\007';
412 write(1, &buf, 1);
4127ae1e 413}
This page took 0.145028 seconds and 5 git commands to generate.