|
|
1.1 ! root 1: /* ! 2: * screen.c 1.4 ! 3: * ! 4: * Screen Handling Functions for Spreadsheet Program `vis' ! 5: * ! 6: * A. F. Gettier ! 7: * Bell Laboratories ! 8: * Update made 11/1/82 11:13:42 ! 9: * Retrieved 11/15/82 13:22:44 ! 10: */ ! 11: #include <math.h> ! 12: #include <stdio.h> ! 13: #include <signal.h> ! 14: #include "curses.h" ! 15: #include "vis.h" ! 16: ! 17: extern int LINES, COLS; ! 18: extern struct qheader Fixup; ! 19: ! 20: int Width=DEFWIDTH; ! 21: int Scale=DEFSCALE; ! 22: ! 23: extern struct colhdr Col; ! 24: extern struct rowhdr Row; ! 25: ! 26: /* ! 27: * Initialize the screen ! 28: */ ! 29: void ! 30: scrinit() ! 31: { ! 32: extern quit(); ! 33: ! 34: initscr(); ! 35: ! 36: savetty(); ! 37: signal(SIGINT, quit); ! 38: ! 39: noecho(); ! 40: crmode(); ! 41: clear(); ! 42: ! 43: /* ! 44: * Set up the Heading ! 45: */ ! 46: ! 47: setheading(); ! 48: ! 49: /* ! 50: * Print out the heading ! 51: */ ! 52: ! 53: prheading(); ! 54: } ! 55: /* ! 56: * Set the headings to the initial setting ! 57: */ ! 58: setheading() ! 59: { ! 60: int i; ! 61: int size; ! 62: struct collabel **c1; ! 63: struct rowlabel **r1; ! 64: ! 65: /* ! 66: * Get the number of Rows ! 67: */ ! 68: size = LINES - 5; ! 69: rowexpand( size ); ! 70: /* ! 71: * Fix the print Positions Stuff ! 72: */ ! 73: r1 = Row.table; ! 74: for ( i=0; i<size; i++ ) { ! 75: r1[i]->position = i+3; ! 76: } ! 77: for ( i=size; i<Row.size; i++ ) { ! 78: r1[i]->position = 0; ! 79: } ! 80: /* ! 81: * Get the number of Columns ! 82: */ ! 83: size = ( COLS - 6 ) / (Width + 1); ! 84: colexpand( size ); ! 85: /* ! 86: * Fix the print Positions Stuff ! 87: */ ! 88: c1 = Col.table; ! 89: for ( i=0; i<size; i++ ) { ! 90: c1[i]->position = i * (Width + 1) + 6; ! 91: c1[i]->cell = i; ! 92: } ! 93: for ( i=size; i<Col.size; i++ ) { ! 94: c1[i]->position = 0; ! 95: c1[i]->cell = i; ! 96: } ! 97: } ! 98: /* ! 99: * Print the heading ! 100: */ ! 101: void ! 102: prheading() ! 103: { ! 104: int i, j, k, l; ! 105: struct collabel **c1; ! 106: struct rowlabel **r1; ! 107: /* ! 108: * Print the Frame ! 109: */ ! 110: erase(); ! 111: move( 2, 4 ); ! 112: printw( "------------------------------------" ); ! 113: printw( "----------------------------------------" ); ! 114: for ( i=3; i<(LINES-2); i++ ) { ! 115: move( i, 4 ); ! 116: printw( "|" ); ! 117: } ! 118: /* ! 119: * Print the Labels ! 120: */ ! 121: r1 = Row.table; ! 122: c1 = Col.table; ! 123: /* ! 124: * First the numbers on the Vertical ! 125: */ ! 126: for ( i=0; i<Row.size; i++ ) { ! 127: if ( r1[i]->position < 0 ) continue; ! 128: if ( r1[i]->position == 0 ) break; ! 129: move( r1[i]->position, 1 ); ! 130: printw( "%d", i+1 ); ! 131: } ! 132: /* ! 133: * and the letters on the Horizontal ! 134: */ ! 135: l = i = 0; ! 136: while ( i < Col.size && c1[i]->position+c1[i]->width+1 < COLS ) { ! 137: if ( c1[i]->position <= 0 ) { ! 138: i++; ! 139: if ( l == 0 ) continue; ! 140: else break; ! 141: } ! 142: l = 0; ! 143: move( 1, c1[i]->position + c1[i]->width/2 ); ! 144: j = i++; ! 145: k = j / 26; ! 146: if ( k > 0 ) k = k + 'A' - 1; ! 147: else k = ' '; ! 148: j = j % 26 + 'A'; ! 149: printw( "%c%c", k, j ); ! 150: } ! 151: } ! 152: ! 153: /* ! 154: * Print the Node ! 155: */ ! 156: prnode( node ) ! 157: struct node *node; ! 158: { ! 159: int i, j; ! 160: struct collabel **c1; ! 161: struct rowlabel **r1; ! 162: ! 163: /* ! 164: * Get the print position ! 165: * ! 166: * ! 167: * get the correct row ! 168: */ ! 169: r1 = Row.table; ! 170: i = node->row; ! 171: if ( i >= Row.size || r1[i]->position <= 0 ) return; ! 172: /* ! 173: * get the correct Column ! 174: */ ! 175: c1 = Col.table; ! 176: j = node->col; ! 177: if ( j >= Col.size || c1[j]->position <= 0 ) return; ! 178: /* ! 179: * Print the node ! 180: */ ! 181: move( r1[i]->position, c1[j]->position ); ! 182: noutput( node, c1[j]->width, c1[j]->scale ); ! 183: } ! 184: /* ! 185: * output a single element ! 186: * assume the cursor is positioned ! 187: */ ! 188: noutput( node, wid, scale ) ! 189: struct node *node; ! 190: int wid, scale; ! 191: { ! 192: int i; ! 193: char tbuf[80], *x; ! 194: ! 195: switch( node->type ) { ! 196: case UNDEF: ! 197: for ( i=0; i<wid; i++ ) tbuf[i] = ' '; ! 198: i = wid/2; ! 199: tbuf[i++] = '*'; ! 200: tbuf[i] = '*'; ! 201: tbuf[wid] = '\0'; ! 202: break; ! 203: case UNRES: ! 204: for ( i=0; i<wid; i++ ) tbuf[i] = ' '; ! 205: i = wid/2; ! 206: tbuf[i++] = '?'; ! 207: tbuf[i] = '?'; ! 208: tbuf[wid] = '\0'; ! 209: break; ! 210: case NUM: ! 211: if ( (x=dtoa( node->value, wid, scale )) == 0 ) { ! 212: for ( i=0; i<wid; i++ ) tbuf[i] = '#'; ! 213: tbuf[wid] = '\0'; ! 214: } ! 215: else (void)strcpy( tbuf, x ); ! 216: break; ! 217: case STRING: ! 218: (void)strncpy( tbuf, node->svalue, wid ); ! 219: for ( i=strlen( tbuf ); i<wid; i++ ) tbuf[i] = ' '; ! 220: tbuf[wid] = '\0'; ! 221: break; ! 222: } ! 223: printw( "%s", tbuf ); ! 224: } ! 225: ! 226: /* dtoa.c ! 227: * S. Coffin, BTL Dept. 43372, FJ 1A110, x5151 ! 228: * Apr. 15, 1982 ! 229: * ! 230: * Converts a double precision float to a right-justified ! 231: * printable character string according to the parameters ! 232: * size = total field width desired ! 233: * scale = number of digits to the right of the decimal ! 234: * ! 235: * returns a pointer to the string. If the size given ! 236: * is too small for the number, the routine attempts ! 237: * to use "e" notation. If it still will not fit, NULL ! 238: * is returned. ! 239: */ ! 240: ! 241: char * ! 242: dtoa( input, size, scale ) ! 243: double input; ! 244: int size, scale; ! 245: { ! 246: static char output[80]; ! 247: char pattern[80]; ! 248: int j=0, i; ! 249: ! 250: output[0] = '\0'; ! 251: ! 252: /* get a sample string */ ! 253: (void)sprintf( pattern, "%-39.39lf", input ); ! 254: ! 255: /* if the number is near zero, then try "e" notation */ ! 256: j=0; ! 257: while( (pattern[j]=='0' || pattern[j]=='.') && pattern[j++]!='\0' ); ! 258: ! 259: if( j < size && j > size/2 ) pattern[size] = '\0'; ! 260: else if ( j>size/2 && size>=9 ) ! 261: (void)sprintf( pattern, "%9.2e", input ); ! 262: else { ! 263: /* not too near zero, so find the decimal point */ ! 264: j=0; ! 265: while( pattern[j++] != '.' ); ! 266: ! 267: /* truncate it to the scale */ ! 268: if( scale == 0 ) pattern[j-1] = '\0'; ! 269: else pattern[j+scale] = '\0'; ! 270: ! 271: /* if its still too big, try "e" notation */ ! 272: if( (j-1 > size) || (j+scale > size) ) ! 273: (void)sprintf( pattern, "%9.2e",input); ! 274: } ! 275: ! 276: /* is it still too big? */ ! 277: i=strlen(pattern); ! 278: if( i <= size ) { ! 279: /* ok, so right-justify the result, and return */ ! 280: for( j = 0; j < (size-i); j++ ) output[j]=' '; ! 281: output[j] = '\0'; ! 282: strcat( output, pattern ); ! 283: return( output ); ! 284: } ! 285: else return( NULL ); ! 286: } ! 287: ! 288: /* ! 289: * Copy out the Standard screen to a file ! 290: */ ! 291: copyfile( fp ) ! 292: FILE *fp; ! 293: { ! 294: int i, j, k; ! 295: char bf[150]; ! 296: char *tbf; ! 297: (void)fprintf( fp, "\n\n" ); ! 298: for ( i=1; i<LINES-2; i++ ) { ! 299: ! 300: tbf = bf; ! 301: ! 302: j = 0; ! 303: k = COLS - 2; ! 304: while ( j < COLS ) { ! 305: bf[j] = (char)(stdscr->_y[i][j]); ! 306: if ( bf[j] > ' ' ) k = j; ! 307: j++; ! 308: } ! 309: bf[k+1] = '\0'; ! 310: (void)fprintf( fp, "%s\n", bf ); ! 311: } ! 312: (void)fprintf( fp, "\n\n" ); ! 313: } ! 314: /* ! 315: * reset the global scale ! 316: */ ! 317: setscale( n ) ! 318: int n; ! 319: { ! 320: int i; ! 321: struct collabel **c1; ! 322: Scale = n; ! 323: /* ! 324: * Reset the individual headings ! 325: */ ! 326: c1 = Col.table; ! 327: for ( i=0; i<Col.size; i++ ) { ! 328: c1[i]->scale = Scale; ! 329: } ! 330: /* ! 331: * Repaint the screen ! 332: */ ! 333: prheading(); ! 334: repaint(); ! 335: } ! 336: /* ! 337: * reset the global width ! 338: */ ! 339: setwidth( n ) ! 340: int n; ! 341: { ! 342: int i; ! 343: struct collabel **c1; ! 344: ! 345: Width = n; ! 346: /* ! 347: * Reset the individual headings ! 348: */ ! 349: c1 = Col.table; ! 350: for ( i=0; i<Col.size; i++ ) { ! 351: c1[i]->width = Width; ! 352: } ! 353: fixcolheading(); ! 354: /* ! 355: * Repaint the screen ! 356: */ ! 357: prheading(); ! 358: repaint(); ! 359: } ! 360: /* ! 361: * reset an individual scale ! 362: */ ! 363: isetscale( col, n ) ! 364: int col, n; ! 365: { ! 366: struct collabel **c1; ! 367: /* ! 368: * Make sure it's valid ! 369: */ ! 370: if ( col > Col.size ) colexpand( col ); ! 371: if ( col < 0 ) { ! 372: char bfr[64]; ! 373: lexinit(); ! 374: unput( '\n' ); ! 375: (void)sprintf( bfr, "Attempt to change scale of column %d", ! 376: col ); ! 377: yyerror( bfr ); ! 378: return; ! 379: } ! 380: /* ! 381: * Reset the individual headings ! 382: */ ! 383: c1 = Col.table; ! 384: c1[col]->scale = n; ! 385: /* ! 386: * Repaint the screen ! 387: */ ! 388: prheading(); ! 389: repaint(); ! 390: } ! 391: /* ! 392: * reset an individual width ! 393: */ ! 394: isetwidth( col, n ) ! 395: int col, n; ! 396: { ! 397: struct collabel **c1; ! 398: ! 399: /* ! 400: * Make sure it's valid ! 401: */ ! 402: if ( col > Col.size ) colexpand( col ); ! 403: if ( col < 0 ) { ! 404: char bfr[64]; ! 405: lexinit(); ! 406: unput( '\n' ); ! 407: (void)sprintf( bfr, "Attempt to change scale of column %d", ! 408: col ); ! 409: yyerror( bfr ); ! 410: return; ! 411: } ! 412: /* ! 413: * Reset the individual headings ! 414: */ ! 415: c1 = Col.table; ! 416: c1[col]->width = n; ! 417: fixcolheading(); ! 418: /* ! 419: * Repaint the screen ! 420: */ ! 421: prheading(); ! 422: repaint(); ! 423: } ! 424: /* ! 425: * Repaint the Screen ! 426: */ ! 427: repaint() ! 428: { ! 429: int i, j; ! 430: struct node *n; ! 431: struct collabel **c1; ! 432: struct rowlabel **r1; ! 433: ! 434: r1 = Row.table; ! 435: c1 = Col.table; ! 436: for ( i=0; i<Row.size; i++ ) { ! 437: if( r1[i]->position == 0 ) break; ! 438: if( r1[i]->position < 0 ) continue; ! 439: n = r1[i]->next; ! 440: while ( n != 0 ) { ! 441: j = n->col; ! 442: if( c1[j]->position == 0 ) break; ! 443: if( c1[j]->position > 0 ) prnode( n ); ! 444: n = n->next; ! 445: } ! 446: } ! 447: } ! 448: /* ! 449: * Set the new Row headings ! 450: */ ! 451: fixrowheading() ! 452: { ! 453: int i, start; ! 454: int size; ! 455: struct rowlabel **r1; ! 456: ! 457: size = LINES - 5; ! 458: /* ! 459: * Get the Starting position ! 460: */ ! 461: r1 = Row.table; ! 462: for ( start=0; start<Row.size; start++ ) ! 463: if ( r1[start]->position >= 0 ) break; ! 464: /* ! 465: * Get more rows if needed ! 466: */ ! 467: rowexpand( start + size + 1 ); ! 468: r1 = Row.table; ! 469: /* ! 470: * Fix the print Positions Stuff ! 471: */ ! 472: for ( i=0; i<size; i++ ) { ! 473: r1[i+start]->position = i+3; ! 474: } ! 475: for ( i=size+start; i<Row.size; i++ ) { ! 476: r1[i]->position = 0; ! 477: } ! 478: } ! 479: /* ! 480: * Set the new Col headings ! 481: */ ! 482: fixcolheading() ! 483: { ! 484: int i, j, cpos, start; ! 485: struct collabel **c1; ! 486: /* ! 487: * Find the First cell to print ! 488: */ ! 489: c1 = Col.table; ! 490: for ( start=0; start<Col.size; start++ ) { ! 491: if ( c1[start]->position >= 0 ) break; ! 492: } ! 493: /* ! 494: * Fix the print Positions Stuff ! 495: */ ! 496: cpos = 6; ! 497: for ( i=start; i<Col.size; i++ ) { ! 498: c1[i]->position = cpos; ! 499: cpos += c1[i]->width + 1; ! 500: if ( cpos > COLS ) { ! 501: c1[i]->position = 0; ! 502: } ! 503: } ! 504: i = (COLS - cpos ) / ( Width + 1 ); ! 505: j = Col.size; ! 506: colexpand( i+j+1 ); ! 507: c1 = Col.table; ! 508: for ( i=j; i<Col.size; i++ ) { ! 509: c1[i]->position = cpos; ! 510: cpos += c1[i]->width + 1; ! 511: if ( cpos > COLS ) { ! 512: c1[i]->position = 0; ! 513: } ! 514: } ! 515: } ! 516: /* ! 517: * zero out all the screen stuff ! 518: */ ! 519: zeroscreen() ! 520: { ! 521: initscr(); ! 522: erase(); ! 523: Row.size = 0; ! 524: Col.size = 0; ! 525: Width = DEFWIDTH; ! 526: Scale = DEFSCALE; ! 527: /* ! 528: * Set up the Heading ! 529: */ ! 530: setheading(); ! 531: /* ! 532: * Print out the heading ! 533: */ ! 534: prheading(); ! 535: } ! 536: ! 537: /* ! 538: * SCROLLING ! 539: */ ! 540: scrup( n ) ! 541: int n; ! 542: { ! 543: int i, j, start; ! 544: struct rowlabel **r1; ! 545: ! 546: r1 = Row.table; ! 547: /* ! 548: * Get the starting position ! 549: */ ! 550: for ( start=0; start<Row.size; start++ ) { ! 551: if ( r1[start]->position >= 0 ) break; ! 552: } ! 553: /* ! 554: * Fix the offending rows ! 555: */ ! 556: i = start - n; ! 557: if ( i < 0 ) i = 0; ! 558: for ( j=i; j<Row.size; j++ ) { ! 559: r1[j]->position = 0; ! 560: } ! 561: /* ! 562: * Redraw the screen ! 563: */ ! 564: fixrowheading(); ! 565: prheading(); ! 566: repaint(); ! 567: } ! 568: scrdown( n ) ! 569: int n; ! 570: { ! 571: int i, start; ! 572: struct rowlabel **r1; ! 573: ! 574: r1 = Row.table; ! 575: /* ! 576: * Get the starting position ! 577: */ ! 578: for ( start=0; start<Row.size; start++ ) { ! 579: if ( r1[start]->position >= 0 ) break; ! 580: } ! 581: /* ! 582: * Increase number of rows, if needed ! 583: */ ! 584: rowexpand( start + n + 1 ); ! 585: r1 = Row.table; ! 586: /* ! 587: * Get rid of the offending rows ! 588: */ ! 589: move( 3, 0 ); ! 590: for ( i=0; i<n; i++ ) { ! 591: ! 592: r1[start+i]->position = -1; ! 593: ! 594: } ! 595: /* ! 596: * Redraw the screen ! 597: */ ! 598: fixrowheading(); ! 599: prheading(); ! 600: repaint(); ! 601: } ! 602: scrleft( n ) ! 603: int n; ! 604: { ! 605: int i, j, start; ! 606: struct collabel **c1; ! 607: ! 608: c1 = Col.table; ! 609: /* ! 610: * Get the starting position ! 611: */ ! 612: for ( start=0; start<Col.size; start++ ) { ! 613: if ( c1[start]->position >= 0 ) break; ! 614: } ! 615: /* ! 616: * Fix the offending rows ! 617: */ ! 618: i = start - n; ! 619: if ( i < 0 ) i = 0; ! 620: for ( j=i; j<Col.size; j++ ) { ! 621: c1[j]->position = 0; ! 622: } ! 623: /* ! 624: * Redraw the screen ! 625: */ ! 626: fixcolheading(); ! 627: prheading(); ! 628: repaint(); ! 629: } ! 630: scrright( n ) ! 631: int n; ! 632: { ! 633: int i, start; ! 634: struct collabel **c1; ! 635: ! 636: c1 = Col.table; ! 637: /* ! 638: * Get the starting position ! 639: */ ! 640: for ( start=0; start<Col.size; start++ ) { ! 641: if ( c1[start]->position >= 0 ) break; ! 642: } ! 643: /* ! 644: * Increase number of cols, if needed ! 645: */ ! 646: colexpand( start + n + 1 ); ! 647: c1 = Col.table; ! 648: /* ! 649: * Get rid of the offending rows ! 650: */ ! 651: for ( i=0; i<n; i++ ) { ! 652: c1[start+i]->position = -1; ! 653: } ! 654: /* ! 655: * Redraw the screen ! 656: */ ! 657: fixcolheading(); ! 658: prheading(); ! 659: repaint(); ! 660: } ! 661: ! 662: ! 663: void beep(){}
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.