ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/ra_t8.c
Revision: 2.9
Committed: Fri Nov 10 17:04:52 1995 UTC (28 years, 5 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 2.8: +0 -1 lines
Log Message:
removed memcpy() declaration

File Contents

# Content
1 /* Copyright (c) 1992 Regents of the University of California */
2
3 #ifndef lint
4 static char SCCSid[] = "$SunId$ LBL";
5 #endif
6
7 /*
8 * ra_t8.c - program to convert between RADIANCE and
9 * Targa 8-bit color-mapped images.
10 *
11 * 8/22/88 Adapted from ra_pr.c
12 */
13
14 #include <stdio.h>
15
16 #include "color.h"
17
18 #include "resolu.h"
19
20 #include "targa.h"
21
22 #ifdef MSDOS
23 #include <fcntl.h>
24 #endif
25
26 #include <math.h>
27
28 #ifndef BSD
29 #define bcopy(s,d,n) (void)memcpy(d,s,n)
30 #endif
31
32 #define goodpic(h) (my_imType(h) && my_mapType(h))
33 #define my_imType(h) (((h)->dataType==IM_CMAP || (h)->dataType==IM_CCMAP) \
34 && (h)->dataBits==8 && (h)->imType==0)
35 #define my_mapType(h) ((h)->mapType==CM_HASMAP && \
36 ((h)->CMapBits==24 || (h)->CMapBits==32))
37
38 #define taralloc(h) (BYTE *)emalloc((h)->x*(h)->y)
39
40 BYTE clrtab[256][3];
41
42 extern int samplefac;
43
44 extern char *ecalloc(), *emalloc();
45
46 extern long ftell();
47
48 double gamv = 2.2; /* gamv correction */
49
50 int bradj = 0; /* brightness adjustment */
51
52 char *progname;
53
54 char errmsg[128];
55
56 COLR *inl;
57
58 BYTE *tarData;
59
60 int xmax, ymax;
61
62
63 main(argc, argv)
64 int argc;
65 char *argv[];
66 {
67 struct hdStruct head;
68 int dither = 1;
69 int reverse = 0;
70 int ncolors = 256;
71 int greyscale = 0;
72 int i;
73 #ifdef MSDOS
74 extern int _fmode;
75 _fmode = O_BINARY;
76 setmode(fileno(stdin), O_BINARY);
77 setmode(fileno(stdout), O_BINARY);
78 #endif
79 progname = argv[0];
80 samplefac = 0;
81
82 for (i = 1; i < argc; i++)
83 if (argv[i][0] == '-')
84 switch (argv[i][1]) {
85 case 'd':
86 dither = !dither;
87 break;
88 case 'g':
89 gamv = atof(argv[++i]);
90 break;
91 case 'r':
92 reverse = !reverse;
93 break;
94 case 'b':
95 greyscale = 1;
96 break;
97 case 'e':
98 if (argv[i+1][0] != '+' && argv[i+1][0] != '-')
99 goto userr;
100 bradj = atoi(argv[++i]);
101 break;
102 case 'c':
103 ncolors = atoi(argv[++i]);
104 break;
105 case 'n':
106 samplefac = atoi(argv[++i]);
107 break;
108 default:
109 goto userr;
110 }
111 else
112 break;
113
114 if (i < argc-2)
115 goto userr;
116 if (i <= argc-1 && freopen(argv[i], "r", stdin) == NULL) {
117 sprintf(errmsg, "cannot open input \"%s\"", argv[i]);
118 quiterr(errmsg);
119 }
120 if (i == argc-2 && freopen(argv[i+1], "w", stdout) == NULL) {
121 sprintf(errmsg, "cannot open output \"%s\"", argv[i+1]);
122 quiterr(errmsg);
123 }
124 if (reverse) {
125 /* get header */
126 if (getthead(&head, NULL, stdin) < 0)
127 quiterr("bad targa file");
128 if (!goodpic(&head))
129 quiterr("incompatible format");
130 xmax = head.x;
131 ymax = head.y;
132 /* put header */
133 newheader("RADIANCE", stdout);
134 printargs(i, argv, stdout);
135 fputformat(COLRFMT, stdout);
136 putchar('\n');
137 fprtresolu(xmax, ymax, stdout);
138 /* convert file */
139 tg2ra(&head);
140 } else {
141 if (getrhead(&head, stdin) < 0)
142 quiterr("bad Radiance input");
143 /* write header */
144 putthead(&head, NULL, stdout);
145 /* convert file */
146 if (greyscale)
147 getgrey(ncolors);
148 else
149 getmapped(ncolors, dither);
150 /* write data */
151 writetarga(&head, tarData, stdout);
152 }
153 quiterr(NULL);
154 userr:
155 fprintf(stderr,
156 "Usage: %s [-d][-n samp][-c ncolors][-b][-g gamv][-e +/-stops] input [output]\n",
157 progname);
158 fprintf(stderr, " Or: %s -r [-g gamv][-e +/-stops] [input [output]]\n",
159 progname);
160 exit(1);
161 }
162
163
164 int
165 getint2(fp) /* get a 2-byte positive integer */
166 register FILE *fp;
167 {
168 register int b1, b2;
169
170 if ((b1 = getc(fp)) == EOF || (b2 = getc(fp)) == EOF)
171 quiterr("read error");
172
173 return(b1 | b2<<8);
174 }
175
176
177 putint2(i, fp) /* put a 2-byte positive integer */
178 register int i;
179 register FILE *fp;
180 {
181 putc(i&0xff, fp);
182 putc(i>>8&0xff, fp);
183 }
184
185
186 quiterr(err) /* print message and exit */
187 char *err;
188 {
189 if (err != NULL) {
190 fprintf(stderr, "%s: %s\n", progname, err);
191 exit(1);
192 }
193 exit(0);
194 }
195
196
197 eputs(s)
198 char *s;
199 {
200 fputs(s, stderr);
201 }
202
203
204 quit(code)
205 int code;
206 {
207 exit(code);
208 }
209
210
211 getthead(hp, ip, fp) /* read header from input */
212 struct hdStruct *hp;
213 char *ip;
214 register FILE *fp;
215 {
216 int nidbytes;
217
218 if ((nidbytes = getc(fp)) == EOF)
219 return(-1);
220 hp->mapType = getc(fp);
221 hp->dataType = getc(fp);
222 hp->mapOrig = getint2(fp);
223 hp->mapLength = getint2(fp);
224 hp->CMapBits = getc(fp);
225 hp->XOffset = getint2(fp);
226 hp->YOffset = getint2(fp);
227 hp->x = getint2(fp);
228 hp->y = getint2(fp);
229 hp->dataBits = getc(fp);
230 hp->imType = getc(fp);
231
232 if (ip != NULL)
233 if (nidbytes)
234 fread((char *)ip, nidbytes, 1, fp);
235 else
236 *ip = '\0';
237 else if (nidbytes)
238 fseek(fp, (long)nidbytes, 1);
239
240 return(feof(fp) || ferror(fp) ? -1 : 0);
241 }
242
243
244 putthead(hp, ip, fp) /* write header to output */
245 struct hdStruct *hp;
246 char *ip;
247 register FILE *fp;
248 {
249 if (ip != NULL)
250 putc(strlen(ip), fp);
251 else
252 putc(0, fp);
253 putc(hp->mapType, fp);
254 putc(hp->dataType, fp);
255 putint2(hp->mapOrig, fp);
256 putint2(hp->mapLength, fp);
257 putc(hp->CMapBits, fp);
258 putint2(hp->XOffset, fp);
259 putint2(hp->YOffset, fp);
260 putint2(hp->x, fp);
261 putint2(hp->y, fp);
262 putc(hp->dataBits, fp);
263 putc(hp->imType, fp);
264
265 if (ip != NULL)
266 fputs(ip, fp);
267
268 return(ferror(fp) ? -1 : 0);
269 }
270
271
272 getrhead(h, fp) /* load RADIANCE input file header */
273 register struct hdStruct *h;
274 FILE *fp;
275 {
276 /* get header info. */
277 if (checkheader(fp, COLRFMT, NULL) < 0 ||
278 fgetresolu(&xmax, &ymax, fp) < 0)
279 return(-1);
280 /* assign header */
281 h->textSize = 0;
282 h->mapType = CM_HASMAP;
283 h->dataType = IM_CMAP;
284 h->mapOrig = 0;
285 h->mapLength = 256;
286 h->CMapBits = 24;
287 h->XOffset = 0;
288 h->YOffset = 0;
289 h->x = xmax;
290 h->y = ymax;
291 h->dataBits = 8;
292 h->imType = 0;
293 /* allocate scanline */
294 inl = (COLR *)emalloc(xmax*sizeof(COLR));
295 /* allocate targa data */
296 tarData = taralloc(h);
297
298 return(0);
299 }
300
301
302 tg2ra(hp) /* targa file to RADIANCE file */
303 struct hdStruct *hp;
304 {
305 union {
306 BYTE c3[256][3];
307 BYTE c4[256][4];
308 } map;
309 COLR ctab[256];
310 COLR *scanline;
311 register int i, j;
312
313 /* get color table */
314 if ((hp->CMapBits==24 ? fread((char *)(map.c3+hp->mapOrig),
315 3*hp->mapLength,1,stdin) :
316 fread((char *)(map.c4+hp->mapOrig),
317 4*hp->mapLength,1,stdin)) != 1)
318 quiterr("error reading color table");
319 /* convert table */
320 for (i = hp->mapOrig; i < hp->mapOrig+hp->mapLength; i++)
321 if (hp->CMapBits == 24)
322 setcolr(ctab[i],
323 pow((map.c3[i][2]+.5)/256.,gamv),
324 pow((map.c3[i][1]+.5)/256.,gamv),
325 pow((map.c3[i][0]+.5)/256.,gamv));
326 else
327 setcolr(ctab[i],
328 pow((map.c4[i][3]+.5)/256.,gamv),
329 pow((map.c4[i][2]+.5)/256.,gamv),
330 pow((map.c4[i][1]+.5)/256.,gamv));
331 if (bradj)
332 shiftcolrs(ctab, 256, bradj);
333 /* allocate targa data */
334 tarData = taralloc(hp);
335 /* get data */
336 readtarga(hp, tarData, stdin);
337 /* allocate input scanline */
338 scanline = (COLR *)emalloc(xmax*sizeof(COLR));
339 /* convert file */
340 for (i = ymax-1; i >= 0; i--) {
341 for (j = 0; j < xmax; j++)
342 copycolr(scanline[j], ctab[tarData[i*xmax+j]]);
343 if (fwritecolrs(scanline, xmax, stdout) < 0)
344 quiterr("error writing RADIANCE file");
345 }
346 free((char *)scanline);
347 free((char *)tarData);
348 }
349
350
351 getmapped(nc, dith) /* read in and quantize image */
352 int nc; /* number of colors to use */
353 int dith; /* use dithering? */
354 {
355 long fpos;
356 register int y;
357
358 setcolrgam(gamv);
359 fpos = ftell(stdin);
360 if ((samplefac ? neu_init(xmax*ymax) : new_histo(xmax*ymax)) == -1)
361 quiterr("cannot initialized histogram");
362 for (y = ymax-1; y >= 0; y--) {
363 if (freadcolrs(inl, xmax, stdin) < 0)
364 quiterr("error reading Radiance input");
365 if (bradj)
366 shiftcolrs(inl, xmax, bradj);
367 colrs_gambs(inl, xmax);
368 if (samplefac)
369 neu_colrs(inl, xmax);
370 else
371 cnt_colrs(inl, xmax);
372 }
373 if (fseek(stdin, fpos, 0) == EOF)
374 quiterr("Radiance input must be from a file");
375 if (samplefac) /* map colors */
376 neu_clrtab(nc);
377 else
378 new_clrtab(nc);
379 for (y = ymax-1; y >= 0; y--) {
380 if (freadcolrs(inl, xmax, stdin) < 0)
381 quiterr("error reading Radiance input");
382 if (bradj)
383 shiftcolrs(inl, xmax, bradj);
384 colrs_gambs(inl, xmax);
385 if (samplefac)
386 if (dith)
387 neu_dith_colrs(tarData+y*xmax, inl, xmax);
388 else
389 neu_map_colrs(tarData+y*xmax, inl, xmax);
390 else
391 if (dith)
392 dith_colrs(tarData+y*xmax, inl, xmax);
393 else
394 map_colrs(tarData+y*xmax, inl, xmax);
395 }
396 }
397
398
399 getgrey(nc) /* read in and convert to greyscale image */
400 int nc; /* number of colors to use */
401 {
402 int y;
403 register BYTE *dp;
404 register int x;
405
406 setcolrgam(gamv);
407 dp = tarData+xmax*ymax;;
408 for (y = ymax-1; y >= 0; y--) {
409 if (freadcolrs(inl, xmax, stdin) < 0)
410 quiterr("error reading Radiance input");
411 if (bradj)
412 shiftcolrs(inl, xmax, bradj);
413 x = xmax;
414 while (x--)
415 inl[x][GRN] = normbright(inl[x]);
416 colrs_gambs(inl, xmax);
417 x = xmax;
418 if (nc < 256)
419 while (x--)
420 *--dp = ((long)inl[x][GRN]*nc+nc/2)>>8;
421 else
422 while (x--)
423 *--dp = inl[x][GRN];
424 }
425 for (x = 0; x < nc; x++)
426 clrtab[x][RED] = clrtab[x][GRN] =
427 clrtab[x][BLU] = ((long)x*256+128)/nc;
428 }
429
430
431 writetarga(h, d, fp) /* write out targa data */
432 struct hdStruct *h;
433 BYTE *d;
434 FILE *fp;
435 {
436 register int i, j;
437
438 for (i = 0; i < h->mapLength; i++) /* write color map */
439 for (j = 2; j >= 0; j--)
440 putc(clrtab[i][j], fp);
441 if (h->dataType == IM_CMAP) { /* uncompressed */
442 if (fwrite((char *)d,h->x*sizeof(BYTE),h->y,fp) != h->y)
443 quiterr("error writing targa file");
444 return;
445 }
446 quiterr("unsupported output type");
447 }
448
449
450 readtarga(h, data, fp) /* read in targa data */
451 struct hdStruct *h;
452 BYTE *data;
453 FILE *fp;
454 {
455 register int cnt, c;
456 register BYTE *dp;
457
458 if (h->dataType == IM_CMAP) { /* uncompressed */
459 if (fread((char *)data,h->x*sizeof(BYTE),h->y,fp) != h->y)
460 goto readerr;
461 return;
462 }
463 for (dp = data; dp < data+h->x*h->y; ) {
464 if ((c = getc(fp)) == EOF)
465 goto readerr;
466 cnt = (c & 0x7f) + 1;
467 if (c & 0x80) { /* repeated pixel */
468 if ((c = getc(fp)) == EOF)
469 goto readerr;
470 while (cnt--)
471 *dp++ = c;
472 } else /* non-repeating pixels */
473 while (cnt--) {
474 if ((c = getc(fp)) == EOF)
475 goto readerr;
476 *dp++ = c;
477 }
478 }
479 return;
480 readerr:
481 quiterr("error reading targa file");
482 }