1: 
   2: /*-----------------------------------------------------------------------------
   3:  *  ipress - most of the code directly dependent on interpress used by dipress
   4:  *	     to produce an interpress file from device independent troff
   5:  *	     intermediate code.
   6:  *
   7:  *  William LeFebvre
   8:  *
   9:  * Copyright (c) 1984, 1985 Xerox Corp.
  10:  *
  11:  * History:
  12:  *	John Mellor-Crummey 28-aug-1985 restructuring and minor modifications
  13:  *
  14:  *	ed flint 10-may-1985	coerce device.num_char_wid to unsigned char, change
  15:  *				ch argument in outputChar to unsigned int
  16:  *				since we now have > 128 special characters
  17:  *---------------------------------------------------------------------------*/
  18: 
  19: 
  20: #include <stdio.h>
  21: #include <ctype.h>
  22: #include <signal.h>
  23: #include <math.h>
  24: #include <sys/types.h>
  25: #include <sys/file.h>
  26: #include <sys/stat.h>
  27: 
  28: #include "deviceinfo.h" /* typesetter characteristics */
  29: 
  30: #include "iptokens.h"   /* \					*/
  31: #include "literal.h"    /*  > interface levels for interpress	*/
  32: #include "operator.h"   /* /					*/
  33: 
  34: #include "defs.h"   /* constant and macro definitions */
  35: #include "externs.h"    /* declarations for global variables */
  36: 
  37: 
  38: 
  39: /* initialize device */
  40: initDevice()
  41: {
  42:     int  lines = 0;
  43:     int  timapf;
  44:     int  ret;
  45:     register char *ptr;
  46:     register char **ipp;
  47:     register char **trp;
  48:     char temp[60];
  49:     struct stat stbuf;
  50: 
  51:     if (dbg) printf("initDevice called\n");
  52: 
  53:     /* start the preamble */
  54:     ip_select(outputfile);
  55:     /* special master instructions go here... */
  56:     Op(beginBlock);
  57:     Op(beginBody);
  58: 
  59:     /* save scaling transform that uses a mica co-ordinate system */
  60:     AppendRational(1L, 100000);
  61:     Op(scale);
  62:     AppendInteger((long) F_transform);
  63:     Op(fset);
  64: 
  65:     /* select file that holds page bodies */
  66:     ip_select(pagebodyfile);
  67: 
  68:     /* open file that maps troff names to interpress names */
  69:     (void) sprintf(temp, "%s/dev%s/interpress-fonts", fontdirectory, devicename);
  70:     if ((timapf = open(temp, O_RDONLY,0)) == -1)
  71:         reportError(QUIT, "can't open %s (%s)", temp, sys_errlist[errno]);
  72: 
  73:     /* read in the whole thing */
  74:     ret = fstat(timapf, &stbuf);
  75:     if (dbg) printf("stat returned %d, errno %d\n", ret, errno);
  76:     timap = malloc((unsigned)(stbuf.st_size + 1));
  77:     if (dbg) printf("reading %d bytes from timapf\n", stbuf.st_size);
  78:     ret = read(timapf, timap, (int)stbuf.st_size);
  79:     if (dbg) printf("read returned %d, errno %d, timapf %d\n", ret, errno, timapf);
  80:     timap[(int)stbuf.st_size] = '\0';
  81:     (void) close(timapf);
  82: 
  83:     /* count the newlines */
  84:     if (dbg) printf("pointer starts at %08x ... ", timap);
  85: 
  86:     for (ptr = timap; *ptr != '\0'; ptr++)
  87:         if (*ptr == '\n') lines++;
  88: 
  89:     if (dbg) printf("ends at %08x\n", ptr);
  90:     if (dbg) printf("found %d lines\n", lines);
  91: 
  92:     /* allocate the mapping arrays */
  93:     trp = trname = (char **)malloc((unsigned)(lines * 2 * sizeof(char *)));
  94:     ipp = ipname = trname + lines;
  95: 
  96:     /* break out the strings and store pointers in the arrays */
  97:     ptr = timap;
  98:     mapcnt = 0;
  99:     while (*ptr)
 100:     {
 101:         if (dbg) printf("loop: ptr = %08x, *ptr = %c\n", ptr, *ptr);
 102:         *trp++ = ptr;
 103:         while (!white(*ptr)) ptr++;
 104:         *ptr++ = '\0';
 105:         while (white(*ptr)) ptr++;
 106:         *ipp++ = ptr;
 107:         while (*++ptr != '\n') /* nothing */;
 108:         *ptr++ = '\0';
 109:         mapcnt++;
 110:     }
 111: 
 112:     if (dbg)
 113:     {
 114:         int i;
 115: 
 116:         for (i = 0; i < lines; i++)
 117:             printf("%s\t%s\n", trname[i], ipname[i]);
 118:     }
 119: 
 120:     /* reset vertical and horizontal positions */
 121:     hor_pos = ver_pos = old_hor = old_ver = 0;
 122: 
 123:     /* reset the font information */
 124:     bzero((char *) currfonts, sizeof(currfonts));
 125: }
 126: 
 127: setScale(spi)       /* set resolution */
 128: 
 129: int spi;
 130: 
 131: {
 132:     /* set the scaling variable used in all x and y calculations */
 133:     scale = floor(2540.0 / (double)spi + 0.5);
 134:     if (dbg) printf("setScale(%d) sets scale to %e\n", spi, scale);
 135: 
 136:     /*
 137: 	     *  Set the drawing scale based on the scale.  This factor is applied to
 138: 	     *	all points drawn in the bitmap for graphical objects.  It is scaled
 139: 	     *	down from micas to 508 dpi so that the bitmaps aren't of unwieldy
 140: 	     *	size, but still retain enough information to look decent on a good
 141: 	     *	device.  508/2540 == 0.2
 142: 	     */
 143:     drawscale = scale * .2;
 144:     if (dbg) printf("setScale(%d) sets drawscale to %e\n", spi, drawscale);
 145: }
 146: 
 147: pushCurrentEnv()    /* begin a new block */
 148: {
 149:     statep->ssize = size;
 150:     statep->sfont = font;
 151:     statep->shorig = hor_orig;
 152:     statep->svorig = ver_orig;
 153:     statep->shpos = hor_pos;
 154:     statep->svpos = ver_pos;
 155:     hor_orig = hor_pos;
 156:     ver_orig = ver_pos;
 157:     hor_pos = ver_pos = 0;
 158:     if (statep++ >= state + MAXSTATE)
 159:     {
 160:         reportError(QUIT, "{ nested too deep");
 161:     }
 162:     hor_pos = ver_pos = 0;
 163: }
 164: 
 165: popSavedEnv()   /* pop to previous state */
 166: {
 167:     if (--statep < state)
 168:     {
 169:         reportError(QUIT, "extra }");
 170:     }
 171:     size = statep->ssize;
 172:     font = statep->sfont;
 173:     hor_pos = statep->shpos;
 174:     ver_pos = statep->svpos;
 175:     hor_orig = statep->shorig;
 176:     ver_orig = statep->svorig;
 177: }
 178: 
 179: newpage(n)      /* new page */
 180: int n;
 181: {
 182:     int i;
 183:     char buff[15];
 184: 
 185:     /* print any pending bitmap */
 186: 
 187:     /* terminate previous page if outputting */
 188:     if (outputflag)
 189:     {
 190:         print_bitmap();
 191:         Op(endBody);
 192:     }
 193:     else flush_bitmap();
 194: 
 195:     /* reset vertical positions */
 196:     ver_pos = old_ver = 0;
 197: 
 198:     /* check new page number against those found in the nPageRanges */
 199:     if (nPageRanges == 0)
 200:     {
 201:         /* no -o specified -- do all pages */
 202:         outputflag = 1;
 203:     }
 204:     else
 205:     {
 206:         /* see if new page has been selected for output */
 207:         outputflag = 0;
 208:         for (i = 0; i < nPageRanges; i++)
 209:         {
 210:             if ((n >= pagerange[i][0]) && (n <= pagerange[i][1]))
 211:             {
 212:                 outputflag = 1;
 213:                 break;
 214:             }
 215:         }
 216:     }
 217: 
 218:     /* start new page */
 219:     if (outputflag)
 220:     {
 221:         Op(beginBody);
 222:         (void) sprintf(buff, "Page %d", n);
 223:         AppendComment(buff);
 224:         Fget(F_transform);
 225:         Op(concatt);
 226:         AppendInteger(2L);
 227:         AppendInteger((long) I_strokeEnd);
 228:         Op(iset);
 229:     }
 230: 
 231:     /* font/size no longer valid -- force a new assignment */
 232:     oldftsz = -1;
 233: }
 234: 
 235: newLine()       /* new line (no vertical motion implied) */
 236: {
 237:     if (dbg == 3)
 238:         putchar('\n');
 239:     flushbuff();
 240:     endcorrect();
 241:     hor_pos = 0;
 242:     virgin_line = 1;
 243: }
 244: 
 245: internalSize(number)        /* convert integer to internal size number */
 246: int number;
 247: {
 248:     int index;
 249: 
 250:     if (number >= pointsizeTab[device.num_sizes - 1])
 251:     {
 252:         /* larger than largest -- use largest */
 253:         return(device.num_sizes-1);
 254:     }
 255:     else if (number <= pointsizeTab[0])
 256:     {
 257:         /* smaller than smallest -- use smallest */
 258:         return(0);
 259:     }
 260: 
 261:     /* else find the size in pointsizeTab and return index */
 262:     for (index = 0; number > pointsizeTab[index]; index++);
 263:     return(index);
 264: }
 265: 
 266: 
 267: 
 268: 
 269: 
 270: /* handle device stop command */
 271: resetDevice()
 272: {
 273:     int amt;
 274:     static int is_reset = 0;
 275:     char bigbuff[1024];
 276: 
 277:     if (is_reset) return; /* ignore multiple resets */
 278: 
 279:     print_bitmap();
 280: 
 281:     /* this is the absolute last thing that we do */
 282:     /* wrap up the preamble and the body */
 283:     ip_select(outputfile);
 284:     Op(endBody);
 285:     ip_select(pagebodyfile);
 286:     Op(endBody);
 287:     Op(endBlock);
 288:     ip_close();         /* close the body */
 289: 
 290:     /*
 291: 	     *  Reopen the body and copy it onto the end of the real file (which is
 292: 	     *	where we have been building the preamble).  We don't need to ip_flush
 293: 	     *	the preamble since that is done everytime we ip_select the body.
 294: 	     *	Conveniently enough, "tempfilename" still holds the name of the body
 295: 	     *	temporary.
 296: 	     */
 297:     pagebodyfile = open(tempfilename, O_RDONLY,0);
 298:     while ((amt = read(pagebodyfile, bigbuff, sizeof(bigbuff))) != 0)
 299:     {
 300:         (void) write(outputfile, bigbuff, amt);
 301:     }
 302: 
 303:     /* close and unlink the body temporary file */
 304:     (void) close(pagebodyfile);
 305:     (void) unlink(tempfilename);
 306: 
 307:     /* send the file off to the printer */
 308:     tempfilename[strlen(tempfilename) - 1] = '\0';
 309:     if (outputfile != 1)
 310:     {
 311:         IPprint(tempfilename);
 312:     }
 313: 
 314:     /* we are now reset */
 315:     is_reset = 1;
 316: }
 317: 
 318: outputString(character)     /* print a "funny" character */
 319: char *character;
 320: {
 321:     int i;
 322: 
 323:     if (!outputflag)
 324:         return;
 325:     if (dbg > 2) printf("\\(%s", character);
 326:     if (dbg > 3) putchar(' ');
 327:     for (i = 0; i < device.spec_char_num; i++)
 328:         if (strcmp(&specCharStrTab[specCharTab[i]], character) == 0)
 329:             break;
 330:     if (i < device.spec_char_num) {
 331:         /*	printf(" i = %d so i+128 = %d\n", i, i+128);	*/
 332:         outputChar((unsigned int) i + 128);
 333:     }
 334:     else {
 335:         if (dbg > 3)
 336:             printf("-- character not found");
 337:     }
 338: 
 339:     if (dbg > 2)
 340:         putchar('\n');
 341: }
 342: 
 343: outputChar(character)       /* put a character */
 344: unsigned int character;
 345: {
 346:     unsigned char *widp;    /* pointer to appropriate width table */
 347:     register char *codep;   /* pointer to appropriate table of codes */
 348:     register int i, old_font, fnt_index;
 349:     int j, value;
 350: 
 351:     if (!outputflag)
 352:         return;
 353: 
 354:     if (character <= 32)
 355:     {
 356:         if (dbg) printf("non-existent character 0%o\n", character);
 357:         charw = charWidthTab[font][0] * pointsizeTab[size-1] / device.width_units;
 358:         return;
 359:     }
 360:     character -= 32;
 361: 
 362:     old_font= font;
 363:     i = fontIndexTab[font][character] & 255;
 364:     if (i != 0)             /* it's on this font */
 365:     {
 366:         codep = charCodeTab[font];
 367:         widp = charWidthTab[font];
 368:     }
 369:     else if (specFontPos > 0)           /* on special (we hope) */
 370:     {
 371:         /* assertion:  i == 0 */
 372:         fnt_index= specFontPos;
 373:         for (j=0; j <= device.num_fonts; j++)
 374:         {
 375:             struct font_entry *fb;
 376: 
 377:             fnt_index= (fnt_index+1) % (device.num_fonts+1);
 378: 
 379:             if ((fb = fontPtr[fnt_index]) != NULL)
 380:             {
 381:                 if (fb->special_flag && (i = fontIndexTab[fnt_index][character] & 255) != 0)
 382:                 {
 383:                     codep = charCodeTab[fnt_index];
 384:                     widp = charWidthTab[fnt_index];
 385:                     setFont(fnt_index);
 386:                     break;
 387:                 }
 388:             }
 389:         }
 390:         /* assertion:  if j > device.num_fonts then i == 0 and character was not found */
 391:     }
 392: 
 393:     value= codep[i] & 255;
 394: 
 395:     if (i == 0 || value == 0)
 396:     {
 397:         if (dbg) printf("character not found 0%o\n", character+32);
 398:         return;
 399:     }
 400: 
 401:     /* remember this character's width */
 402:     /* This MUST be done before calling showchar */
 403:     charw = (widp[i] * pointsizeTab[size-1] + device.width_units/2) / device.width_units;
 404:     if (dbg == 3)
 405:     {
 406:         if (isprint(character+32))
 407:             putchar(character+32);
 408:     }
 409:     if (dbg > 3)
 410:     {
 411:         if (isprint(character+32))
 412:             printf("character %c %d\n", character+32, value);
 413:         else
 414:             printf("character %03o %d\n", character+32, value);
 415:     }
 416: 
 417:     if (value == 0377)
 418:     {
 419:         /* special escape to an extended code */
 420:         value = getexcode(i);
 421:     }
 422: 
 423:     if (dbg < 6)
 424:         showchar(value);
 425: 
 426:     if (font != old_font)
 427:     {
 428:         setFont(old_font);
 429:     }
 430: }
 431: 
 432: 
 433: setPointSize(n)     /* set point size to n */
 434: 
 435: int n;          /* internal value:  index into pointsizeTab */
 436: 
 437: {
 438:     size = n;
 439:     ftsz = ((long)font << 16) | ((long)size);
 440: }
 441: 
 442: setFont(n)      /* set font to n */
 443: 
 444: int n;          /* internal index */
 445: 
 446: {
 447:     font = n;
 448:     ftsz = ((long)font << 16) | ((long)size);
 449: }
 450: /*
 451:  *	reportError	an error reporting hack that uses dummy parameters
 452:  *			as place holders for arguments that may or may not
 453:  *			exist, fprintf will sort out how many should be there
 454:  */
 455: /*VARARGS 2*/
 456: reportError(f, s, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8)
 457: char *s, *arg1, *arg2, *arg3, *arg4, *arg5, *arg6, *arg7, *arg8;
 458: {
 459:     fprintf(stderr, "dipress: ");
 460:     fprintf(stderr, s, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8);
 461:     fprintf(stderr, "\nerror encountered near line %d\n", linenumber);
 462:     if (f == QUIT) goodbye();
 463: }
 464: 
 465: 
 466: 
 467: 
 468: /*
 469:  *  Graphics drawing primitives.  These use the vector drawing capabilities of
 470:  *  interpress to draw straight lines.  All other primitive objects (circle,
 471:  *  ellipse, etc.) are built in a bitmap and printed with a pixel vector.
 472:  */
 473: 
 474: drawline(dh, dv)
 475: int dh,dv;
 476: {
 477: 
 478:     if(!outputflag) return;
 479:     AppendInteger((long) curr_strokewidth);
 480:     AppendInteger((long) I_strokeWidth);
 481:     Op(iset);
 482:     Moveto(xloc(hor_pos), yloc(ver_pos));
 483:     hor_pos += dh;
 484:     ver_pos += dv;
 485:     Lineto(xloc(hor_pos), yloc(ver_pos));
 486:     Op(maskstroke);
 487: }
 488: 
 489: /* routines used by interpress dependent routines */
 490: 
 491: char showbuff[Showbuff_size + 1];
 492: char *showp = showbuff;
 493: int  showcnt = 0;
 494: 
 495: showchar(ch)        /* buffer "ch" for use in a "show" command */
 496: int ch;
 497: {
 498:     char *framep;
 499:     register int hdiff, vdiff;
 500: 
 501:     /* set correct position */
 502:     vdiff = ver_pos - old_ver;
 503:     hdiff = hor_pos - old_hor;
 504:     if (dbg > 4)
 505:     {
 506:         printf("old_hor %d, hor_pos %d, hdiff %d;  old_ver %d, ver_pos %d, vdiff %d %s\n",
 507:         old_hor, hor_pos, hdiff, old_ver, ver_pos, vdiff,
 508:         virgin_line ? "(virgin)" : "");
 509:     }
 510: 
 511:     /* NOTE:  this expression depends on boolean true being 1! */
 512:     /* See K&R, Appendix A, section 7.7, page 190 */
 513:     if (ch == '_') goto underbar;
 514:     switch (((vdiff != 0) << 1) | (hdiff != 0))
 515:     {
 516:     case 0:     /* no change */
 517:         break;
 518:     default:
 519:     underbar:
 520:         flushbuff();
 521:         Setxy(xloc(hor_pos), yloc(ver_pos));
 522:         break;
 523:     }
 524: 
 525:     /*
 526: 	     *  Update old_hor and old_ver.  Account for character width in old_hor but not in
 527: 	     *	hor_pos.  If the next hInc call is for the width of the character, the
 528: 	     *	next time showchar gets called, old_hor will equal hor_pos.
 529: 	     */
 530:     old_ver = ver_pos;
 531:     old_hor = hor_pos + charw;
 532: 
 533:     /* line is no longer virgin */
 534:     virgin_line = 0;
 535: 
 536:     /* font and point still the same? */
 537:     if (ftsz != oldftsz)
 538:     {
 539:         flushbuff();
 540:         if ((framep = currfonts[font]->frames) == NULL)
 541:         {
 542:             /* previously unused -- give it a frame table */
 543:             framep = currfonts[font]->frames = malloc((unsigned)(device.num_sizes * sizeof(char)));
 544:             bzero(framep, device.num_sizes * sizeof(char));
 545:         }
 546: 
 547:         if (framep[size] == 0)
 548:         {
 549:             /* make a new font */
 550:             ip_select(outputfile);
 551:             SetupFont(currfonts[font]->uname,
 552:             floor(pointsizeTab[size-1] * 35.28 + .5),
 553:             frameindex);
 554:             ip_select(pagebodyfile);
 555:             framep[size] = frameindex++;
 556:         }
 557: 
 558:         /* switch to new font/size combo */
 559:         Setfont(framep[size]);
 560:         oldftsz = ftsz;
 561:     }
 562: 
 563:     /* adjust for character codes > 0377 */
 564:     if (ch > 0377)
 565:     {
 566:         if (dbg > 4)
 567:         {
 568:             printf("processing large code: 0%o (%d)\n", ch, ch);
 569:         }
 570: 
 571:         if (showcnt + 5 > Showbuff_size)
 572:         {
 573:             flushbuff();
 574:         }
 575:         *showp++ = '\377';
 576:         *showp++ = (ch & 0177400) >> 8;
 577:         *showp++ = ch & 255;
 578:         *showp++ = '\377';
 579:         *showp++ = '\0';
 580:         showcnt += 5;
 581:     }
 582:     else
 583:     {
 584:         *showp++ = ch;
 585:         if (++showcnt > Showbuff_size)
 586:         {
 587:             flushbuff();
 588:         }
 589:     }
 590: }
 591: 
 592: /*
 593:  *  getexcode(findex) - get the extended code for the character "findex"
 594:  */
 595: 
 596: getexcode(findex)
 597: int findex;
 598: {
 599:     register int extfd;
 600:     register int i;
 601:     register unsigned short *tab;
 602:     char temp[132];
 603: 
 604:     if (dbg > 4)
 605:     {
 606:         printf("getexcode(%d)\n", findex);
 607:     }
 608: 
 609:     if ((tab = currfonts[font]->extab) == NULL)
 610:     {
 611:         /* load in the extended code table */
 612: 
 613:         (void) sprintf(temp, "%s/dev%s/%s.out.ext",
 614:         fontdirectory, devicename, currfonts[font]->name);
 615:         if (dbg > 4)
 616:         {
 617:             printf("opening and reading %s\n", temp);
 618:         }
 619:         if ((extfd = open(temp, O_RDONLY,0)) == -1)
 620:         {
 621:             reportError(CONTINUE, "can't open %s (%s)", temp, sys_errlist[errno]);
 622:             return(0);
 623:         }
 624:         currfonts[font]->extab = tab = (unsigned short *)
 625:             malloc( (unsigned)(i = (device.spec_char_num + 128-32) * sizeof(short)) );
 626:         (void) read(extfd, (char *)tab, i); /* should test result! */
 627:         (void) close(extfd);
 628:     }
 629: 
 630:     if (dbg > 4)
 631:     {
 632:         printf("getexcode returning %.7o\n", tab[findex]);
 633:     }
 634:     return(tab[findex]);
 635: }
 636: 
 637: flushbuff()     /* flush and reset "showbuff" */
 638: {
 639:     if (showcnt == 0)
 640:         return;
 641: 
 642:     if (!in_correct)
 643:     {
 644:         startcorrect();
 645:     }
 646: 
 647:     /* we must do the append_Sequence explicitly, */
 648:     /* because showbuff might have nulls in it.   */
 649:     append_Sequence(sequenceString, showcnt, (unsigned char *)showbuff);
 650:     Op(show);
 651:     showp = showbuff;
 652:     showcnt = 0;
 653: }
 654: 
 655: int hstart;
 656: 
 657: startcorrect()
 658: {
 659: #ifdef CORRECT_BLOCKS
 660:     Op(correct);
 661:     Op(beginBody);
 662: #endif
 663:     in_correct = 1;
 664:     hstart = hor_pos;
 665: }
 666: 
 667: endcorrect()
 668: {
 669:     /* append a Setcorrectmeasure operation */
 670:     /* "hor_pos" or "old_hor"???  Make it "old_hor" for now */
 671: #ifdef CORRECT_BLOCKS
 672:     Setcorrectmeasure(xloc(old_hor), 0.0);
 673:     Op(endBody);
 674: #endif
 675:     in_correct = 0;
 676: }
 677: 
 678: /*
 679:  *  IPprint(filename) - send the file "filename" to the interpress printer.
 680:  *			 This routine is *very* dependent on local
 681:  *			 environments.
 682:  */
 683: 
 684: IPprint(filename)
 685: char *filename;
 686: {
 687:     if (dbg)
 688:     {
 689:         printf("interpress file saved in %s.\n", filename);
 690:         return;
 691:     }
 692: 
 693:     if (vfork() == 0)
 694:     {
 695:         /* is child */
 696:         execl("/usr/local/bin/qip", "qip", "-nc", "-nk", filename, 0);
 697:         exit(1);
 698:     }
 699: }
 700: 
 701: /* bitmap graphics object sizing functions */
 702: 
 703: g_sizearc(x1, y1, xc, yc, x2, y2)
 704: int x1, y1, xc, yc, x2, y2;
 705: {
 706:     int minx;
 707:     int miny;
 708:     int maxx;
 709:     int maxy;
 710:     int quad1;
 711:     int quad2;
 712:     int radius;
 713:     int axc;
 714:     int ayc;
 715:     int i;
 716: 
 717:     /* the center and the second point are offsets from the first */
 718:     /* calculate actual center and radius */
 719:     axc = x1 + xc;
 720:     ayc = y1 + yc;
 721:     radius = (int)(hypot((double)xc, (double)yc) + .5);
 722:     if (dbg > 1)
 723:     {
 724:         printf("g_sizearc(%d, %d, %d, %d, %d, %d): radius is %d\n",
 725:         x1, y1, xc, yc, x2, y2, radius);
 726:     }
 727: 
 728:     /* preset the minmal and maximal points -- this is our first guess */
 729:     if ((minx = x1 + xc + x2) > x1)
 730:     {
 731:         maxx = minx;
 732:         minx = x1;
 733:     }
 734:     else
 735:     {
 736:         maxx = x1;
 737:     }
 738:     if ((miny = y1 + yc + y2) > y1)
 739:     {
 740:         maxy = miny;
 741:         miny = y1;
 742:     }
 743:     else
 744:     {
 745:         maxy = y1;
 746:     }
 747: 
 748:     /* calculate the offset from the center to the first point */
 749:     x1 = -xc;
 750:     y1 = -yc;       /* now all three arguments are offsets */
 751: 
 752:     /* calculate the quadrant of each endpoint */
 753:     quad1 = quadrant(x1, y1);
 754:     quad2 = quadrant(x2, y2);
 755:     if (dbg > 1)
 756:     {
 757:         printf("(%d, %d) in quadrant %d ... ", x1, y1, quad1);
 758:         printf("(%d, %d) in quadrant %d\n", x2, y2, quad2);
 759:     }
 760: 
 761:     /* insure that quad1 < quad2 */
 762:     if (quad2 < quad1)
 763:     {
 764:         quad2 += 4;
 765:     }
 766: 
 767:     /* compensate for arc at each quadrant boundary */
 768:     for (i = quad1 + 1; i <= quad2; i++)
 769:     {
 770:         switch (i & 3)
 771:         {
 772:         case 0:     /* 1st quadrant */
 773:             maxx = axc + radius;
 774:             break;
 775: 
 776:         case 1:     /* 2nd quadrant */
 777:             miny = ayc - radius;
 778:             break;
 779: 
 780:         case 2:     /* 3rd quadrant */
 781:             minx = axc - radius;
 782:             break;
 783: 
 784:         case 3:     /* 4th quadrant */
 785:             maxy = ayc + radius;
 786:             break;
 787:         }
 788:     }
 789: 
 790:     /* now set the extremes */
 791:     if (dbg > 1)
 792:     {
 793:         printf("extremes are %d, %d, %d, %d\n", minx, miny, maxx, maxy);
 794:     }
 795:     gobj_size(minx, miny, maxx, maxy);
 796: }
 797: 
 798: quadrant(dx, dy)
 799: int dx,dy;
 800: {
 801:     register int yplus;
 802: 
 803:     yplus = dy > 0;
 804:     if (dx > 0)
 805:     {
 806:         return(yplus ? 3 : 0);
 807:     }
 808:     else
 809:     {
 810:         return(yplus ? 2 : 1);
 811:     }
 812: }
 813: 
 814: 
 815: g_sizeWigglyLine(str)
 816: char *str;
 817: {
 818:     int minx;
 819:     int miny;
 820:     int maxx;
 821:     int maxy;
 822:     int currx;
 823:     int curry;
 824:     int incx;
 825:     int incy;
 826: 
 827:     currx = minx = maxx = hor_pos;
 828:     curry = miny = maxy = ver_pos;
 829: 
 830:     while(white(*str)) str++; /* trim leading white space */
 831: 
 832:     while (*str)
 833:     {
 834: 
 835:         (void) readNumber(&str,&incx);
 836:         (void) readNumber(&str,&incy);
 837:         currx += incx;
 838:         curry += incy;
 839:         if (currx > maxx)
 840:             maxx = currx;
 841:         else if (currx < minx)
 842:             minx = currx;
 843:         if (curry > maxy)
 844:             maxy = curry;
 845:         else if (curry < miny)
 846:             miny = curry;
 847:     }
 848:     gobj_size(minx, miny, maxx, maxy);
 849: }

Defined functions

IPprint defined in line 684; used 1 times
drawline defined in line 474; used 1 times
endcorrect defined in line 667; used 1 times
flushbuff defined in line 637; used 5 times
g_sizearc defined in line 703; used 1 times
getexcode defined in line 596; used 1 times
initDevice defined in line 40; used 1 times
internalSize defined in line 245; used 1 times
newLine defined in line 235; used 1 times
newpage defined in line 179; used 1 times
outputChar defined in line 343; used 3 times
outputString defined in line 318; used 1 times
popSavedEnv defined in line 165; used 1 times
quadrant defined in line 798; used 2 times
setFont defined in line 442; used 3 times
setPointSize defined in line 433; used 1 times
setScale defined in line 127; used 1 times
showchar defined in line 495; used 1 times
startcorrect defined in line 657; used 1 times

Defined variables

hstart defined in line 655; used 1 times
showbuff defined in line 491; used 3 times
showcnt defined in line 493; used 6 times
showp defined in line 492; used 7 times
Last modified: 1986-03-30
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 3443
Valid CSS Valid XHTML 1.0 Strict