ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/pcomb.c
(Generate patch)

Comparing ray/src/px/pcomb.c (file contents):
Revision 1.16 by greg, Fri May 24 15:47:53 1991 UTC vs.
Revision 2.10 by greg, Thu Apr 29 14:32:07 1993 UTC

# Line 1 | Line 1
1 < /* Copyright (c) 1991 Regents of the University of California */
1 > /* Copyright (c) 1992 Regents of the University of California */
2  
3   #ifndef lint
4   static char SCCSid[] = "$SunId$ LBL";
# Line 10 | Line 10 | static char SCCSid[] = "$SunId$ LBL";
10   *      1/4/89
11   */
12  
13 < #include <stdio.h>
13 > #include "standard.h"
14  
15 #include <errno.h>
16
15   #include "color.h"
16  
17 + #include "resolu.h"
18 +
19   #include "calcomp.h"
20  
21 + #include "view.h"
22 +
23   #define MAXINP          32              /* maximum number of input files */
24   #define WINSIZ          9               /* scanline window size */
25   #define MIDSCN          4               /* current scan position */
26  
25 #define BRT             (-1)            /* special index for brightness */
26
27   struct {
28 <        char    *name;          /* file name */
28 >        char    *name;          /* file or command name */
29          FILE    *fp;            /* stream pointer */
30 +        VIEW    vw;             /* view for picture */
31 +        RESOLU  rs;             /* image resolution and orientation */
32          COLOR   *scan[WINSIZ];  /* input scanline window */
33          COLOR   coef;           /* coefficient */
34 +        COLOR   expos;          /* recorded exposure */
35   }       input[MAXINP];                  /* input pictures */
36  
37   int     nfiles;                         /* number of input files */
38  
39 < char    *vcolin[3] = {"ri", "gi", "bi"};
40 < char    *vcolout[3] = {"ro", "go", "bo"};
39 > char    Command[] = "<Command>";
40 > char    vcolin[3][4] = {"ri", "gi", "bi"};
41 > char    vcolout[3][4] = {"ro", "go", "bo"};
42   char    vbrtin[] = "li";
43   char    vbrtout[] = "lo";
44 < char    *vcolcoef[3] = {"rc", "gc", "bc"};
45 < char    vbrtcoef[] = "lc";
44 > char    vcolexp[3][4] = {"re", "ge", "be"};
45 > char    vbrtexp[] = "le";
46  
47 < #define vnfiles         "nfiles"
44 < #define vxres           "xres"
45 < #define vyres           "yres"
46 < #define vxpos           "x"
47 < #define vypos           "y"
47 > char    vray[6][4] = {"Ox", "Oy", "Oz", "Dx", "Dy", "Dz"};
48  
49 + char    vnfiles[] = "nfiles";
50 + char    vxmax[] = "xmax";
51 + char    vymax[] = "ymax";
52 + char    vxres[] = "xres";
53 + char    vyres[] = "yres";
54 + char    vxpos[] = "x";
55 + char    vypos[] = "y";
56 +
57   int     nowarn = 0;                     /* no warning messages? */
58  
59 < int     original = 0;                   /* origninal values? */
59 > int     xmax = 0, ymax = 0;             /* input resolution */
60  
61 < int     xres=0, yres=0;                 /* picture resolution */
61 > int     xscan, yscan;                   /* input position */
62  
63 < int     xpos, ypos;                     /* picture position */
63 > int     xres, yres;                     /* output resolution */
64  
65 + int     xpos, ypos;                     /* output position */
66 +
67 + char    *progname;                      /* global argv[0] */
68 +
69   int     wrongformat = 0;
70 + int     gotview;
71  
72 + FILE    *popen();
73  
74 + extern char     *emalloc();
75 +
76 +
77   main(argc, argv)
78   int     argc;
79   char    *argv[];
80   {
81 +        int     original;
82          double  f;
83          int     a, i;
84 + #ifdef MSDOS
85 +        extern int  _fmode;
86 +        _fmode = O_BINARY;
87 +        setmode(fileno(stdin), O_BINARY);
88 +        setmode(fileno(stdout), O_BINARY);
89 + #endif
90 +        progname = argv[0];
91                                                  /* scan options */
92          for (a = 1; a < argc; a++) {
93                  if (argv[a][0] == '-')
94                          switch (argv[a][1]) {
95                          case 'x':
71                                xres = atoi(argv[++a]);
72                                continue;
96                          case 'y':
97 <                                yres = atoi(argv[++a]);
97 >                                a++;
98                                  continue;
99                          case 'w':
100                                  nowarn = !nowarn;
101                                  continue;
79                        case 'o':
80                                original = !original;
81                                continue;
102                          case 'f':
103                          case 'e':
104                                  a++;
# Line 87 | Line 107 | char   *argv[];
107                  break;
108          }
109                                          /* process files */
110 <        for (nfiles = 0; nfiles < MAXINP; nfiles++)
110 >        for (nfiles = 0; nfiles < MAXINP; nfiles++) {
111                  setcolor(input[nfiles].coef, 1.0, 1.0, 1.0);
112 +                setcolor(input[nfiles].expos, 1.0, 1.0, 1.0);
113 +                copystruct(&input[nfiles].vw, &stdview);
114 +        }
115          nfiles = 0;
116 +        original = 0;
117          for ( ; a < argc; a++) {
118                  if (nfiles >= MAXINP) {
119                          eputs(argv[0]);
# Line 102 | Line 126 | char   *argv[];
126                                  input[nfiles].name = "<stdin>";
127                                  input[nfiles].fp = stdin;
128                                  break;
129 +                        case 'o':
130 +                                original++;
131 +                                continue;
132                          case 's':
133                                  f = atof(argv[++a]);
134                                  scalecolor(input[nfiles].coef, f);
# Line 115 | Line 142 | char   *argv[];
142                                  goto usage;
143                          }
144                  else {
145 <                        input[nfiles].name = argv[a];
146 <                        input[nfiles].fp = fopen(argv[a], "r");
145 >                        if (argv[a][0] == '!') {
146 >                                input[nfiles].name = Command;
147 >                                input[nfiles].fp = popen(argv[a]+1, "r");
148 >                        } else {
149 >                                input[nfiles].name = argv[a];
150 >                                input[nfiles].fp = fopen(argv[a], "r");
151 >                        }
152                          if (input[nfiles].fp == NULL) {
153                                  perror(argv[a]);
154                                  quit(1);
155                          }
156                  }
157                  checkfile();
158 +                if (original) {
159 +                        colval(input[nfiles].coef,RED) /=
160 +                                        colval(input[nfiles].expos,RED);
161 +                        colval(input[nfiles].coef,GRN) /=
162 +                                        colval(input[nfiles].expos,GRN);
163 +                        colval(input[nfiles].coef,BLU) /=
164 +                                        colval(input[nfiles].expos,BLU);
165 +                }
166                  nfiles++;
167 +                original = 0;
168          }
169 <        init();                         /* set constant expressions */
169 >        init();                         /* set constants */
170                                          /* go back and get expressions */
171          for (a = 1; a < argc; a++) {
172                  if (argv[a][0] == '-')
173                          switch (argv[a][1]) {
174                          case 'x':
175 +                                varset(vxres, ':', eval(argv[++a]));
176 +                                continue;
177                          case 'y':
178 <                                a++;
178 >                                varset(vyres, ':', eval(argv[++a]));
179                                  continue;
180                          case 'w':
138                        case 'o':
181                                  continue;
182                          case 'f':
183                                  fcompile(argv[++a]);
# Line 146 | Line 188 | char   *argv[];
188                          }
189                  break;
190          }
191 +                                                /* set/get output resolution */
192 +        if (!vardefined(vxres))
193 +                varset(vxres, ':', (double)xmax);
194 +        if (!vardefined(vyres))
195 +                varset(vyres, ':', (double)ymax);
196 +        xres = varvalue(vxres) + .5;
197 +        yres = varvalue(vyres) + .5;
198 +        if (xres <= 0 || yres <= 0) {
199 +                eputs(argv[0]);
200 +                eputs(": illegal output resolution\n");
201 +                quit(1);
202 +        }
203                                                  /* complete header */
204          printargs(argc, argv, stdout);
205          fputformat(COLRFMT, stdout);
206          putchar('\n');
207 <        fputresolu(YMAJOR|YDECR, xres, yres, stdout);
207 >        fprtresolu(xres, yres, stdout);
208                                                  /* combine pictures */
209          combine();
210          quit(0);
# Line 158 | Line 212 | usage:
212          eputs("Usage: ");
213          eputs(argv[0]);
214          eputs(
215 < " [-w][-h][-x xr][-y yr][-e expr][-f file] [ [-s f][-c r g b] pic ..]\n");
215 > " [-w][-x xr][-y yr][-e expr][-f file] [ [-o][-s f][-c r g b] pic ..]\n");
216          quit(1);
217   }
218  
# Line 173 | Line 227 | char   *s;
227          if (isformat(s)) {                      /* check format */
228                  formatval(fmt, s);
229                  wrongformat = strcmp(fmt, COLRFMT);
230 <        } else if (original && isexpos(s)) {    /* exposure */
177 <                d = 1.0/exposval(s);
178 <                scalecolor(input[nfiles].coef, d);
179 <        } else if (original && iscolcor(s)) {   /* color correction */
180 <                colcorval(ctmp, s);
181 <                colval(input[nfiles].coef,RED) /= colval(ctmp,RED);
182 <                colval(input[nfiles].coef,GRN) /= colval(ctmp,GRN);
183 <                colval(input[nfiles].coef,BLU) /= colval(ctmp,BLU);
184 <        } else {                                /* echo unaffected line */
185 <                putchar('\t');
186 <                fputs(s, stdout);
230 >                return;         /* don't echo */
231          }
232 +        if (isexpos(s)) {                       /* exposure */
233 +                d = exposval(s);
234 +                scalecolor(input[nfiles].expos, d);
235 +        } else if (iscolcor(s)) {               /* color correction */
236 +                colcorval(ctmp, s);
237 +                multcolor(input[nfiles].expos, ctmp);
238 +        } else if (isview(s) && sscanview(&input[nfiles].vw, s) > 0)
239 +                gotview++;
240 +                                                /* echo line */
241 +        putchar('\t');
242 +        fputs(s, stdout);
243   }
244  
245  
# Line 192 | Line 247 | checkfile()                    /* ready a file */
247   {
248          register int    i;
249                                          /* process header */
250 +        gotview = 0;
251          fputs(input[nfiles].name, stdout);
252          fputs(":\n", stdout);
253          getheader(input[nfiles].fp, tputs, NULL);
# Line 200 | Line 256 | checkfile()                    /* ready a file */
256                  eputs(": not in Radiance picture format\n");
257                  quit(1);
258          }
259 <        if (fgetresolu(&xpos, &ypos, input[nfiles].fp) != (YMAJOR|YDECR)) {
259 >        if (!gotview || setview(&input[nfiles].vw) != NULL)
260 >                input[nfiles].vw.type = 0;
261 >        if (!fgetsresolu(&input[nfiles].rs, input[nfiles].fp)) {
262                  eputs(input[nfiles].name);
263                  eputs(": bad picture size\n");
264                  quit(1);
265          }
266 <        if (xres == 0 && yres == 0) {
267 <                xres = xpos;
268 <                yres = ypos;
269 <        } else if (xpos != xres || ypos != yres) {
266 >        if (xmax == 0 && ymax == 0) {
267 >                xmax = scanlen(&input[nfiles].rs);
268 >                ymax = numscans(&input[nfiles].rs);
269 >        } else if (scanlen(&input[nfiles].rs) != xmax ||
270 >                        numscans(&input[nfiles].rs) != ymax) {
271                  eputs(input[nfiles].name);
272                  eputs(": resolution mismatch\n");
273                  quit(1);
274          }
275                                          /* allocate scanlines */
276          for (i = 0; i < WINSIZ; i++)
277 <                input[nfiles].scan[i] = (COLOR *)emalloc(xres*sizeof(COLOR));
277 >                input[nfiles].scan[i] = (COLOR *)emalloc(xmax*sizeof(COLOR));
278   }
279  
280  
281 < init()                          /* perform final setup */
281 > init()                                  /* perform final setup */
282   {
283 <        double  l_colin(), l_coef();
283 >        double  l_colin(), l_expos(), l_ray();
284          register int    i;
226                                                /* prime input */
227        for (ypos = yres+(MIDSCN-1); ypos >= yres; ypos--)
228                advance();
285                                                  /* define constants */
286          varset(vnfiles, ':', (double)nfiles);
287 <        varset(vxres, ':', (double)xres);
288 <        varset(vyres, ':', (double)yres);
287 >        varset(vxmax, ':', (double)xmax);
288 >        varset(vymax, ':', (double)ymax);
289                                                  /* set functions */
290          for (i = 0; i < 3; i++) {
291 <                funset(vcolcoef[i], 1, ':', l_coef);
291 >                funset(vcolexp[i], 1, ':', l_expos);
292                  funset(vcolin[i], 1, '=', l_colin);
293          }
294 <        funset(vbrtcoef, 1, ':', l_coef);
294 >        funset(vbrtexp, 1, ':', l_expos);
295          funset(vbrtin, 1, '=', l_colin);
296 +        for (i = 0; i < 6; i++)
297 +                funset(vray[i], 1, '=', l_ray);
298   }
299  
300  
# Line 259 | Line 317 | combine()                      /* combine pictures */
317                  brtdef = NULL;
318                                                  /* allocate scanline */
319          scanout = (COLOR *)emalloc(xres*sizeof(COLOR));
320 +                                                /* set input position */
321 +        yscan = ymax+MIDSCN;
322                                                  /* combine files */
323          for (ypos = yres-1; ypos >= 0; ypos--) {
324              advance();
325              varset(vypos, '=', (double)ypos);
326              for (xpos = 0; xpos < xres; xpos++) {
327 +                xscan = (long)xpos*xmax/xres;
328                  varset(vxpos, '=', (double)xpos);
329                  eclock++;
330                  if (brtdef != NULL) {
# Line 278 | Line 339 | combine()                      /* combine pictures */
339                          } else {
340                              d = 0.0;
341                              for (i = 0; i < nfiles; i++)
342 <                                d += colval(input[i].scan[MIDSCN][xpos],j);
342 >                                d += colval(input[i].scan[MIDSCN][xscan],j);
343                          }
344                          if (d < 0.0)
345                              d = 0.0;
# Line 295 | Line 356 | combine()                      /* combine pictures */
356   }
357  
358  
359 < advance()                       /* read in next scanline */
359 > advance()                       /* read in data for next scanline */
360   {
361 +        int     ytarget;
362          register COLOR  *st;
363          register int    i, j;
364  
365 <        for (i = 0; i < nfiles; i++) {
366 <                st = input[i].scan[WINSIZ-1];
367 <                for (j = WINSIZ-1; j > 0; j--)  /* rotate window */
368 <                        input[i].scan[j] = input[i].scan[j-1];
369 <                input[i].scan[0] = st;
370 <                if (ypos < MIDSCN)              /* hit bottom */
371 <                        continue;
372 <                if (freadscan(st, xres, input[i].fp) < 0) {
373 <                        eputs(input[i].name);
374 <                        eputs(": read error\n");
375 <                        quit(1);
365 >        for (ytarget = (long)ypos*ymax/yres; yscan > ytarget; yscan--)
366 >                for (i = 0; i < nfiles; i++) {
367 >                        st = input[i].scan[WINSIZ-1];
368 >                        for (j = WINSIZ-1; j > 0; j--)  /* rotate window */
369 >                                input[i].scan[j] = input[i].scan[j-1];
370 >                        input[i].scan[0] = st;
371 >                        if (yscan <= MIDSCN)            /* hit bottom? */
372 >                                continue;
373 >                        if (freadscan(st, xmax, input[i].fp) < 0) {  /* read */
374 >                                eputs(input[i].name);
375 >                                eputs(": read error\n");
376 >                                quit(1);
377 >                        }
378 >                        if (fabs(colval(input[i].coef,RED)-1.0) > 1e-3 ||
379 >                                fabs(colval(input[i].coef,GRN)-1.0) > 1e-3 ||
380 >                                fabs(colval(input[i].coef,BLU)-1.0) > 1e-3)
381 >                                for (j = 0; j < xmax; j++)  /* adjust color */
382 >                                        multcolor(st[j], input[i].coef);
383                  }
315                for (j = 0; j < xres; j++)      /* adjust color */
316                        multcolor(st[j], input[i].coef);
317        }
384   }
385  
386  
387   double
388 < l_coef(nam)                     /* return picture coefficients */
388 > l_expos(nam)                    /* return picture exposure */
389   register char   *nam;
390   {
391          register int    fn, n;
326        double  d;
392  
393 <        d = argument(1);
394 <        if (d > -.5 && d < .5)
395 <                return((double)nfiles);
396 <        fn = d - .5;
397 <        if (fn < 0 || fn >= nfiles) {
333 <                errno = EDOM;
334 <                return(0.0);
335 <        }
336 <        if (nam == vbrtcoef)
337 <                return(bright(input[fn].coef));
393 >        fn = argument(1) - .5;
394 >        if (fn < 0 || fn >= nfiles)
395 >                return(1.0);
396 >        if (nam == vbrtexp)
397 >                return(bright(input[fn].expos));
398          n = 3;
399          while (n--)
400 <                if (nam == vcolcoef[n])
401 <                        return(colval(input[fn].coef,n));
402 <        eputs("Bad call to l_coef()!\n");
400 >                if (nam == vcolexp[n])
401 >                        return(colval(input[fn].expos,n));
402 >        eputs("Bad call to l_expos()!\n");
403          quit(1);
404   }
405  
# Line 366 | Line 426 | register char  *nam;
426                  d = argument(2);
427                  if (d < 0.0) {
428                          xoff = d-.5;
429 <                        if (xpos+xoff < 0)
430 <                                xoff = -xpos;
429 >                        if (xscan+xoff < 0)
430 >                                xoff = -xscan;
431                  } else {
432                          xoff = d+.5;
433 <                        if (xpos+xoff >= xres)
434 <                                xoff = xres-1-xpos;
433 >                        if (xscan+xoff >= xmax)
434 >                                xoff = xmax-1-xscan;
435                  }
436          }
437          if (n >= 3) {
# Line 380 | Line 440 | register char  *nam;
440                          yoff = d-.5;
441                          if (yoff+MIDSCN < 0)
442                                  yoff = -MIDSCN;
443 <                        if (ypos+yoff < 0)
444 <                                yoff = -ypos;
443 >                        if (yscan+yoff < 0)
444 >                                yoff = -yscan;
445                  } else {
446                          yoff = d+.5;
447                          if (yoff+MIDSCN >= WINSIZ)
448                                  yoff = WINSIZ-1-MIDSCN;
449 <                        if (ypos+yoff >= yres)
450 <                                yoff = yres-1-ypos;
449 >                        if (yscan+yoff >= ymax)
450 >                                yoff = ymax-1-yscan;
451                  }
452          }
453          if (nam == vbrtin)
454 <                return(bright(input[fn].scan[MIDSCN+yoff][xpos+xoff]));
454 >                return(bright(input[fn].scan[MIDSCN+yoff][xscan+xoff]));
455          n = 3;
456          while (n--)
457              if (nam == vcolin[n])
458 <                return(colval(input[fn].scan[MIDSCN+yoff][xpos+xoff],n));
458 >                return(colval(input[fn].scan[MIDSCN+yoff][xscan+xoff],n));
459          eputs("Bad call to l_colin()!\n");
460          quit(1);
461   }
462  
463  
464 + double
465 + l_ray(nam)              /* return ray origin or direction */
466 + register char   *nam;
467 + {
468 +        static long     ltick[MAXINP];
469 +        static FVECT    lorg[MAXINP], ldir[MAXINP];
470 +        FLOAT   loc[2];
471 +        double  d;
472 +        int     fn;
473 +        register int    i;
474 +
475 +        d = argument(1);
476 +        if (d > -.5 && d < .5)
477 +                return((double)nfiles);
478 +        fn = d - .5;
479 +        if (fn < 0 || fn >= nfiles) {
480 +                errno = EDOM;
481 +                return(0.0);
482 +        }
483 +        if (ltick[fn] < eclock) {               /* need to compute? */
484 +                lorg[fn][0] = lorg[fn][1] = lorg[fn][2] = 0.0;
485 +                ldir[fn][0] = ldir[fn][1] = ldir[fn][2] = 0.0;
486 +                if (input[fn].vw.type == 0)
487 +                        errno = ERANGE;
488 +                else {
489 +                        pix2loc(loc, &input[fn].rs, xpos, ypos);
490 +                        if (viewray(lorg[fn], ldir[fn],
491 +                                        &input[fn].vw, loc[0], loc[1]) < 0)
492 +                                errno = ERANGE;
493 +                }
494 +                ltick[fn] = eclock;
495 +        }
496 +        i = 6;
497 +        while (i--)
498 +                if (nam == vray[i])
499 +                        return(i < 3 ? lorg[fn][i] : ldir[fn][i-3]);
500 +        eputs("Bad call to l_ray()!\n");
501 +        quit(1);
502 + }
503 +
504 +
505   wputs(msg)
506   char    *msg;
507   {
# Line 416 | Line 517 | char   *msg;
517   }
518  
519  
520 < quit(code)
521 < int     code;
520 > quit(code)              /* exit gracefully */
521 > int  code;
522   {
523 +        register int  i;
524 +                                /* close input files */
525 +        for (i = 0; i < nfiles; i++)
526 +                if (input[i].name == Command)
527 +                        pclose(input[i].fp);
528 +                else
529 +                        fclose(input[i].fp);
530          exit(code);
531   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines