ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/pvalue.c
Revision: 2.45
Committed: Mon Sep 16 23:02:53 2024 UTC (5 months, 4 weeks ago) by greg
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 2.44: +4 -2 lines
Log Message:
fix(pvalue): Fixed issue with -r -h -b combo

File Contents

# Content
1 #ifndef lint
2 static const char RCSid[] = "$Id: pvalue.c,v 2.44 2024/09/11 23:21:01 greg Exp $";
3 #endif
4 /*
5 * pvalue.c - program to print pixel values.
6 *
7 * 4/23/86
8 */
9
10 #include "platform.h"
11 #include "standard.h"
12 #include "color.h"
13 #include "resolu.h"
14 #include "view.h"
15
16 #define min(a,b) ((a)<(b)?(a):(b))
17
18 /* what to put out (also RED, GRN, BLU) */
19 #define ALL 3
20 #define BRIGHT 4
21
22 RESOLU picres; /* resolution of picture */
23 int uniq = 0; /* print only unique values? */
24 int doexposure = 0; /* exposure change? (>100 to print) */
25 int dataonly = 0; /* data only format? */
26 int putprim = ALL; /* what to put out */
27 int reverse = 0; /* reverse conversion? */
28 int format = 'a'; /* input/output format */
29 const char *fmtid = "ascii"; /* format identifier for header */
30 int header = 1; /* do header? */
31 long skipbytes = 0; /* skip bytes in input? */
32 int swapbytes = 0; /* swap bytes? */
33 int interleave = 1; /* file is interleaved? */
34 int resolution = 1; /* put/get resolution string? */
35 int original = 0; /* convert to original values? */
36 int wrongformat = 0; /* wrong input format? */
37 double gamcor = 1.0; /* gamma correction */
38
39 RGBPRIMP outprims = stdprims; /* output primaries for reverse conversion */
40 RGBPRIMS myprims;
41
42 int ord[3] = {RED, GRN, BLU}; /* RGB ordering */
43 int rord[4]; /* reverse ordering */
44
45 COLOR exposure = WHTCOLOR;
46
47 char *progname;
48
49 FILE *fin;
50 FILE *fin2 = NULL, *fin3 = NULL; /* for other color channels */
51
52
53 typedef int getfunc_t(COLOR col);
54 typedef int putfunc_t(COLOR col);
55 typedef double brightfunc_t(COLOR col);
56
57 getfunc_t *getval;
58 putfunc_t *putval;
59 brightfunc_t *mybright;
60
61 static gethfunc checkhead;
62 static brightfunc_t rgb_bright, xyz_bright;
63 static getfunc_t getbascii, getbint, getbdouble, getbfloat, getbbyte, getbword;
64 static getfunc_t getcascii, getcint, getcdouble, getcfloat, getcbyte, getcword;
65 static putfunc_t putbascii, putbint, putbdouble, putbfloat, putbbyte, putbword;
66 static putfunc_t putcascii, putcint, putcdouble, putcfloat, putcbyte, putcword;
67 static putfunc_t putpascii, putpint, putpdouble, putpfloat, putpbyte, putpword;
68
69 static int IDformat(const char *s);
70 static void set_io(void);
71 static void pixtoval(void);
72 static void valtopix(void);
73
74
75 static double
76 rgb_bright(
77 COLOR clr
78 )
79 {
80 return(bright(clr));
81 }
82
83 static double
84 xyz_bright(
85 COLOR clr
86 )
87 {
88 return(clr[CIEY]);
89 }
90
91 int
92 main(
93 int argc,
94 char **argv
95 )
96 {
97 const char *inpmode = "r";
98 double d, expval = 1.0;
99 int i;
100
101 progname = argv[0];
102 mybright = &rgb_bright; /* default */
103 picres.rt = PIXSTANDARD;
104
105 for (i = 1; i < argc; i++)
106 if (argv[i][0] == '-' || argv[i][0] == '+')
107 switch (argv[i][1]) {
108 case 'h': /* header */
109 header = argv[i][0] == '+';
110 break;
111 case 'H': /* resolution string */
112 resolution = argv[i][0] == '+';
113 break;
114 case 's': /* skip bytes in header */
115 skipbytes = atol(argv[++i]);
116 break;
117 case 'u': /* unique values */
118 uniq = argv[i][0] == '-';
119 break;
120 case 'o': /* original values */
121 original = argv[i][0] == '-';
122 break;
123 case 'O': /* original watts/sr/m^2 */
124 original = -(argv[i][0] == '-');
125 break;
126 case 'g': /* gamma correction */
127 gamcor = atof(argv[i+1]);
128 if (argv[i][0] == '+')
129 gamcor = 1.0/gamcor;
130 i++;
131 break;
132 case 'e': /* exposure correction */
133 d = atof(argv[i+1]);
134 if (argv[i+1][0] == '-' || argv[i+1][0] == '+')
135 d = pow(2.0, d);
136 if (argv[i][0] == '-')
137 expval *= d;
138 scalecolor(exposure, d);
139 doexposure++;
140 i++;
141 break;
142 case 'R': /* reverse byte sequence */
143 if (argv[i][0] == '-') {
144 ord[0]=BLU; ord[1]=GRN; ord[2]=RED;
145 } else {
146 ord[0]=RED; ord[1]=GRN; ord[2]=BLU;
147 }
148 break;
149 case 'r': /* reverse conversion */
150 reverse = argv[i][0] == '-';
151 break;
152 case 'n': /* non-interleaved RGB */
153 interleave = argv[i][0] == '+';
154 break;
155 case 'b': /* brightness values */
156 putprim = argv[i][0] == '-' ? BRIGHT : ALL;
157 break;
158 case 'p': /* primary controls */
159 switch (argv[i][2]) {
160 /* these two options affect -r conversion */
161 case '\0':
162 myprims[RED][CIEX] = atof(argv[++i]);
163 myprims[RED][CIEY] = atof(argv[++i]);
164 myprims[GRN][CIEX] = atof(argv[++i]);
165 myprims[GRN][CIEY] = atof(argv[++i]);
166 myprims[BLU][CIEX] = atof(argv[++i]);
167 myprims[BLU][CIEY] = atof(argv[++i]);
168 myprims[WHT][CIEX] = atof(argv[++i]);
169 myprims[WHT][CIEY] = atof(argv[++i]);
170 outprims = myprims;
171 break;
172 case 'x': case 'X': outprims = NULL; break;
173 /* the following options affect +r only */
174 case 'r': case 'R': putprim = RED; break;
175 case 'g': case 'G': putprim = GRN; break;
176 case 'b': case 'B': putprim = BLU; break;
177 default: goto unkopt;
178 }
179 break;
180 case 'd': /* data only (no indices) */
181 dataonly = (argv[i][0] == '-');
182 switch (argv[i][2]) {
183 case '\0':
184 case 'a': /* ascii */
185 format = 'a';
186 fmtid = "ascii";
187 break;
188 case 'i': /* integer */
189 format = 'i';
190 fmtid = "ascii";
191 break;
192 case 'b': /* byte */
193 dataonly = 1;
194 format = 'b';
195 fmtid = "byte";
196 break;
197 case 'W': /* 16-bit swapped */
198 swapbytes = 1;
199 case 'w': /* 16-bit */
200 dataonly = 1;
201 format = 'w';
202 fmtid = "16-bit";
203 break;
204 case 'F': /* swapped floats */
205 swapbytes = 1;
206 case 'f': /* float */
207 dataonly = 1;
208 format = 'f';
209 fmtid = "float";
210 break;
211 case 'D': /* swapped doubles */
212 swapbytes = 1;
213 case 'd': /* double */
214 dataonly = 1;
215 format = 'd';
216 fmtid = "double";
217 break;
218 default:
219 goto unkopt;
220 }
221 break;
222 case 'x': /* x resolution */
223 case 'X':
224 resolution = 0;
225 if (argv[i][0] == '-')
226 picres.rt |= XDECR;
227 else
228 picres.rt &= ~XDECR;
229 if (picres.yr == 0)
230 picres.rt &= ~YMAJOR;
231 picres.xr = atoi(argv[++i]);
232 break;
233 case 'y': /* y resolution */
234 case 'Y':
235 resolution = 0;
236 if (argv[i][0] == '-')
237 picres.rt |= YDECR;
238 else
239 picres.rt &= ~YDECR;
240 if (picres.xr == 0)
241 picres.rt |= YMAJOR;
242 picres.yr = atoi(argv[++i]);
243 break;
244 default:
245 unkopt:
246 fprintf(stderr, "%s: unknown option: %s\n",
247 progname, argv[i]);
248 quit(1);
249 break;
250 }
251 else
252 break;
253 /* recognize special formats */
254 if (dataonly & (format == 'b')) {
255 if (putprim == ALL)
256 fmtid = "24-bit_rgb";
257 else
258 fmtid = "8-bit_grey";
259 }
260 if (dataonly & (format == 'w')) {
261 if (putprim == ALL)
262 fmtid = "48-bit_rgb";
263 else
264 fmtid = "16-bit_grey";
265 }
266 if (!reverse | ((format != 'a') & (format != 'i')))
267 inpmode = "rb";
268 /* assign reverse ordering */
269 rord[ord[0]] = 0;
270 rord[ord[1]] = 1;
271 rord[ord[2]] = 2;
272 /* get input */
273 if (i == argc) {
274 long n = skipbytes;
275 if (inpmode[1] == 'b')
276 SET_FILE_BINARY(stdin);
277 while (n-- > 0)
278 if (getchar() == EOF) {
279 fprintf(stderr,
280 "%s: cannot skip %ld bytes on standard input\n",
281 progname, skipbytes);
282 quit(1);
283 }
284 fin = stdin;
285 } else if (i < argc) {
286 if ((fin = fopen(argv[i], inpmode)) == NULL) {
287 fprintf(stderr, "%s: can't open file \"%s\"\n",
288 progname, argv[i]);
289 quit(1);
290 }
291 if (reverse & (putprim != BRIGHT ) & (i == argc-3)) {
292 if ((fin2 = fopen(argv[i+1], inpmode)) == NULL) {
293 fprintf(stderr, "%s: can't open file \"%s\"\n",
294 progname, argv[i+1]);
295 quit(1);
296 }
297 if ((fin3 = fopen(argv[i+2], inpmode)) == NULL) {
298 fprintf(stderr, "%s: can't open file \"%s\"\n",
299 progname, argv[i+2]);
300 quit(1);
301 }
302 interleave = -1;
303 } else if (i != argc-1)
304 fin = NULL;
305 if (reverse & (putprim != BRIGHT) & !interleave) {
306 fin2 = fopen(argv[i], inpmode);
307 fin3 = fopen(argv[i], inpmode);
308 }
309 if (skipbytes && (fseek(fin, skipbytes, SEEK_SET) || (fin2 != NULL &&
310 fseek(fin2, skipbytes, SEEK_SET) |
311 fseek(fin3, skipbytes, SEEK_SET)))) {
312 fprintf(stderr, "%s: cannot skip %ld bytes on input\n",
313 progname, skipbytes);
314 quit(1);
315 }
316 }
317 if (fin == NULL) {
318 fprintf(stderr, "%s: bad # file arguments\n", progname);
319 quit(1);
320 }
321 if (reverse) {
322 SET_FILE_BINARY(stdout);
323 /* get header */
324 if (header) {
325 getheader(fin, checkhead, stdout);
326 if (wrongformat) {
327 fprintf(stderr, "%s: wrong input format (expected %s)\n",
328 progname, fmtid);
329 quit(1);
330 }
331 if (fin2 != NULL) {
332 getheader(fin2, NULL, NULL);
333 getheader(fin3, NULL, NULL);
334 }
335 resolution &= (picres.xr <= 0) | (picres.yr <= 0);
336 } else {
337 newheader("RADIANCE", stdout);
338 }
339 /* get resolution */
340 if ((resolution && !fgetsresolu(&picres, fin)) ||
341 (picres.xr <= 0) | (picres.yr <= 0)) {
342 fprintf(stderr, "%s: missing resolution\n", progname);
343 quit(1);
344 }
345 if (resolution && fin2 != NULL) {
346 RESOLU pres2;
347 if (!fgetsresolu(&pres2, fin2) ||
348 (pres2.rt != picres.rt) |
349 (pres2.xr != picres.xr) |
350 (pres2.yr != picres.yr) ||
351 !fgetsresolu(&pres2, fin3) ||
352 (pres2.rt != picres.rt) |
353 (pres2.xr != picres.xr) |
354 (pres2.yr != picres.yr)) {
355 fprintf(stderr, "%s: resolution mismatch\n",
356 progname);
357 quit(1);
358 }
359 }
360 /* add to header */
361 printargs(i, argv, stdout);
362 if ((expval < .99) | (expval > 1.01))
363 fputexpos(expval, stdout);
364 if (!header & (putprim != ALL)) {
365 NCSAMP = 1; /* no header, so trust user */
366 } else if (NCSAMP == 1) {
367 if (putprim == ALL)
368 putprim = BRIGHT;
369 } else {
370 if (NCSAMP != 3) {
371 fprintf(stderr, "%s: input NCOMP must be 1 or 3\n",
372 progname);
373 quit(1);
374 }
375 if (putprim != ALL) {
376 fprintf(stderr, "%s: NCOMP mismatch\n", progname);
377 quit(1);
378 }
379 }
380 if (outprims != NULL) {
381 if (outprims != stdprims)
382 fputprims(outprims, stdout);
383 fputformat(COLRFMT, stdout);
384 } else { /* XYZ data */
385 if (original < 0) {
386 scalecolor(exposure, WHTEFFICACY);
387 doexposure++;
388 }
389 fputformat(CIEFMT, stdout);
390 }
391 putchar('\n');
392 fputsresolu(&picres, stdout); /* always put resolution */
393 valtopix();
394 } else {
395 if ((format != 'a') & (format != 'i'))
396 SET_FILE_BINARY(stdout);
397 /* get header */
398 picres.rt = PIXSTANDARD;
399 picres.xr = picres.yr = 0;
400 getheader(fin, checkhead, header ? stdout : (FILE *)NULL);
401 if (wrongformat) {
402 fprintf(stderr,
403 "%s: input not a Radiance RGBE picture\n",
404 progname);
405 quit(1);
406 }
407 if ((picres.xr <= 0) | (picres.yr <= 0) &&
408 !fgetsresolu(&picres, fin)) {
409 fprintf(stderr, "%s: missing resolution\n", progname);
410 quit(1);
411 }
412 if ((original < 0) & (mybright == &xyz_bright)) {
413 scalecolor(exposure, 1./WHTEFFICACY);
414 doexposure++;
415 }
416 if (header) {
417 printargs(i, argv, stdout);
418 if (dataonly)
419 printf("%s%c\n", NCOMPSTR, "13"[putprim==ALL]);
420 if (dataonly && !resolution & !uniq)
421 printf("NCOLS=%d\nNROWS=%d\n", scanlen(&picres),
422 numscans(&picres));
423 if ((expval < .99) | (expval > 1.01))
424 fputexpos(expval, stdout);
425 if (swapbytes) {
426 if (nativebigendian())
427 puts("BigEndian=0");
428 else
429 puts("BigEndian=1");
430 } else if ((format != 'a') & (format != 'i') &
431 (format != 'b'))
432 fputendian(stdout);
433 fputformat(fmtid, stdout);
434 putchar('\n');
435 }
436 if (resolution) /* put resolution */
437 fputsresolu(&picres, stdout);
438 pixtoval();
439 }
440
441 quit(0);
442 return 0; /* pro forma return */
443 }
444
445
446 static int
447 IDformat(const char *s)
448 {
449 if (!s || !*s) return(0);
450 if (!strcmp(s, "ascii")) return('a');
451 if (!strcmp(s, "float")) return('f');
452 if (!strcmp(s, "double")) return('d');
453 if (!strcmp(s, "byte")) return('b');
454 if (!strcmp(s, "16-bit")) return('w');
455 return(0);
456 }
457
458
459 static int
460 checkhead( /* deal with line from header */
461 char *line,
462 void *p
463 )
464 {
465 static char fmt[MAXFMTLEN];
466 FILE *fout = (FILE *)p;
467 double d;
468 COLOR ctmp;
469 int rv;
470
471 if (formatval(fmt, line)) {
472 if (reverse) {
473 if (format == 'a') {
474 format = IDformat(fmt);
475 if (format)
476 fmtid = fmt;
477 else
478 wrongformat = 1;
479 } else
480 wrongformat = strcmp(fmt, fmtid);
481 } else if (!strcmp(fmt, CIEFMT))
482 mybright = &xyz_bright;
483 else if (!strcmp(fmt, COLRFMT) || !strcmp(fmt, SPECFMT))
484 mybright = &rgb_bright;
485 else
486 wrongformat = 1;
487 return(1);
488 }
489 if (!strncmp(line,"NROWS=",6)) {
490 picres.yr = atoi(line+6);
491 return(1);
492 }
493 if (!strncmp(line,"NCOLS=",6)) {
494 picres.xr = atoi(line+6);
495 return(1);
496 }
497 if (isncomp(line)) {
498 NCSAMP = ncompval(line);
499 dataonly |= reverse; /* pretty safe assumption */
500 return(1);
501 }
502 if (iswlsplit(line)) {
503 wlsplitval(WLPART, line);
504 return(1);
505 }
506 if (original && isexpos(line)) {
507 d = 1.0/exposval(line);
508 scalecolor(exposure, d);
509 doexposure++;
510 return(1);
511 }
512 if (original && iscolcor(line)) {
513 colcorval(ctmp, line);
514 setcolor(exposure, colval(exposure,RED)/colval(ctmp,RED),
515 colval(exposure,GRN)/colval(ctmp,GRN),
516 colval(exposure,BLU)/colval(ctmp,BLU));
517 doexposure++;
518 return(1);
519 }
520 if ((rv = isbigendian(line)) >= 0) {
521 if (reverse)
522 swapbytes = (nativebigendian() != rv);
523 return(1);
524 }
525 if (fout != NULL)
526 fputs(line, fout);
527 return(0);
528 }
529
530
531 static void
532 pixtoval(void) /* convert picture to values */
533 {
534 COLOR *scanln;
535 int dogamma;
536 COLOR lastc;
537 RREAL hv[2];
538 int startprim, endprim;
539 long startpos;
540 int x, y;
541
542 scanln = (COLOR *)malloc(scanlen(&picres)*sizeof(COLOR));
543 if (scanln == NULL) {
544 fprintf(stderr, "%s: out of memory\n", progname);
545 quit(1);
546 }
547 dogamma = gamcor < .95 || gamcor > 1.05;
548 if ((putprim == ALL) & !interleave) {
549 startprim = RED; endprim = BLU;
550 startpos = ftell(fin);
551 } else {
552 startprim = putprim; endprim = putprim;
553 }
554 for (putprim = startprim; putprim <= endprim; putprim++) {
555 if (putprim != startprim && fseek(fin, startpos, SEEK_SET)) {
556 fprintf(stderr, "%s: seek error on input file\n",
557 progname);
558 quit(1);
559 }
560 set_io();
561 setcolor(lastc, 0.0, 0.0, 0.0);
562 for (y = 0; y < numscans(&picres); y++) {
563 if (fread2scan(scanln, scanlen(&picres), fin,
564 NCSAMP, WLPART) < 0) {
565 fprintf(stderr, "%s: read error\n", progname);
566 quit(1);
567 }
568 for (x = 0; x < scanlen(&picres); x++) {
569 if (uniq) {
570 if ( colval(scanln[x],RED) ==
571 colval(lastc,RED) &&
572 colval(scanln[x],GRN) ==
573 colval(lastc,GRN) &&
574 colval(scanln[x],BLU) ==
575 colval(lastc,BLU) )
576 continue;
577 else
578 copycolor(lastc, scanln[x]);
579 }
580 if (doexposure)
581 multcolor(scanln[x], exposure);
582 if (dogamma)
583 setcolor(scanln[x],
584 pow(colval(scanln[x],RED), 1.0/gamcor),
585 pow(colval(scanln[x],GRN), 1.0/gamcor),
586 pow(colval(scanln[x],BLU), 1.0/gamcor));
587 if (!dataonly) {
588 pix2loc(hv, &picres, x, y);
589 printf("%7d %7d ",
590 (int)(hv[0]*picres.xr),
591 (int)(hv[1]*picres.yr));
592 }
593 if ((*putval)(scanln[x]) < 0) {
594 fprintf(stderr, "%s: write error\n",
595 progname);
596 quit(1);
597 }
598 }
599 }
600 }
601 free((void *)scanln);
602 }
603
604
605 static void
606 valtopix(void) /* convert values to a pixel file */
607 {
608 int dogamma;
609 COLOR *scanln;
610 COLR rgbe;
611 int x, y;
612
613 scanln = (COLOR *)malloc(scanlen(&picres)*sizeof(COLOR));
614 if (scanln == NULL) {
615 fprintf(stderr, "%s: out of memory\n", progname);
616 quit(1);
617 }
618 dogamma = gamcor < .95 || gamcor > 1.05;
619 set_io();
620 for (y = 0; y < numscans(&picres); y++) {
621 for (x = 0; x < scanlen(&picres); x++) {
622 if (!dataonly) {
623 fscanf(fin, "%*d %*d");
624 if (fin2 != NULL) {
625 fscanf(fin2, "%*d %*d");
626 fscanf(fin3, "%*d %*d");
627 }
628 }
629 if ((*getval)(scanln[x]) < 0) {
630 fprintf(stderr, "%s: read error\n", progname);
631 quit(1);
632 }
633 if (dogamma)
634 setcolor(scanln[x],
635 pow(colval(scanln[x],RED), gamcor),
636 pow(colval(scanln[x],GRN), gamcor),
637 pow(colval(scanln[x],BLU), gamcor));
638 if (doexposure)
639 multcolor(scanln[x], exposure);
640 if (uniq) { /* uncompressed? */
641 setcolr(rgbe, scanln[x][RED],
642 scanln[x][GRN],
643 scanln[x][BLU]);
644 if (putbinary(rgbe, sizeof(COLR), 1, stdout) != 1)
645 goto writerr;
646 }
647 }
648 /* write scan if compressed */
649 if (!uniq && fwritescan(scanln, scanlen(&picres), stdout) < 0)
650 goto writerr;
651 }
652 free((void *)scanln);
653 return;
654 writerr:
655 fprintf(stderr, "%s: write error\n", progname);
656 quit(1);
657 }
658
659
660 void
661 quit(code)
662 int code;
663 {
664 exit(code);
665 }
666
667
668 static int
669 getcascii( /* get an ascii color value from stream(s) */
670 COLOR col
671 )
672 {
673 double vd[3];
674
675 if (fin2 == NULL) {
676 if (fscanf(fin, "%lf %lf %lf", &vd[0], &vd[1], &vd[2]) != 3)
677 return(-1);
678 } else {
679 if (fscanf(fin, "%lf", &vd[0]) != 1 ||
680 fscanf(fin2, "%lf", &vd[1]) != 1 ||
681 fscanf(fin3, "%lf", &vd[2]) != 1)
682 return(-1);
683 }
684 setcolor(col, vd[rord[RED]], vd[rord[GRN]], vd[rord[BLU]]);
685 return(0);
686 }
687
688
689 static int
690 getcdouble( /* get a double color value from stream(s) */
691 COLOR col
692 )
693 {
694 double vd[3];
695
696 if (fin2 == NULL) {
697 if (getbinary(vd, sizeof(double), 3, fin) != 3)
698 return(-1);
699 } else {
700 if (getbinary(vd, sizeof(double), 1, fin) != 1 ||
701 getbinary(vd+1, sizeof(double), 1, fin2) != 1 ||
702 getbinary(vd+2, sizeof(double), 1, fin3) != 1)
703 return(-1);
704 }
705 if (swapbytes)
706 swap64((char *)vd, 3);
707 setcolor(col, vd[rord[RED]], vd[rord[GRN]], vd[rord[BLU]]);
708 return(0);
709 }
710
711
712 static int
713 getcfloat( /* get a float color value from stream(s) */
714 COLOR col
715 )
716 {
717 float vf[3];
718
719 if (fin2 == NULL) {
720 if (getbinary(vf, sizeof(float), 3, fin) != 3)
721 return(-1);
722 } else {
723 if (getbinary(vf, sizeof(float), 1, fin) != 1 ||
724 getbinary(vf+1, sizeof(float), 1, fin2) != 1 ||
725 getbinary(vf+2, sizeof(float), 1, fin3) != 1)
726 return(-1);
727 }
728 if (swapbytes)
729 swap32((char *)vf, 3);
730 setcolor(col, vf[rord[RED]], vf[rord[GRN]], vf[rord[BLU]]);
731 return(0);
732 }
733
734
735 static int
736 getcint( /* get an int color value from stream(s) */
737 COLOR col
738 )
739 {
740 int vi[3];
741
742 if (fin2 == NULL) {
743 if (fscanf(fin, "%d %d %d", &vi[0], &vi[1], &vi[2]) != 3)
744 return(-1);
745 } else {
746 if (fscanf(fin, "%d", &vi[0]) != 1 ||
747 fscanf(fin2, "%d", &vi[1]) != 1 ||
748 fscanf(fin3, "%d", &vi[2]) != 1)
749 return(-1);
750 }
751 setcolor(col, (vi[rord[RED]]+.5)/256.,
752 (vi[rord[GRN]]+.5)/256., (vi[rord[BLU]]+.5)/256.);
753 return(0);
754 }
755
756
757 static int
758 getcbyte( /* get a byte color value from stream(s) */
759 COLOR col
760 )
761 {
762 uby8 vb[3];
763
764 if (fin2 == NULL) {
765 if (getbinary(vb, sizeof(uby8), 3, fin) != 3)
766 return(-1);
767 } else {
768 if (getbinary(vb, sizeof(uby8), 1, fin) != 1 ||
769 getbinary(vb+1, sizeof(uby8), 1, fin2) != 1 ||
770 getbinary(vb+2, sizeof(uby8), 1, fin3) != 1)
771 return(-1);
772 }
773 setcolor(col, (vb[rord[RED]]+.5)/256.,
774 (vb[rord[GRN]]+.5)/256., (vb[rord[BLU]]+.5)/256.);
775 return(0);
776 }
777
778
779 static int
780 getcword( /* get a 16-bit color value from stream(s) */
781 COLOR col
782 )
783 {
784 uint16 vw[3];
785
786 if (fin2 == NULL) {
787 if (getbinary(vw, sizeof(uint16), 3, fin) != 3)
788 return(-1);
789 } else {
790 if (getbinary(vw, sizeof(uint16), 1, fin) != 1 ||
791 getbinary(vw+1, sizeof(uint16), 1, fin2) != 1 ||
792 getbinary(vw+2, sizeof(uint16), 1, fin3) != 1)
793 return(-1);
794 }
795 if (swapbytes)
796 swap16((char *)vw, 3);
797 setcolor(col, (vw[rord[RED]]+.5)/65536.,
798 (vw[rord[GRN]]+.5)/65536., (vw[rord[BLU]]+.5)/65536.);
799 return(0);
800 }
801
802
803 static int
804 getbascii( /* get an ascii brightness value from fin */
805 COLOR col
806 )
807 {
808 double vd;
809
810 if (fscanf(fin, "%lf", &vd) != 1)
811 return(-1);
812 setcolor(col, vd, vd, vd);
813 return(0);
814 }
815
816
817 static int
818 getbdouble( /* get a double brightness value from fin */
819 COLOR col
820 )
821 {
822 double vd;
823
824 if (getbinary(&vd, sizeof(double), 1, fin) != 1)
825 return(-1);
826 if (swapbytes)
827 swap64((char *)&vd, 1);
828 setcolor(col, vd, vd, vd);
829 return(0);
830 }
831
832
833 static int
834 getbfloat( /* get a float brightness value from fin */
835 COLOR col
836 )
837 {
838 float vf;
839
840 if (getbinary(&vf, sizeof(float), 1, fin) != 1)
841 return(-1);
842 if (swapbytes)
843 swap32((char *)&vf, 1);
844 setcolor(col, vf, vf, vf);
845 return(0);
846 }
847
848
849 static int
850 getbint( /* get an int brightness value from fin */
851 COLOR col
852 )
853 {
854 int vi;
855 double d;
856
857 if (fscanf(fin, "%d", &vi) != 1)
858 return(-1);
859 d = (vi+.5)/256.;
860 setcolor(col, d, d, d);
861 return(0);
862 }
863
864
865 static int
866 getbbyte( /* get a byte brightness value from fin */
867 COLOR col
868 )
869 {
870 uby8 vb;
871 double d;
872
873 if (getbinary(&vb, sizeof(uby8), 1, fin) != 1)
874 return(-1);
875 d = (vb+.5)/256.;
876 setcolor(col, d, d, d);
877 return(0);
878 }
879
880
881 static int
882 getbword( /* get a 16-bit brightness value from fin */
883 COLOR col
884 )
885 {
886 uint16 vw;
887 double d;
888
889 if (getbinary(&vw, sizeof(uint16), 1, fin) != 1)
890 return(-1);
891 if (swapbytes)
892 swap16((char *)&vw, 1);
893 d = (vw+.5)/65536.;
894 setcolor(col, d, d, d);
895 return(0);
896 }
897
898
899 static int
900 putcascii( /* put an ascii color to stdout */
901 COLOR col
902 )
903 {
904 fprintf(stdout, "%15.3e %15.3e %15.3e\n",
905 colval(col,ord[0]),
906 colval(col,ord[1]),
907 colval(col,ord[2]));
908
909 return(ferror(stdout) ? -1 : 0);
910 }
911
912
913 static int
914 putcfloat( /* put a float color to stdout */
915 COLOR col
916 )
917 {
918 float vf[3];
919
920 vf[0] = colval(col,ord[0]);
921 vf[1] = colval(col,ord[1]);
922 vf[2] = colval(col,ord[2]);
923 if (swapbytes)
924 swap32((char *)vf, 3);
925 putbinary(vf, sizeof(float), 3, stdout);
926
927 return(ferror(stdout) ? -1 : 0);
928 }
929
930
931 static int
932 putcdouble( /* put a double color to stdout */
933 COLOR col
934 )
935 {
936 double vd[3];
937
938 vd[0] = colval(col,ord[0]);
939 vd[1] = colval(col,ord[1]);
940 vd[2] = colval(col,ord[2]);
941 if (swapbytes)
942 swap64((char *)vd, 3);
943 putbinary(vd, sizeof(double), 3, stdout);
944
945 return(ferror(stdout) ? -1 : 0);
946 }
947
948
949 static int
950 putcint( /* put an int color to stdout */
951 COLOR col
952 )
953 {
954 fprintf(stdout, "%d %d %d\n",
955 (int)(colval(col,ord[0])*256.),
956 (int)(colval(col,ord[1])*256.),
957 (int)(colval(col,ord[2])*256.));
958
959 return(ferror(stdout) ? -1 : 0);
960 }
961
962
963 static int
964 putcbyte( /* put a byte color to stdout */
965 COLOR col
966 )
967 {
968 long i;
969 uby8 vb[3];
970
971 i = colval(col,ord[0])*256.;
972 vb[0] = min(i,255);
973 i = colval(col,ord[1])*256.;
974 vb[1] = min(i,255);
975 i = colval(col,ord[2])*256.;
976 vb[2] = min(i,255);
977 putbinary(vb, sizeof(uby8), 3, stdout);
978
979 return(ferror(stdout) ? -1 : 0);
980 }
981
982
983 static int
984 putcword( /* put a 16-bit color to stdout */
985 COLOR col
986 )
987 {
988 long i;
989 uint16 vw[3];
990
991 i = colval(col,ord[0])*65536.;
992 vw[0] = min(i,65535);
993 i = colval(col,ord[1])*65536.;
994 vw[1] = min(i,65535);
995 i = colval(col,ord[2])*65536.;
996 vw[2] = min(i,65535);
997 if (swapbytes)
998 swap16((char *)vw, 3);
999 putbinary(vw, sizeof(uint16), 3, stdout);
1000
1001 return(ferror(stdout) ? -1 : 0);
1002 }
1003
1004
1005 static int
1006 putbascii( /* put an ascii brightness to stdout */
1007 COLOR col
1008 )
1009 {
1010 fprintf(stdout, "%15.3e\n", (*mybright)(col));
1011
1012 return(ferror(stdout) ? -1 : 0);
1013 }
1014
1015
1016 static int
1017 putbfloat( /* put a float brightness to stdout */
1018 COLOR col
1019 )
1020 {
1021 float vf;
1022
1023 vf = (*mybright)(col);
1024 if (swapbytes)
1025 swap32((char *)&vf, 1);
1026 putbinary(&vf, sizeof(float), 1, stdout);
1027
1028 return(ferror(stdout) ? -1 : 0);
1029 }
1030
1031
1032 static int
1033 putbdouble( /* put a double brightness to stdout */
1034 COLOR col
1035 )
1036 {
1037 double vd;
1038
1039 vd = (*mybright)(col);
1040 if (swapbytes)
1041 swap64((char *)&vd, 1);
1042 putbinary(&vd, sizeof(double), 1, stdout);
1043
1044 return(ferror(stdout) ? -1 : 0);
1045 }
1046
1047
1048 static int
1049 putbint( /* put an int brightness to stdout */
1050 COLOR col
1051 )
1052 {
1053 fprintf(stdout, "%d\n", (int)((*mybright)(col)*256.));
1054
1055 return(ferror(stdout) ? -1 : 0);
1056 }
1057
1058
1059 static int
1060 putbbyte( /* put a byte brightness to stdout */
1061 COLOR col
1062 )
1063 {
1064 int i;
1065 uby8 vb;
1066
1067 i = (*mybright)(col)*256.;
1068 vb = min(i,255);
1069 putbinary(&vb, sizeof(uby8), 1, stdout);
1070
1071 return(ferror(stdout) ? -1 : 0);
1072 }
1073
1074
1075 static int
1076 putbword( /* put a 16-bit brightness to stdout */
1077 COLOR col
1078 )
1079 {
1080 long i;
1081 uint16 vw;
1082
1083 i = (*mybright)(col)*65536.;
1084 vw = min(i,65535);
1085 if (swapbytes)
1086 swap16((char *)&vw, 1);
1087 putbinary(&vw, sizeof(uint16), 1, stdout);
1088
1089 return(ferror(stdout) ? -1 : 0);
1090 }
1091
1092
1093 static int
1094 putpascii( /* put an ascii primary to stdout */
1095 COLOR col
1096 )
1097 {
1098 fprintf(stdout, "%15.3e\n", colval(col,putprim));
1099
1100 return(ferror(stdout) ? -1 : 0);
1101 }
1102
1103
1104 static int
1105 putpfloat( /* put a float primary to stdout */
1106 COLOR col
1107 )
1108 {
1109 float vf;
1110
1111 vf = colval(col,putprim);
1112 if (swapbytes)
1113 swap32((char *)&vf, 1);
1114 putbinary(&vf, sizeof(float), 1, stdout);
1115
1116 return(ferror(stdout) ? -1 : 0);
1117 }
1118
1119
1120 static int
1121 putpdouble( /* put a double primary to stdout */
1122 COLOR col
1123 )
1124 {
1125 double vd;
1126
1127 vd = colval(col,putprim);
1128 if (swapbytes)
1129 swap64((char *)&vd, 1);
1130 putbinary(&vd, sizeof(double), 1, stdout);
1131
1132 return(ferror(stdout) ? -1 : 0);
1133 }
1134
1135
1136 static int
1137 putpint( /* put an int primary to stdout */
1138 COLOR col
1139 )
1140 {
1141 fprintf(stdout, "%d\n", (int)(colval(col,putprim)*256.));
1142
1143 return(ferror(stdout) ? -1 : 0);
1144 }
1145
1146
1147 static int
1148 putpbyte( /* put a byte primary to stdout */
1149 COLOR col
1150 )
1151 {
1152 long i;
1153 uby8 vb;
1154
1155 i = colval(col,putprim)*256.;
1156 vb = min(i,255);
1157 putbinary(&vb, sizeof(uby8), 1, stdout);
1158
1159 return(ferror(stdout) ? -1 : 0);
1160 }
1161
1162
1163 static int
1164 putpword( /* put a 16-bit primary to stdout */
1165 COLOR col
1166 )
1167 {
1168 long i;
1169 uint16 vw;
1170
1171 i = colval(col,putprim)*65536.;
1172 vw = min(i,65535);
1173 if (swapbytes)
1174 swap16((char *)&vw, 1);
1175 putbinary(&vw, sizeof(uint16), 1, stdout);
1176
1177 return(ferror(stdout) ? -1 : 0);
1178 }
1179
1180
1181 static void
1182 set_io(void) /* set put and get functions */
1183 {
1184 switch (format) {
1185 case 'a': /* ascii */
1186 if (putprim == BRIGHT) {
1187 getval = getbascii;
1188 putval = putbascii;
1189 } else if (putprim != ALL) {
1190 getval = getbascii;
1191 putval = putpascii;
1192 } else {
1193 getval = getcascii;
1194 putval = putcascii;
1195 if (reverse && !interleave) {
1196 fprintf(stderr,
1197 "%s: ASCII input files must be interleaved\n",
1198 progname);
1199 quit(1);
1200 }
1201 }
1202 return;
1203 case 'f': /* binary float */
1204 if (putprim == BRIGHT) {
1205 getval = getbfloat;
1206 putval = putbfloat;
1207 } else if (putprim != ALL) {
1208 getval = getbfloat;
1209 putval = putpfloat;
1210 } else {
1211 getval = getcfloat;
1212 putval = putcfloat;
1213 if (reverse && !interleave) {
1214 if (fin2 == NULL)
1215 goto namerr;
1216 if (fseek(fin2,
1217 (long)sizeof(float)*picres.xr*picres.yr, SEEK_CUR))
1218 goto seekerr;
1219 if (fseek(fin3,
1220 (long)sizeof(float)*2*picres.xr*picres.yr, SEEK_CUR))
1221 goto seekerr;
1222 }
1223 }
1224 return;
1225 case 'd': /* binary double */
1226 if (putprim == BRIGHT) {
1227 getval = getbdouble;
1228 putval = putbdouble;
1229 } else if (putprim != ALL) {
1230 getval = getbdouble;
1231 putval = putpdouble;
1232 } else {
1233 getval = getcdouble;
1234 putval = putcdouble;
1235 if (reverse && !interleave) {
1236 if (fin2 == NULL)
1237 goto namerr;
1238 if (fseek(fin2,
1239 (long)sizeof(double)*picres.xr*picres.yr, SEEK_CUR))
1240 goto seekerr;
1241 if (fseek(fin3,
1242 (long)sizeof(double)*2*picres.xr*picres.yr, SEEK_CUR))
1243 goto seekerr;
1244 }
1245 }
1246 return;
1247 case 'i': /* integer */
1248 if (putprim == BRIGHT) {
1249 getval = getbint;
1250 putval = putbint;
1251 } else if (putprim != ALL) {
1252 getval = getbint;
1253 putval = putpint;
1254 } else {
1255 getval = getcint;
1256 putval = putcint;
1257 if (reverse && !interleave) {
1258 fprintf(stderr,
1259 "%s: integer input files must be interleaved\n",
1260 progname);
1261 quit(1);
1262 }
1263 }
1264 return;
1265 case 'b': /* byte */
1266 if (putprim == BRIGHT) {
1267 getval = getbbyte;
1268 putval = putbbyte;
1269 } else if (putprim != ALL) {
1270 getval = getbbyte;
1271 putval = putpbyte;
1272 } else {
1273 getval = getcbyte;
1274 putval = putcbyte;
1275 if (reverse && !interleave) {
1276 if (fin2 == NULL)
1277 goto namerr;
1278 if (fseek(fin2,
1279 (long)sizeof(uby8)*picres.xr*picres.yr, SEEK_CUR))
1280 goto seekerr;
1281 if (fseek(fin3,
1282 (long)sizeof(uby8)*2*picres.xr*picres.yr, SEEK_CUR))
1283 goto seekerr;
1284 }
1285 }
1286 return;
1287 case 'w': /* 16-bit */
1288 if (putprim == BRIGHT) {
1289 getval = getbword;
1290 putval = putbword;
1291 } else if (putprim != ALL) {
1292 getval = getbword;
1293 putval = putpword;
1294 } else {
1295 getval = getcword;
1296 putval = putcword;
1297 if (reverse && !interleave) {
1298 if (fin2 == NULL)
1299 goto namerr;
1300 if (fseek(fin2,
1301 (long)sizeof(uint16)*picres.xr*picres.yr, SEEK_CUR))
1302 goto seekerr;
1303 if (fseek(fin3,
1304 (long)sizeof(uint16)*2*picres.xr*picres.yr, SEEK_CUR))
1305 goto seekerr;
1306 }
1307 }
1308 return;
1309 }
1310 /* badopt: */ /* label not used */
1311 fprintf(stderr, "%s: botched file type\n", progname);
1312 quit(1);
1313 namerr:
1314 fprintf(stderr, "%s: non-interleaved file(s) must be named\n",
1315 progname);
1316 quit(1);
1317 seekerr:
1318 fprintf(stderr, "%s: cannot seek on interleaved input file\n",
1319 progname);
1320 quit(1);
1321 }