|
|
1.1 root 1: #include <stdio.h>
2: #include <string.h>
3: #include <stdlib.h>
4: #include "grap.h"
5: #include "y.tab.h"
6:
7: int nnum = 0; /* number of saved numbers */
8: double num[MAXNUM];
9:
10: int just; /* current justification mode (RJUST, etc.) */
11: int sizeop; /* current optional operator for size change */
12: double sizexpr; /* current size change expression */
13:
14: void savenum(int n, double f) /* save f in num[n] */
15: {
16: num[n] = f;
17: nnum = n+1;
18: if (nnum >= MAXNUM)
19: ERROR "too many numbers" WARNING;
20: }
21:
22: void setjust(int j)
23: {
24: just |= j;
25: }
26:
27: void setsize(int op, double expr)
28: {
29: sizeop = op;
30: sizexpr = expr;
31: }
32:
33: char *tostring(char *s)
34: {
35: register char *p;
36:
37: p = malloc(strlen(s)+1);
38: if (p == NULL)
39: ERROR "out of space in tostring on %s", s FATAL;
40: strcpy(p, s);
41: return(p);
42: }
43:
44: void range(Point pt) /* update the range for point pt */
45: {
46: Obj *p = pt.obj;
47:
48: if (!(p->coord & XFLAG)) {
49: if (pt.x > p->pt1.x)
50: p->pt1.x = pt.x;
51: if (pt.x < p->pt.x)
52: p->pt.x = pt.x;
53: }
54: if (!(p->coord & YFLAG)) {
55: if (pt.y > p->pt1.y)
56: p->pt1.y = pt.y;
57: if (pt.y < p->pt.y)
58: p->pt.y = pt.y;
59: }
60: }
61:
62: void halfrange(Obj *p, int side, double val) /* record max and min for one direction */
63: {
64: if (!(p->coord&XFLAG) && (side == LEFT || side == RIGHT)) {
65: if (val < p->pt.y)
66: p->pt.y = val;
67: if (val > p->pt1.y)
68: p->pt1.y = val;
69: } else if (!(p->coord&YFLAG) && (side == TOP || side == BOT)) {
70: if (val < p->pt.x)
71: p->pt.x = val;
72: if (val > p->pt1.x)
73: p->pt1.x = val;
74: }
75: }
76:
77:
78: Obj *lookup(char *s, int inst) /* find s in objlist, install if inst */
79: {
80: Obj *p;
81: int found = 0;
82:
83: for (p = objlist; p; p = p->next)
84: if (strcmp(s, p->name) == 0) {
85: found = 1;
86: break;
87: }
88: if (p == NULL && inst != 0) {
89: p = (Obj *) calloc(1, sizeof(Obj));
90: if (p == NULL)
91: ERROR "out of space in lookup" FATAL;
92: p->name = tostring(s);
93: p->type = NAME;
94: p->pt = ptmax;
95: p->pt1 = ptmin;
96: p->fval = 0.0;
97: p->next = objlist;
98: objlist = p;
99: }
100: dprintf("lookup(%s,%d) = %d\n", s, inst, found);
101: return p;
102: }
103:
104: double getvar(Obj *p) /* return value of variable */
105: {
106: return p->fval;
107: }
108:
109: double setvar(Obj *p, double f) /* set value of variable to f */
110: {
111: if (strcmp(p->name, "pointsize") == 0) { /* kludge */
112: pointsize = f;
113: ps_set = 1;
114: }
115: p->type = VARNAME;
116: return p->fval = f;
117: }
118:
119: Point makepoint(Obj *s, double x, double y) /* make a Point */
120: {
121: Point p;
122:
123: dprintf("makepoint: %s, %g,%g\n", s->name, x, y);
124: p.obj = s;
125: p.x = x;
126: p.y = y;
127: return p;
128: }
129:
130: Attr *makefattr(int type, double fval) /* set double in attribute */
131: {
132: return makeattr(type, fval, (char *) 0, 0, 0);
133: }
134:
135: Attr *makesattr(char *s) /* make an Attr cell containing s */
136: {
137: Attr *ap = makeattr(STRING, sizexpr, s, just, sizeop);
138: just = sizeop = 0;
139: sizexpr = 0.0;
140: return ap;
141: }
142:
143: Attr *makeattr(int type, double fval, char *sval, int just, int op)
144: {
145: Attr *a;
146:
147: a = (Attr *) malloc(sizeof(Attr));
148: if (a == NULL)
149: ERROR "out of space in makeattr" FATAL;
150: a->type = type;
151: a->fval = fval;
152: a->sval = sval;
153: a->just = just;
154: a->op = op;
155: a->next = NULL;
156: return a;
157: }
158:
159: Attr *addattr(Attr *a1, Attr *ap) /* add attr ap to end of list a1 */
160: {
161: Attr *p;
162:
163: if (a1 == 0)
164: return ap;
165: if (ap == 0)
166: return a1;
167: for (p = a1; p->next; p = p->next)
168: ;
169: p->next = ap;
170: return a1;
171: }
172:
173: void freeattr(Attr *ap) /* free an attribute list */
174: {
175: Attr *p;
176:
177: while (ap) {
178: p = ap->next; /* save next */
179: if (ap->sval)
180: free(ap->sval);
181: free((char *) ap);
182: ap = p;
183: }
184: }
185:
186: char *slprint(Attr *stringlist) /* print strings from stringlist */
187: {
188: int ntext, n, last_op, last_just;
189: double last_fval;
190: static char buf[1000];
191: Attr *ap;
192:
193: buf[0] = '\0';
194: last_op = last_just = 0;
195: last_fval = 0.0;
196: for (ntext = 0, ap = stringlist; ap != NULL; ap = ap->next)
197: ntext++;
198: sprintf(buf, "box invis wid 0 ht %d*textht", ntext);
199: n = strlen(buf);
200: for (ap = stringlist; ap != NULL; ap = ap->next) {
201: if (ap->op == 0) { /* propagate last value */
202: ap->op = last_op;
203: ap->fval = last_fval;
204: } else {
205: last_op = ap->op;
206: last_fval = ap->fval;
207: }
208: sprintf(buf+n, " \"%s\"", ps_set || ap->op ? sizeit(ap) : ap->sval);
209: if (ap->just)
210: last_just = ap->just;
211: if (last_just)
212: strcat(buf+n, juststr(last_just));
213: n = strlen(buf);
214: }
215: return buf; /* watch it: static */
216: }
217:
218: char *juststr(int j) /* convert RJUST, etc., into string */
219: {
220: static char buf[50];
221:
222: buf[0] = '\0';
223: if (j & RJUST)
224: strcat(buf, " rjust");
225: if (j & LJUST)
226: strcat(buf, " ljust");
227: if (j & ABOVE)
228: strcat(buf, " above");
229: if (j & BELOW)
230: strcat(buf, " below");
231: return buf; /* watch it: static */
232: }
233:
234: char *sprntf(char *s, Attr *ap) /* sprintf(s, attrlist ap) */
235: {
236: char buf[500];
237: int n;
238: Attr *p;
239:
240: for (n = 0, p = ap; p; p = p->next)
241: n++;
242: switch (n) {
243: case 0:
244: return s;
245: case 1:
246: sprintf(buf, s, ap->fval);
247: break;
248: case 2:
249: sprintf(buf, s, ap->fval, ap->next->fval);
250: break;
251: case 3:
252: sprintf(buf, s, ap->fval, ap->next->fval, ap->next->next->fval);
253: break;
254: case 4:
255: sprintf(buf, s, ap->fval, ap->next->fval, ap->next->next->fval, ap->next->next->next->fval);
256: break;
257: case 5:
258: ERROR "too many expressions in sprintf" WARNING;
259: }
260: free(s);
261: return tostring(buf);
262: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.