|
|
1.1 ! root 1: #include <stdio.h> ! 2: #include <stdlib.h> ! 3: #include "pic.h" ! 4: #include "y.tab.h" ! 5: ! 6: #define NBRACK 20 /* depth of [...] */ ! 7: #define NBRACE 20 /* depth of {...} */ ! 8: ! 9: struct pushstack stack[NBRACK]; ! 10: int nstack = 0; ! 11: struct pushstack bracestack[NBRACE]; ! 12: int nbstack = 0; ! 13: ! 14: void blockadj(obj *); ! 15: ! 16: obj *leftthing(int c) /* called for {... or [... */ ! 17: /* really ought to be separate functions */ ! 18: { ! 19: obj *p; ! 20: ! 21: if (c == '[') { ! 22: if (nstack >= NBRACK) ! 23: ERROR "[...] nested too deep" FATAL; ! 24: stack[nstack].p_x = curx; ! 25: stack[nstack].p_y = cury; ! 26: stack[nstack].p_hvmode = hvmode; ! 27: curx = cury = 0; ! 28: stack[nstack].p_xmin = xmin; ! 29: stack[nstack].p_xmax = xmax; ! 30: stack[nstack].p_ymin = ymin; ! 31: stack[nstack].p_ymax = ymax; ! 32: nstack++; ! 33: xmin = ymin = 30000; ! 34: xmax = ymax = -30000; ! 35: p = makenode(BLOCK, 7); ! 36: p->o_val[4] = nobj; /* 1st item within [...] */ ! 37: if (p->o_nobj != nobj-1) ! 38: fprintf(stderr, "nobjs wrong%d %d\n", p->o_nobj, nobj); ! 39: } else { ! 40: if (nbstack >= NBRACK) ! 41: ERROR "{...} nested too deep" FATAL; ! 42: bracestack[nbstack].p_x = curx; ! 43: bracestack[nbstack].p_y = cury; ! 44: bracestack[nbstack].p_hvmode = hvmode; ! 45: nbstack++; ! 46: p = NULL; ! 47: } ! 48: return(p); ! 49: } ! 50: ! 51: obj *rightthing(obj *p, int c) /* called for ... ] or ... } */ ! 52: { ! 53: obj *q; ! 54: ! 55: if (c == '}') { ! 56: nbstack--; ! 57: curx = bracestack[nbstack].p_x; ! 58: cury = bracestack[nbstack].p_y; ! 59: hvmode = bracestack[nbstack].p_hvmode; ! 60: q = makenode(MOVE, 0); ! 61: dprintf("M %g %g\n", curx, cury); ! 62: } else { ! 63: nstack--; ! 64: curx = stack[nstack].p_x; ! 65: cury = stack[nstack].p_y; ! 66: hvmode = stack[nstack].p_hvmode; ! 67: q = makenode(BLOCKEND, 7); ! 68: q->o_val[4] = p->o_nobj + 1; /* back pointer */ ! 69: p->o_val[5] = q->o_nobj - 1; /* forward pointer */ ! 70: if (xmin > xmax) /* nothing happened */ ! 71: xmin = xmax; ! 72: if (ymin > ymax) ! 73: ymin = ymax; ! 74: p->o_val[0] = xmin; p->o_val[1] = ymin; ! 75: p->o_val[2] = xmax; p->o_val[3] = ymax; ! 76: p->o_symtab = q->o_symtab = stack[nstack+1].p_symtab; ! 77: xmin = stack[nstack].p_xmin; ! 78: ymin = stack[nstack].p_ymin; ! 79: xmax = stack[nstack].p_xmax; ! 80: ymax = stack[nstack].p_ymax; ! 81: } ! 82: return(q); ! 83: } ! 84: ! 85: obj *blockgen(obj *p, obj *q) /* handles [...] */ ! 86: { ! 87: int i, invis, at, with; ! 88: double ddval, h, w, xwith, ywith; ! 89: double x0, y0, x1, y1, cx, cy; ! 90: obj *ppos; ! 91: Attr *ap; ! 92: ! 93: invis = at = 0; ! 94: with = xwith = ywith = 0; ! 95: ddval = 0; ! 96: w = p->o_val[2] - p->o_val[0]; ! 97: h = p->o_val[3] - p->o_val[1]; ! 98: cx = (p->o_val[2] + p->o_val[0]) / 2; /* geom ctr of [] wrt local orogin */ ! 99: cy = (p->o_val[3] + p->o_val[1]) / 2; ! 100: dprintf("cx,cy=%g,%g\n", cx, cy); ! 101: for (i = 0; i < nattr; i++) { ! 102: ap = &attr[i]; ! 103: switch (ap->a_type) { ! 104: case HEIGHT: ! 105: h = ap->a_val.f; ! 106: break; ! 107: case WIDTH: ! 108: w = ap->a_val.f; ! 109: break; ! 110: case WITH: ! 111: with = ap->a_val.i; /* corner */ ! 112: break; ! 113: case PLACE: /* actually with position ... */ ! 114: ppos = ap->a_val.o; ! 115: xwith = cx - ppos->o_x; ! 116: ywith = cy - ppos->o_y; ! 117: with = PLACE; ! 118: break; ! 119: case AT: ! 120: case FROM: ! 121: ppos = ap->a_val.o; ! 122: curx = ppos->o_x; ! 123: cury = ppos->o_y; ! 124: at++; ! 125: break; ! 126: case INVIS: ! 127: invis = INVIS; ! 128: break; ! 129: case TEXTATTR: ! 130: savetext(ap->a_sub, ap->a_val.p); ! 131: break; ! 132: } ! 133: } ! 134: if (with) { ! 135: switch (with) { ! 136: case NORTH: ywith = -h / 2; break; ! 137: case SOUTH: ywith = h / 2; break; ! 138: case EAST: xwith = -w / 2; break; ! 139: case WEST: xwith = w / 2; break; ! 140: case NE: xwith = -w / 2; ywith = -h / 2; break; ! 141: case SE: xwith = -w / 2; ywith = h / 2; break; ! 142: case NW: xwith = w / 2; ywith = -h / 2; break; ! 143: case SW: xwith = w / 2; ywith = h / 2; break; ! 144: } ! 145: curx += xwith; ! 146: cury += ywith; ! 147: } ! 148: if (!at) { ! 149: if (isright(hvmode)) ! 150: curx += w / 2; ! 151: else if (isleft(hvmode)) ! 152: curx -= w / 2; ! 153: else if (isup(hvmode)) ! 154: cury += h / 2; ! 155: else ! 156: cury -= h / 2; ! 157: } ! 158: x0 = curx - w / 2; ! 159: y0 = cury - h / 2; ! 160: x1 = curx + w / 2; ! 161: y1 = cury + h / 2; ! 162: extreme(x0, y0); ! 163: extreme(x1, y1); ! 164: p->o_x = curx; ! 165: p->o_y = cury; ! 166: p->o_nt1 = ntext1; ! 167: p->o_nt2 = ntext; ! 168: ntext1 = ntext; ! 169: p->o_val[0] = w; ! 170: p->o_val[1] = h; ! 171: p->o_val[2] = cx; ! 172: p->o_val[3] = cy; ! 173: p->o_val[5] = q->o_nobj - 1; /* last item in [...] */ ! 174: p->o_ddval = ddval; ! 175: p->o_attr = invis; ! 176: dprintf("[] %g %g %g %g at %g %g, h=%g, w=%g\n", x0, y0, x1, y1, curx, cury, h, w); ! 177: if (isright(hvmode)) ! 178: curx = x1; ! 179: else if (isleft(hvmode)) ! 180: curx = x0; ! 181: else if (isup(hvmode)) ! 182: cury = y1; ! 183: else ! 184: cury = y0; ! 185: for (i = 0; i <= 5; i++) ! 186: q->o_val[i] = p->o_val[i]; ! 187: stack[nstack+1].p_symtab = NULL; /* so won't be found again */ ! 188: blockadj(p); /* fix up coords for enclosed blocks */ ! 189: return(p); ! 190: } ! 191: ! 192: void blockadj(obj *p) /* adjust coords in block starting at p */ ! 193: { ! 194: double dx, dy; ! 195: int n, lev; ! 196: ! 197: dx = p->o_x - p->o_val[2]; ! 198: dy = p->o_y - p->o_val[3]; ! 199: n = p->o_nobj + 1; ! 200: dprintf("into blockadj: dx,dy=%g,%g\n", dx, dy); ! 201: for (lev = 1; lev > 0; n++) { ! 202: p = objlist[n]; ! 203: if (p->o_type == BLOCK) ! 204: lev++; ! 205: else if (p->o_type == BLOCKEND) ! 206: lev--; ! 207: dprintf("blockadj: type=%d o_x,y=%g,%g;", p->o_type, p->o_x, p->o_y); ! 208: p->o_x += dx; ! 209: p->o_y += dy; ! 210: dprintf(" becomes %g,%g\n", p->o_x, p->o_y); ! 211: switch (p->o_type) { /* other absolute coords */ ! 212: case LINE: ! 213: case ARROW: ! 214: case SPLINE: ! 215: p->o_val[0] += dx; ! 216: p->o_val[1] += dy; ! 217: break; ! 218: case ARC: ! 219: p->o_val[0] += dx; ! 220: p->o_val[1] += dy; ! 221: p->o_val[2] += dx; ! 222: p->o_val[3] += dy; ! 223: break; ! 224: } ! 225: } ! 226: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.