ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/meta/expand.c
Revision: 1.1
Committed: Sat Feb 22 02:07:26 2003 UTC (21 years, 1 month ago) by greg
Content type: text/plain
Branch: MAIN
CVS Tags: rad3R5
Log Message:
Changes and check-in for 3.5 release
Includes new source files and modifications not recorded for many years
See ray/doc/notes/ReleaseNotes for notes between 3.1 and 3.5 release

File Contents

# Content
1 #ifndef lint
2 static const char RCSid[] = "$Id$";
3 #endif
4 /*
5 * Expansion routine for command implementation
6 * on simple drivers
7 */
8
9
10 #include "meta.h"
11
12
13 /* vector characters file */
14 #define VINPUT "vchars.mta"
15
16 #define FIRSTCHAR ' ' /* first vector character */
17
18 #define LASTCHAR '~' /* last vector character */
19
20 #define PEPS 5 /* minimum size for fill area */
21
22 #define fillok(p) ((p)->xy[XMX] - (p)->xy[XMN] > PEPS && \
23 (p)->xy[YMX] - (p)->xy[YMN] > PEPS)
24
25
26
27 static short *xlist; /* pointer to expansion list */
28
29
30
31 expand(infp, exlist) /* expand requested commands */
32
33 FILE *infp;
34 short *exlist;
35
36 {
37 static PRIMITIVE pincl = {PINCL, 02, -1, -1, -1, -1, VINPUT};
38 static short vcloaded = FALSE;
39
40 xlist = exlist;
41
42 if (exlist[comndx(PVSTR)] == 1 && !vcloaded) {
43 vcloaded = TRUE;
44 exprim(&pincl);
45 }
46
47 exfile(infp);
48
49 if (inseg())
50 error(USER, "unclosed segment in expand");
51
52 }
53
54
55
56
57 static
58 exfile(fp) /* expand the given file */
59
60 register FILE *fp;
61
62 {
63 PRIMITIVE curp;
64
65 while (readp(&curp, fp)) {
66 exprim(&curp);
67 fargs(&curp);
68 }
69
70 }
71
72
73
74
75 static
76 exprim(p) /* expand primitive */
77
78 register PRIMITIVE *p;
79
80 {
81 int xflag = xlist[comndx(p->com)];
82 /* 1==expand, 0==pass, -1==discard */
83 if (xflag != -1)
84 if (xflag == 1)
85 switch (p->com) {
86
87 case POPEN:
88 openseg(p->args);
89 break;
90
91 case PSEG:
92 segment(p, exprim);
93 break;
94
95 case PCLOSE:
96 closeseg();
97 break;
98
99 case PINCL:
100 include(p->arg0, p->args);
101 break;
102
103 case PMSTR:
104 sendmstr(p);
105 break;
106
107 case PVSTR:
108 sendvstr(p);
109 break;
110
111 case PPFILL:
112 polyfill(p);
113 break;
114
115 default:
116 sprintf(errmsg, "unsupported command '%c' in exprim", p->com);
117 error(WARNING, errmsg);
118 break;
119 }
120 else if (inseg())
121 segprim(p);
122 else
123 writep(p, stdout);
124
125 }
126
127
128
129
130 static
131 sendmstr(p) /* expand a matrix string */
132
133 register PRIMITIVE *p;
134
135 {
136 PRIMITIVE pout;
137 int cheight, cwidth, cthick, ccol;
138
139 cheight = 350;
140 if (p->arg0 & 010)
141 cheight *= 2;
142 cwidth = (6 - ((p->arg0 >> 4) & 03)) * 35;
143 if (p->arg0 & 04)
144 cwidth *= 2;
145 cthick = (p->arg0 & 0100) ? 1 : 0;
146 ccol = p->arg0 & 03;
147
148 pout.com = PVSTR;
149 pout.arg0 = (cthick << 2) | ccol;
150 pout.xy[XMN] = p->xy[XMN];
151 pout.xy[YMN] = p->xy[YMX] - cheight/2;
152 pout.xy[XMX] = p->xy[XMN] + strlen(p->args)*cwidth;
153 if (pout.xy[XMX] >= XYSIZE)
154 pout.xy[XMX] = XYSIZE-1;
155 pout.xy[YMX] = p->xy[YMX] + cheight/2;
156 pout.args = p->args;
157
158 exprim(&pout);
159
160 }
161
162
163
164 static
165 sendvstr(p) /* expand a vector string */
166
167 register PRIMITIVE *p;
168
169 {
170 PRIMITIVE pout;
171 int xadv, yadv;
172 char s[3];
173 register char *cp;
174
175 if (p->args == NULL)
176 error(USER, "illegal empty string in sendvstr");
177
178 pout.com = PSEG;
179 pout.arg0 = p->arg0;
180 switch (p->arg0 & 060) {
181 case 0: /* right */
182 xadv = (p->xy[XMX] - p->xy[XMN])/strlen(p->args);
183 pout.xy[XMN] = p->xy[XMN];
184 pout.xy[XMX] = p->xy[XMN] + xadv;
185 yadv = 0;
186 pout.xy[YMN] = p->xy[YMN];
187 pout.xy[YMX] = p->xy[YMX];
188 break;
189 case 020: /* up */
190 xadv = 0;
191 pout.xy[XMN] = p->xy[XMN];
192 pout.xy[XMX] = p->xy[XMX];
193 yadv = (p->xy[YMX] - p->xy[YMN])/strlen(p->args);
194 pout.xy[YMN] = p->xy[YMN];
195 pout.xy[YMX] = p->xy[YMN] + yadv;
196 break;
197 case 040: /* left */
198 xadv = -(p->xy[XMX] - p->xy[XMN])/strlen(p->args);
199 pout.xy[XMN] = p->xy[XMX] + xadv;
200 pout.xy[XMX] = p->xy[XMX];
201 yadv = 0;
202 pout.xy[YMN] = p->xy[YMN];
203 pout.xy[YMX] = p->xy[YMX];
204 break;
205 case 060: /* down */
206 xadv = 0;
207 pout.xy[XMN] = p->xy[XMN];
208 pout.xy[XMX] = p->xy[XMX];
209 yadv = -(p->xy[YMX] - p->xy[YMN])/strlen(p->args);
210 pout.xy[YMN] = p->xy[YMX] + yadv;
211 pout.xy[YMX] = p->xy[YMX];
212 break;
213 }
214
215 pout.args = s;
216 s[1] = '\'';
217 s[2] = '\0';
218 for (cp = p->args; *cp; cp++)
219 if (*cp < FIRSTCHAR || *cp > LASTCHAR) {
220 sprintf(errmsg, "unknown character (%d) in sendvstr", *cp);
221 error(WARNING, errmsg);
222 }
223 else {
224 s[0] = *cp;
225 exprim(&pout);
226 pout.xy[XMN] += xadv;
227 pout.xy[XMX] += xadv;
228 pout.xy[YMN] += yadv;
229 pout.xy[YMX] += yadv;
230 }
231
232 }
233
234
235
236 static
237 include(code, fname) /* load an include file */
238
239 int code;
240 char *fname;
241
242 {
243 register FILE *fp;
244
245 if (fname == NULL)
246 error(USER, "missing include file name in include");
247
248 if (code == 2 || (fp = fopen(fname, "r")) == NULL)
249 if (code != 0)
250 fp = mfopen(fname, "r");
251 else {
252 sprintf(errmsg, "cannot open user include file \"%s\"", fname);
253 error(USER, errmsg);
254 }
255
256 exfile(fp);
257 fclose(fp);
258
259 }
260
261
262
263 static
264 polyfill(p) /* expand polygon fill command */
265
266 PRIMITIVE *p;
267
268 {
269 char *nextscan();
270 int firstx, firsty, lastx, lasty, x, y;
271 register char *cp;
272
273 if ((cp=nextscan(nextscan(p->args,"%d",&firstx),"%d",&firsty)) == NULL) {
274 sprintf(errmsg, "illegal polygon spec \"%s\" in polyfill", p->args);
275 error(WARNING, errmsg);
276 return;
277 }
278
279 lastx = firstx;
280 lasty = firsty;
281
282 while ((cp=nextscan(nextscan(cp,"%d",&x),"%d",&y)) != NULL) {
283
284 polyedge(p, lastx, lasty, x, y);
285 lastx = x;
286 lasty = y;
287 }
288
289 polyedge(p, lastx, lasty, firstx, firsty);
290 }
291
292
293
294 static
295 polyedge(p, x1, y1, x2, y2) /* expand edge of polygon */
296
297 PRIMITIVE *p;
298 int x1, y1, x2, y2;
299
300 {
301 int reverse;
302 PRIMITIVE pin, pout;
303
304 if (x1 < x2) {
305 pin.xy[XMN] = x1;
306 pin.xy[XMX] = x2;
307 reverse = FALSE;
308 } else {
309 pin.xy[XMN] = x2;
310 pin.xy[XMX] = x1;
311 reverse = TRUE;
312 }
313
314 if (y1 < y2) {
315 pin.xy[YMN] = y1;
316 pin.xy[YMX] = y2;
317 } else {
318 pin.xy[YMN] = y2;
319 pin.xy[YMX] = y1;
320 reverse = y1 > y2 && !reverse;
321 }
322
323 pout.xy[XMN] = xlate(XMN, &pin, p);
324 pout.xy[XMX] = xlate(XMX, &pin, p);
325 pout.xy[YMN] = xlate(YMN, &pin, p);
326 pout.xy[YMX] = xlate(YMX, &pin, p);
327 pout.com = PTFILL;
328 pout.arg0 = 0100 | (reverse << 4) | (p->arg0 & 017);
329 pout.args = NULL;
330 if (fillok(&pout))
331 exprim(&pout);
332
333 if (p->arg0 & 0100) { /* draw border */
334 pout.com = PLSEG;
335 pout.arg0 = reverse << 6;
336 exprim(&pout);
337 }
338
339 pout.com = PRFILL;
340 pout.arg0 = 0100 | (p->arg0 & 017);
341 pout.xy[XMN] = pout.xy[XMX];
342 pout.xy[XMX] = p->xy[XMX];
343 if (fillok(&pout))
344 exprim(&pout);
345
346 }