|
|
1.1 ! root 1: /* ! 2: * Screen driver functions connected with wgetLoc(). ! 3: */ ! 4: #include <scn.h> ! 5: #include <longfield.h> ! 6: ! 7: #define CTRL(c) (c - '@') ! 8: WINDOW *errWindow = NULL; ! 9: static int errSw; /* clear errWindow at next stdscn input */ ! 10: static needsTouch; /* needs touchwin at next stdscn input */ ! 11: static savC; /* exit char for recursion */ ! 12: ! 13: /* ! 14: * loc.field may be a char * or a char ** ! 15: * return the char *. ! 16: */ ! 17: static char * ! 18: fieldPtr(f) register loc *f; ! 19: { ! 20: return ((f->flags & LONGFIELD) ? *((char **)f->field) : f->field); ! 21: } ! 22: ! 23: static void ! 24: longField(f) loc *f; ! 25: { ! 26: register loc *l; /* tmp area pointer */ ! 27: register char *q, *new; ! 28: WINDOW *w; ! 29: char **p, **d; ! 30: int j, len, same; ! 31: ! 32: if (NULL == (w = newwin(8, 80, 0, 0))) ! 33: fatal("Cannot open subwindow"); ! 34: ! 35: touchwin(w); ! 36: p = (char **)f->field; ! 37: d = (char **)f->Default; ! 38: same = (*p == *d); /* is field == default */ ! 39: ! 40: /* zero work fields */ ! 41: for (l = longfield_locs; NULL != (q = l->field); l++) { ! 42: l->help = f->help; ! 43: memset(q, '\0', l->len); ! 44: } ! 45: ! 46: /* move in defaults */ ! 47: if (NULL != (new = *d)) { ! 48: for (l = longfield_locs; NULL != (q = l->field); l++) { ! 49: for (j = 0; *new && (j < l->len); j++) ! 50: *q++ = *new++; ! 51: } ! 52: free(*p); ! 53: } ! 54: ! 55: wscnDriv(w, longfield_data, longfield_locs); ! 56: ! 57: for (len = 1, l = longfield_locs; NULL != (q = l->field); l++) ! 58: len += strlen(q); ! 59: ! 60: *p = new = alloc(len); ! 61: if (same) ! 62: *d = new; ! 63: ! 64: for (l = longfield_locs; NULL != (q = l->field); l++) ! 65: strcat(new, q); ! 66: ! 67: delwin(w); ! 68: } ! 69: ! 70: /* ! 71: * Show any error. ! 72: */ ! 73: void ! 74: showError(s) ! 75: char *s; ! 76: { ! 77: char work[80]; ! 78: ! 79: if (NULL == errWindow) ! 80: fatal("No error window"); ! 81: sprintf(work, "Error: %r", &s); ! 82: wmove(errWindow, 0, 0); ! 83: wstandout(errWindow); ! 84: waddstr(errWindow, work); ! 85: wstandend(errWindow); ! 86: wrefresh(errWindow); ! 87: errSw = 1; ! 88: } ! 89: ! 90: /* ! 91: * Show a help message if one exists. ! 92: */ ! 93: showHelp(msg) ! 94: char *msg; ! 95: { ! 96: if (NULL != errWindow) { ! 97: wmove(errWindow, 1, 0); ! 98: wclrtoeol(errWindow); ! 99: if (NULL != msg) { ! 100: wmove(errWindow, 1, 0); ! 101: waddstr(errWindow, msg); ! 102: } ! 103: wrefresh(errWindow); ! 104: } ! 105: } ! 106: ! 107: /* ! 108: * Get a char from screen, Erase error window if not clear. ! 109: */ ! 110: static ! 111: wgetChr(w) register WINDOW *w; ! 112: { ! 113: register c; ! 114: ! 115: if (needsTouch) { ! 116: needsTouch = 0; ! 117: if (stdscr == w) { ! 118: touchwin(w); ! 119: wrefresh(w); ! 120: } ! 121: } ! 122: ! 123: c = wgetch(w); ! 124: ! 125: if (errSw) { ! 126: wmove(errWindow, 0, 0); ! 127: wclrtoeol(errWindow); ! 128: wrefresh(errWindow); ! 129: errSw = 0; ! 130: } ! 131: return (c); ! 132: } ! 133: ! 134: ! 135: /* ! 136: * if sw == 0: Display a fields default copy to field, then get it. ! 137: * if sw == 1: Display field's default. ! 138: * if sw == 2: Display field. ! 139: */ ! 140: static ! 141: wgetLoc(w, f, sw) register WINDOW *w; register loc *f; int sw; ! 142: { ! 143: int got, /* number of chars processed */ ! 144: c, /* current char */ ! 145: y, x, /* cursor loc */ ! 146: i, /* pos in Default field */ ! 147: state; /* 1 == ESC sequence in process */ ! 148: char *field, *def; ! 149: ! 150: wmove(w, y = f->row, x = f->col); ! 151: ! 152: /* ! 153: * LONGFIELD is defined as 4 ! 154: */ ! 155: switch ((f->flags & LONGFIELD) | sw) { ! 156: case 6: /* display long field */ ! 157: def = *((char **)f->field); /* we have ptr to ptr */ ! 158: break; ! 159: ! 160: case 4: /* get long field */ ! 161: wstandout(w); /* remind user which */ ! 162: ! 163: case 5: /* display long field default */ ! 164: def = *((char **)f->Default); /* we have ptr to ptr */ ! 165: break; ! 166: ! 167: case 2: /* display short field */ ! 168: def = f->field; ! 169: break; ! 170: ! 171: case 1: /* display short field default */ ! 172: def = f->Default; ! 173: break; ! 174: ! 175: case 0: /* get short field */ ! 176: def = f->Default; ! 177: field = f->field; ! 178: ! 179: /* copy Default into field and zero fill */ ! 180: for (got = i = 0; got <= f->len; got++) { ! 181: if (c = def[i]) ! 182: i++; ! 183: field[got] = c; ! 184: } ! 185: } ! 186: ! 187: /* display whatever */ ! 188: if (NULL == def) ! 189: def = ""; ! 190: for (got = i = 0; got < f->len; got++) { ! 191: if (c = def[i]) { ! 192: i++; ! 193: waddch(w, c); ! 194: } ! 195: else ! 196: waddch(w, ' '); ! 197: } ! 198: ! 199: if (f->flags & LONGFIELD) ! 200: wstandend(w); ! 201: ! 202: refresh(); ! 203: ! 204: if (sw || (f->flags & READONLY)) /* display or read only */ ! 205: return (0); ! 206: ! 207: if (f->flags & LONGFIELD) { ! 208: longField(f); /* this calls wgetLoc indirectly */ ! 209: ! 210: wmove(w, y, x); ! 211: field = *((char **)f->field); ! 212: for (got = 0; got < f->len; got++) { ! 213: if (c = *field) { ! 214: field++; ! 215: waddch(w, c); ! 216: } ! 217: else ! 218: waddch(w, ' '); ! 219: } ! 220: ! 221: /* ! 222: * Doing touchwin here makes a wierd flashing ! 223: * when there are many long fields. ! 224: * Set a switch instead. ! 225: */ ! 226: needsTouch = 1; ! 227: wrefresh(w); ! 228: return(savC); /* return the last thing returned by wgetLoc */ ! 229: } ! 230: ! 231: showHelp(f->help); ! 232: ! 233: wmove(w, y, x); ! 234: ! 235: for (state = got = 0; got < f->len; ) { ! 236: wrefresh(w); ! 237: c = wgetChr(w); ! 238: /* ! 239: * Up Arrow key is esc [ A ! 240: * on some systems and ! 241: * esc A on others. ! 242: */ ! 243: if (state) { /* got an escape */ ! 244: switch (c) { ! 245: case '[': ! 246: continue; ! 247: case 'A': ! 248: c = CTRL('P'); ! 249: break; ! 250: case 'B': ! 251: c = CTRL('N'); ! 252: break; ! 253: case 'C': ! 254: c = CTRL('F'); ! 255: break; ! 256: case 'D': ! 257: c = CTRL('B'); ! 258: break; ! 259: } ! 260: state = 0; ! 261: } ! 262: ! 263: switch (c) { ! 264: case CTRL('['): ! 265: state = 1; ! 266: continue; ! 267: case '\r': /* close out line */ ! 268: case '\n': ! 269: field[got] = '\0'; ! 270: for (; got < f->len; got++) ! 271: waddch(w, ' '); ! 272: continue; ! 273: case '\b': /* backspace */ ! 274: if (!got) ! 275: continue; ! 276: got--; ! 277: wmove(w, y, --x); ! 278: case CTRL('D'): ! 279: case 127: /* delete key */ ! 280: if (!field[got]) ! 281: continue; ! 282: for (i = got; c = field[i] = field[i + 1]; i++) ! 283: waddch(w, c); ! 284: waddch(w, ' '); ! 285: ! 286: wmove(w, y, x); ! 287: continue; ! 288: case CTRL('B'): /* back one char */ ! 289: if (!got) ! 290: continue; ! 291: wmove(w, y, --x); ! 292: got--; ! 293: continue; ! 294: case CTRL('P'): /* go to previous field */ ! 295: case '\t': /* go to next field with verify */ ! 296: case CTRL('N'): /* go to next field */ ! 297: case CTRL('Z'): /* end of screen */ ! 298: wrefresh(w); ! 299: return (c); ! 300: case CTRL('C'): /* Give user a chance to kill */ ! 301: userCtlc(); ! 302: continue; ! 303: case CTRL('A'): /* beginning of line */ ! 304: wmove(w, y = f->row, x = f->col); ! 305: got = 0; ! 306: continue; ! 307: case CTRL('E'): /* end of line */ ! 308: while (field[got]) { ! 309: got++; ! 310: x++; ! 311: } ! 312: while (got >= f->len) { /* don't trigger end of field */ ! 313: got--; ! 314: x--; ! 315: } ! 316: wmove(w, y, x); ! 317: continue; ! 318: case CTRL('F'): /* forward one char */ ! 319: if (!(c = field[got])) ! 320: continue; ! 321: default: ! 322: waddch(w, c); ! 323: x++; ! 324: field[got++] = c; ! 325: c = 0; ! 326: } ! 327: } ! 328: field[got] = '\0'; ! 329: wrefresh(w); ! 330: return (c); ! 331: } ! 332: ! 333: /* ! 334: * Show all default items. ! 335: */ ! 336: void ! 337: wshowDefs(w, data, fields) WINDOW *w; backGrnd *data; loc *fields; ! 338: { ! 339: register loc *f; ! 340: ! 341: wshowBak(w, data); ! 342: ! 343: for (f = fields; NULL != f->field; f++) ! 344: wgetLoc(w, f, 1); ! 345: } ! 346: ! 347: /* ! 348: * Print background and get all fields. ! 349: */ ! 350: void ! 351: wscnDriv(w, data, fields) WINDOW *w; backGrnd *data; loc *fields; ! 352: { ! 353: wclear(w); ! 354: wshowBak(w, data); ! 355: wgetAll(w, fields); ! 356: } ! 357: ! 358: /* ! 359: * Get all fields on a given screen. ! 360: * allow emacs style navagation. ! 361: */ ! 362: void ! 363: wgetAll(w, fields) WINDOW *w; loc *fields; ! 364: { ! 365: register loc *f; ! 366: char c; ! 367: ! 368: for (c = 0; c != CTRL('Z'); ) { ! 369: for (f = fields; (c != CTRL('Z')) && (NULL != f->field); f++) { ! 370: switch (c = wgetLoc(w, f, 0)) { ! 371: case CTRL('Z'): ! 372: if (w != stdscr) { ! 373: savC = c; ! 374: return; ! 375: } ! 376: break; ! 377: case CTRL('N'): ! 378: /* at end down with true field */ ! 379: if ((f[1].field == NULL) && (w != stdscr)) { ! 380: savC = c; ! 381: return; ! 382: } ! 383: break; ! 384: case CTRL('P'): ! 385: for (;;) { ! 386: if (f == fields) { /* wrap */ ! 387: /* back out of true field */ ! 388: if (w != stdscr) { ! 389: savC = c; ! 390: return; ! 391: } ! 392: while (NULL != f->field) ! 393: f++; ! 394: } ! 395: if (!((--f)->flags & READONLY)) ! 396: --f; ! 397: break; ! 398: } ! 399: break; ! 400: default: ! 401: switch ((*f->verify)(fieldPtr(f))) { ! 402: case -2: ! 403: savC = ' '; ! 404: return; ! 405: case -1: ! 406: if (f->skipf) { ! 407: f += f->skipf; ! 408: break; ! 409: } ! 410: case 0: ! 411: f--; ! 412: break; ! 413: } ! 414: } ! 415: } ! 416: } ! 417: ! 418: /* verify all fields */ ! 419: for (f = fields; NULL != f->field; f++) { ! 420: switch ((*f->verify)(fieldPtr(f))) { ! 421: case -2: ! 422: return; ! 423: case -1: ! 424: if (f->skipf) { ! 425: f += f->skipf; ! 426: break; ! 427: } ! 428: case 0: ! 429: c = wgetLoc(w, f, 0); ! 430: f--; ! 431: break; ! 432: } ! 433: } ! 434: } ! 435: ! 436: /* ! 437: * Get a field by field location. ! 438: */ ! 439: wgetField(w, table, field) WINDOW *w; loc *table; char *field; ! 440: { ! 441: register loc *f; ! 442: ! 443: for (f = table; NULL != f->field; f++) ! 444: if (field == fieldPtr(f)) ! 445: return (wgetLoc(w, f, 0)); ! 446: fatal("Invalid use of getField"); ! 447: } ! 448: ! 449: /* ! 450: * Put a field by field location. ! 451: */ ! 452: void ! 453: wputField(w, table, field) WINDOW *w; loc *table; char *field; ! 454: { ! 455: register loc *f; ! 456: ! 457: for (f = table; NULL != f->field; f++) ! 458: if (field == fieldPtr(f)) { ! 459: wgetLoc(w, f, 2); ! 460: return; ! 461: } ! 462: fatal("Invalid use of putField"); ! 463: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.