ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/rt/sundev.c
Revision: 1.2
Committed: Sat Apr 15 09:49:24 1989 UTC (36 years, 2 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 1.1: +1 -1 lines
Log Message:
Changed exit signal from hangup to broken pipe

File Contents

# User Rev Content
1 greg 1.1 /* Copyright (c) 1988 Regents of the University of California */
2    
3     #ifndef lint
4     static char SCCSid[] = "$SunId$ LBL";
5     #endif
6    
7     /*
8     * sundev.c - standalone driver for Sunwindows.
9     *
10     * 10/3/88
11     */
12    
13     #include <stdio.h>
14     #include <fcntl.h>
15     #include <suntool/sunview.h>
16     #include <suntool/canvas.h>
17     #include <suntool/tty.h>
18    
19     #include "color.h"
20    
21     #include "driver.h"
22    
23     short icon_image[] = {
24     #include "suntools.icon"
25     };
26     DEFINE_ICON_FROM_IMAGE(sun_icon, icon_image);
27    
28     #ifndef TTYPROG
29     #define TTYPROG "sun.com" /* tty program */
30     #endif
31    
32     #define GAMMA 2.0 /* exponent for color correction */
33    
34     #define COMLH 3 /* number of command lines */
35    
36     #define hashcolr(c) ((67*(c)[RED]+59*(c)[GRN]+71*(c)[BLU])%NCOLORS)
37    
38     int colres = 128; /* color resolution */
39     COLR colrmap[256]; /* our color mapping */
40    
41     #define NCOLORS 251 /* color table size (prime) */
42     #define FIRSTCOLOR 2 /* first usable entry */
43    
44     COLR colrtbl[NCOLORS]; /* our color table */
45    
46     int sun_clear(), sun_paintr(), sun_getcur(),
47     sun_comout(), sun_comin();
48    
49     int (*dev_func[NREQUESTS])() = { /* request handlers */
50     sun_clear, sun_paintr, sun_getcur,
51     sun_comout, sun_comin
52     };
53    
54     FILE *ttyin;
55    
56     Frame frame = 0;
57     Tty tty = 0;
58     Canvas canvas = 0;
59    
60     int xres = 0, yres = 0;
61    
62     char *progname;
63    
64    
65     main(argc, argv)
66     int argc;
67     char *argv[];
68     {
69     extern Notify_value my_notice_destroy();
70     char *ttyargv[4], arg1[10], arg2[10];
71     int pd[2];
72     int com;
73     register Pixwin *pw;
74    
75     progname = argv[0];
76    
77     frame = window_create(0, FRAME,
78     FRAME_LABEL, argc > 1 ? argv[1] : argv[0],
79     FRAME_ICON, &sun_icon,
80     WIN_X, 0, WIN_Y, 0,
81     0);
82     if (frame == 0)
83     quit("cannot create frame");
84     if (pipe(pd) == -1)
85     quit("cannot create pipe");
86     sprintf(arg1, "%d", getppid());
87     sprintf(arg2, "%d", pd[1]);
88     ttyargv[0] = TTYPROG;
89     ttyargv[1] = arg1;
90     ttyargv[2] = arg2;
91     ttyargv[3] = NULL;
92     #ifdef BSD
93     fcntl(pd[0], F_SETFD, 1);
94     #endif
95     tty = window_create(frame, TTY,
96     TTY_ARGV, ttyargv,
97     WIN_ROWS, COMLH,
98     0);
99     if (tty == 0)
100     quit("cannot create tty subwindow");
101     close(pd[1]);
102     if ((ttyin = fdopen(pd[0], "r")) == NULL)
103     quit("cannot open tty");
104     canvas = window_create(frame, CANVAS,
105     CANVAS_RETAINED, FALSE,
106     WIN_INPUT_DESIGNEE, window_get(tty,WIN_DEVICE_NUMBER),
107     WIN_CONSUME_PICK_EVENTS, WIN_NO_EVENTS,
108     MS_LEFT, MS_MIDDLE, MS_RIGHT, 0,
109     0);
110     if (canvas == 0)
111     quit("cannot create canvas");
112     if (getmap() < 0)
113     quit("not a color screen");
114     window_set(canvas, CANVAS_RETAINED, TRUE, 0);
115     notify_interpose_destroy_func(frame, my_notice_destroy);
116    
117     while ((com = getc(stdin)) != EOF) { /* loop on requests */
118     if (com >= NREQUESTS || dev_func[com] == NULL)
119     quit("invalid request");
120     (*dev_func[com])();
121     }
122     quit(NULL);
123     }
124    
125    
126     quit(msg) /* exit */
127     char *msg;
128     {
129     if (msg != NULL) {
130     fprintf(stderr, "%s: %s\n", progname, msg);
131 greg 1.2 kill(getppid(), SIGPIPE);
132 greg 1.1 exit(1);
133     }
134     exit(0);
135     }
136    
137    
138     Notify_value
139     my_notice_destroy(fr, st) /* we're on our way out */
140     Frame fr;
141     Destroy_status st;
142     {
143     if (st != DESTROY_CHECKING) {
144     kill((int)window_get(tty, TTY_PID), SIGHUP);
145     kill(getppid(), SIGHUP);
146     }
147     return(notify_next_destroy_func(fr, st));
148     }
149    
150    
151     sun_clear() /* clear our canvas */
152     {
153     register Pixwin *pw;
154     int nwidth, nheight;
155    
156     fread(&nwidth, sizeof(nwidth), 1, stdin);
157     fread(&nheight, sizeof(nheight), 1, stdin);
158     pw = canvas_pixwin(canvas);
159     if (nwidth != xres || nheight != yres) {
160     window_set(frame, WIN_SHOW, FALSE, 0);
161     window_set(canvas, CANVAS_AUTO_SHRINK, TRUE,
162     CANVAS_AUTO_EXPAND, TRUE, 0);
163     window_set(canvas, WIN_WIDTH, nwidth, WIN_HEIGHT, nheight, 0);
164     window_set(canvas, CANVAS_AUTO_SHRINK, FALSE,
165     CANVAS_AUTO_EXPAND, FALSE, 0);
166     window_fit(frame);
167     window_set(frame, WIN_SHOW, TRUE, 0);
168     notify_do_dispatch();
169     xres = nwidth;
170     yres = nheight;
171     }
172     pw_writebackground(pw, 0, 0, xres, xres, PIX_SRC);
173     newmap();
174     }
175    
176    
177     sun_paintr() /* fill a rectangle */
178     {
179     COLOR col;
180     int pval;
181     int xmin, ymin, xmax, ymax;
182     register Pixwin *pw;
183    
184     fread(col, sizeof(COLOR), 1, stdin);
185     fread(&xmin, sizeof(xmin), 1, stdin);
186     fread(&ymin, sizeof(ymin), 1, stdin);
187     fread(&xmax, sizeof(xmax), 1, stdin);
188     fread(&ymax, sizeof(ymax), 1, stdin);
189     pval = pixel(col);
190     pw = canvas_pixwin(canvas);
191     pw_rop(pw, xmin, yres-ymax, xmax-xmin, ymax-ymin,
192     PIX_SRC|PIX_COLOR(pval), NULL, 0, 0);
193     }
194    
195    
196     sun_comout() /* output a string to command line */
197     {
198     char out[256];
199    
200     mygets(out, stdin);
201     ttyputs(out);
202     }
203    
204    
205     sun_comin() /* input a string from the command line */
206     {
207     char buf[256];
208     /* echo characters */
209     do {
210     mygets(buf, ttyin);
211     ttyputs(buf);
212     } while (buf[0]);
213     /* get result */
214     mygets(buf, ttyin);
215     /* send reply */
216     putc(COM_COMIN, stdout);
217     myputs(buf, stdout);
218     fflush(stdout);
219     }
220    
221    
222     sun_getcur() /* get cursor position */
223     {
224     Event *ep;
225     int xpos, ypos;
226     int c;
227    
228     notify_no_dispatch(); /* allow read to block */
229     window_set(canvas, WIN_CONSUME_KBD_EVENT, WIN_ASCII_EVENTS, 0);
230     while (window_read_event(canvas, ep) == 0) {
231     switch (event_id(ep)) {
232     case MS_LEFT:
233     case MB1:
234     c = MB1;
235     break;
236     case MS_MIDDLE:
237     case MB2:
238     c = MB2;
239     break;
240     case MS_RIGHT:
241     case MB3:
242     c = MB3;
243     break;
244     case ABORT:
245     c = ABORT;
246     break;
247     default:
248     continue;
249     }
250     xpos = event_x(ep);
251     ypos = yres-1 - event_y(ep);
252     break;
253     }
254     window_set(canvas, WIN_IGNORE_KBD_EVENT, WIN_ASCII_EVENTS, 0);
255     notify_do_dispatch();
256     putc(COM_GETCUR, stdout);
257     putc(c, stdout);
258     fwrite(&xpos, sizeof(xpos), 1, stdout);
259     fwrite(&ypos, sizeof(ypos), 1, stdout);
260     fflush(stdout);
261     }
262    
263    
264     mygets(s, fp) /* get string from file (with nul) */
265     register char *s;
266     register FILE *fp;
267     {
268     register int c;
269    
270     while ((c = getc(fp)) != EOF)
271     if ((*s++ = c) == '\0')
272     return;
273     *s = '\0';
274     }
275    
276    
277     myputs(s, fp) /* put string to file (with nul) */
278     register char *s;
279     register FILE *fp;
280     {
281     do
282     putc(*s, fp);
283     while (*s++);
284     }
285    
286    
287     ttyputs(s) /* put string out to tty subwindow */
288     register char *s;
289     {
290     char buf[256];
291     register char *cp;
292    
293     for (cp = buf; *s; s++) {
294     if (*s == '\n')
295     *cp++ = '\r';
296     *cp++ = *s;
297     }
298     ttysw_output(tty, buf, cp-buf);
299     }
300    
301    
302     int
303     pixel(col) /* return pixel value for color */
304     COLOR col;
305     {
306     COLR clr;
307     register int ndx;
308    
309     mapcolor(clr, col);
310     while ((ndx = insertcolr(clr)) < 0) {
311     reduce_colres();
312     mapcolor(clr, col);
313     }
314     return(ndx+FIRSTCOLOR);
315     }
316    
317    
318     int
319     insertcolr(clr) /* insert a new color */
320     register COLR clr;
321     {
322     int hval;
323     register int ndx, i;
324    
325     hval = ndx = hashcolr(clr);
326    
327     for (i = 1; i < NCOLORS; i++) {
328     if (colrtbl[ndx][EXP] == 0) {
329     colrtbl[ndx][RED] = clr[RED];
330     colrtbl[ndx][GRN] = clr[GRN];
331     colrtbl[ndx][BLU] = clr[BLU];
332     colrtbl[ndx][EXP] = COLXS;
333     newcolr(ndx, clr);
334     return(ndx);
335     }
336     if ( colrtbl[ndx][RED] == clr[RED] &&
337     colrtbl[ndx][GRN] == clr[GRN] &&
338     colrtbl[ndx][BLU] == clr[BLU] )
339     return(ndx);
340     ndx = (hval + i*i) % NCOLORS;
341     }
342     return(-1);
343     }
344    
345    
346     newcolr(ndx, clr) /* enter a color into hardware table */
347     int ndx;
348     COLR clr;
349     {
350     register Pixwin *pw;
351    
352     pw = canvas_pixwin(canvas);
353     pw_putcolormap(pw, ndx+FIRSTCOLOR, 1,
354     &clr[RED], &clr[GRN], &clr[BLU]);
355     pw = (Pixwin *)window_get(tty, WIN_PIXWIN);
356     pw_putcolormap(pw, ndx+FIRSTCOLOR, 1,
357     &clr[RED], &clr[GRN], &clr[BLU]);
358     }
359    
360    
361     reduce_colres() /* reduce the color resolution */
362     {
363     COLR oldtbl[NCOLORS];
364     unsigned char pixmap[256];
365     Pixwin *pw;
366     register int i, j;
367     register unsigned char *p;
368    
369     ttyputs("remapping colors...\n");
370     bcopy(colrtbl, oldtbl, sizeof(oldtbl));
371     colres >>= 1;
372     newmap();
373     for (i = 0; i < 256; i++)
374     pixmap[i] = i;
375     for (i = 0; i < NCOLORS; i++)
376     if (oldtbl[i][EXP] != 0) {
377     for (j = 0; j < 3; j++)
378     oldtbl[i][j] = ((oldtbl[i][j]*colres/256) *
379     256 + 128)/colres;
380     pixmap[i+FIRSTCOLOR] = insertcolr(oldtbl[i])+FIRSTCOLOR;
381     }
382     pw = canvas_pixwin(canvas);
383     /* I probably should get my own memory */
384     p = (unsigned char *)mpr_d(pw->pw_prretained)->md_image;
385     for (j = 0; j < yres; j++) {
386     for (i = 0; i < xres; i++) {
387     *p = pixmap[*p];
388     p++;
389     }
390     if (xres&1) /* 16-bit boundaries */
391     p++;
392     }
393     pw_rop(pw, 0, 0, xres, yres, PIX_SRC, pw->pw_prretained, 0, 0);
394     }
395    
396    
397     mapcolor(clr, col) /* map to our color space */
398     COLR clr;
399     COLOR col;
400     {
401     register int i, p;
402     /* compute color table value */
403     for (i = 0; i < 3; i++) {
404     p = colval(col,i) * 255.0 + 0.5;
405     if (p < 0) p = 0;
406     else if (p > 255) p = 255;
407     clr[i] = colrmap[p][i];
408     }
409     clr[EXP] = COLXS;
410     }
411    
412    
413     getmap() /* allocate color map segments */
414     {
415     char cmsname[20];
416     unsigned char red[256], green[256], blue[256];
417     register Pixwin *pw;
418     register int i;
419    
420     for (i = 0; i < 256; i++)
421     red[i] = green[i] = blue[i] = 128;
422     red[0] = green[0] = blue[0] = 255;
423     red[1] = green[1] = blue[1] = 0;
424     red[255] = green[255] = blue[255] = 0;
425     red[254] = green[254] = blue[254] = 255;
426     red[253] = green[253] = blue[253] = 0;
427     /* name shared segment */
428     sprintf(cmsname, "rv%d", getpid());
429     /* set canvas */
430     pw = canvas_pixwin(canvas);
431     if (pw->pw_pixrect->pr_depth < 8)
432     return(-1);
433     pw_setcmsname(pw, cmsname);
434     pw_putcolormap(pw, 0, 256, red, green, blue);
435     /* set tty subwindow */
436     pw = (Pixwin *)window_get(tty, WIN_PIXWIN);
437     pw_setcmsname(pw, cmsname);
438     pw_putcolormap(pw, 0, 256, red, green, blue);
439     /* set frame */
440     pw = (Pixwin *)window_get(frame, WIN_PIXWIN);
441     pw_setcmsname(pw, cmsname);
442     pw_putcolormap(pw, 0, 256, red, green, blue);
443    
444     return(0);
445     }
446    
447    
448     newmap() /* initialize our color table */
449     {
450     double pow();
451     int val;
452     register int i;
453    
454     for (i = 0; i < 256; i++) {
455     val = pow(i/256.0, 1.0/GAMMA) * colres;
456     val = (val*256 + 128) / colres;
457     colrmap[i][RED] = colrmap[i][GRN] = colrmap[i][BLU] = val;
458     colrmap[i][EXP] = COLXS;
459     }
460     for (i = 0; i < NCOLORS; i++)
461     colrtbl[i][EXP] = 0;
462     }