ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/ra_pict.c
Revision: 2.13
Committed: Sat Mar 5 17:30:38 2022 UTC (2 years, 1 month ago) by greg
Content type: text/plain
Branch: MAIN
CVS Tags: rad5R4, HEAD
Changes since 2.12: +2 -3 lines
Log Message:
fix: removed stray tempbuffer() declaration

File Contents

# Content
1 #ifndef lint
2 static const char RCSid[] = "$Id: ra_pict.c,v 2.12 2019/07/19 17:37:56 greg Exp $";
3 #endif
4 /* Convert an Radiance image to APPLE pict format.
5 *
6 * Orginally Iris to PICT by Paul Haeberli - 1990
7 * Hacked into Rad to PICT by Russell Street 1990
8 *
9 * History:
10 * V 1 -- Does basic conversion
11 * V 1.1 (2/11/91) -- Added options for Gamma
12 * -- verbose option
13 * -- man page
14 * -- better about allocating buffers
15 * V 1.2 (19/11/91) -- Revised to handle opening "The Radiance Way"
16 * -- Added exposure level adjustment
17 */
18
19 #include <math.h>
20
21 #include "rtio.h"
22 #include "platform.h"
23 #include "pict.h"
24 #include "color.h"
25 #include "resolu.h"
26
27 int outbytes; /* This had better be 32 bits! */
28 char *progname;
29 int verbose = 0;
30 float gamcor = 2.0;
31 int bradj = 0;
32
33 static void putrect(int xorg, int yorg, int xsize, int ysize);
34 static void putfprect(int xorg, int yorg, int xsize, int ysize);
35 static void putalong(long l);
36 static void putashort(short s);
37 static void putbyte(int b);
38 static void putbytes(unsigned char *buf, int n );
39 static void putpict(int xsize, int ysize);
40 static void getrow(FILE *in, char *cbuf, int xsize);
41 static int packbits(unsigned char *ibits, unsigned char *pbits, int nbits);
42 static void usage(void);
43
44
45 /* First some utility routines */
46 static void
47 putrect(
48 int xorg,
49 int yorg,
50 int xsize,
51 int ysize
52 )
53 {
54 putashort(yorg);
55 putashort(xorg);
56 putashort(ysize);
57 putashort(xsize);
58 }
59
60 static void
61 putfprect(
62 int xorg,
63 int yorg,
64 int xsize,
65 int ysize
66 )
67 {
68 putalong(yorg<<16);
69 putalong(xorg<<16);
70 putalong(ysize<<16);
71 putalong(xsize<<16);
72 }
73
74 static void
75 putalong(
76 long l
77 )
78 {
79 putbyte((l>>24)&0xff);
80 putbyte((l>>16)&0xff);
81 putbyte((l>>8)&0xff);
82 putbyte((l>>0)&0xff);
83 }
84
85 static void
86 putashort(
87 short s
88 )
89 {
90 putbyte((s>>8)&0xff);
91 putbyte((s>>0)&0xff);
92 }
93
94 static void
95 putbyte(
96 int b
97 )
98 {
99 if (putc(b,stdout) == EOF && ferror(stdout)) {
100 fprintf(stderr,"%s: error on write\n", progname);
101 exit(1);
102 }
103 outbytes++;
104 }
105
106 static void
107 putbytes(
108 unsigned char *buf,
109 int n
110 )
111 {
112 if(!fwrite(buf,n,1,stdout)) {
113 fprintf(stderr,"%s: error on write\n", progname);
114 exit(1);
115 }
116 outbytes+=n;
117 }
118
119 int
120 main(
121 int argc,
122 char **argv
123 )
124 {
125 int xsize, ysize;
126 int i, picsize;
127 int ssizepos, lsizepos;
128 SET_DEFAULT_BINARY();
129 SET_FILE_BINARY(stdin);
130 SET_FILE_BINARY(stdout);
131 progname = argv[0];
132
133 for (i = 1; i < argc ; i++)
134 if (argv[i][0] == '-')
135 switch (argv[i][1]) {
136 case 'g': gamcor = atof(argv[++i]);
137 break;
138
139 case 'e': if (argv[i+1][0] != '+' && argv[i+1][0] != '-')
140 usage();
141 else
142 bradj = atoi(argv[++i]);
143 break;
144
145 case 'v': ;
146 verbose = 1;
147 break;
148
149 case 'r': fprintf(stderr, "Sorry. Get a Macintosh :-)\n");
150 exit(1);
151
152 case '-': i++;
153 goto outofparse;
154 break; /* NOTREACHED */
155
156 default:
157 usage();
158 break;
159 }
160 else
161 break;
162
163 outofparse:
164
165 if (i < argc - 2)
166 usage();
167
168 if (i <= argc - 1 && freopen(argv[i], "r", stdin) == NULL) {
169 fprintf(stderr, "%s: can not open input \"%s\"\n",
170 progname, argv[i]);
171 exit(1);
172 }
173
174 if (i <= argc - 2 && freopen(argv[i+1], "w", stdout) == NULL) {
175 fprintf(stderr, "%s: can not open input \"%s\"\n",
176 progname, argv[i+1]);
177 exit(1);
178 }
179
180 #ifdef DEBUG
181 fprintf(stderr, "Input file: %s\n", i <= argc - 1 ? argv[i] : "stdin");
182 fprintf(stderr, "Outut file: %s\n", i <= argc - 2 ? argv[i+1] : "stdout" );
183 fprintf(stderr, "Gamma: %f\n", gamcor);
184 fprintf(stderr, "Brightness adjust: %d\n", bradj);
185 fprintf(stderr, "Verbose: %s\n", verbose ? "on" : "off");
186 #endif
187
188
189 /* OK. Now we read the size of the Radiance picture */
190 if (checkheader(stdin, COLRFMT, NULL) < 0 ||
191 fgetresolu(&xsize, &ysize, stdin) < 0 /* != (YMAJOR|YDECR) */ ) {
192 fprintf(stderr, "%s: not a radiance picture\n", progname);
193 exit(1);
194 }
195
196 /* Set the gamma correction */
197
198 setcolrgam(gamcor);
199
200 for(i=0; i<HEADER_SIZE; i++)
201 putbyte(0);
202
203 ssizepos = outbytes;
204 putashort(0); /* low 16 bits of file size less HEADER_SIZE */
205 putrect(0,0,xsize,ysize); /* bounding box of picture */
206 putashort(PICT_picVersion);
207 putashort(0x02ff); /* version 2 pict */
208 putashort(PICT_reservedHeader); /* reserved header opcode */
209
210 lsizepos = outbytes;
211 putalong(0); /* full size of the file */
212 putfprect(0,0,xsize,ysize); /* fixed point bounding box of picture */
213 putalong(0); /* reserved */
214
215 putashort(PICT_clipRgn); /* the clip region */
216 putashort(10);
217 putrect(0,0,xsize,ysize);
218
219 if (verbose)
220 fprintf(stderr, "%s: The picture is %d by %d, with a gamma of %f\n",
221 progname, xsize, ysize, gamcor);
222
223
224 putpict(xsize, ysize); /* Here is where all the work is done */
225
226 putashort(PICT_EndOfPicture); /* end of pict */
227
228 picsize = outbytes-HEADER_SIZE;
229 fseek(stdout,ssizepos,0);
230 putashort(picsize&0xffff);
231 fseek(stdout,lsizepos,0);
232 putalong(picsize);
233
234 fclose(stdout);
235 fclose(stdin);
236
237 exit(0);
238 return 0; /* lint fodder */
239 }
240
241 static void
242 putpict(
243 int xsize,
244 int ysize
245 )
246 {
247 int y;
248 int nbytes, rowbytes;
249 char *cbuf, *pbuf;
250
251 cbuf = (char *)malloc(4 * xsize);
252
253 if (cbuf == NULL) {
254 fprintf(stderr, "%s: not enough memory\n", progname);
255 exit(1);
256 }
257
258 pbuf = (char *)malloc(4 * xsize);
259
260 if (pbuf == NULL) {
261 fprintf(stderr, "%s: not enough memory\n", progname);
262 exit(1);
263 }
264
265 putashort(PICT_Pack32BitsRect); /* 32 bit rgb */
266 rowbytes = 4*xsize;
267 putalong(0x000000ff); /* base address */
268
269
270 if(rowbytes&1)
271 rowbytes++;
272 putashort(rowbytes|0x8000); /* rowbytes */
273 putrect(0,0,xsize,ysize); /* bounds */
274 putashort(0); /* version */
275
276 putashort(4); /* packtype */
277 putalong(0); /* packsize */
278 putalong(72<<16); /* hres */
279 putalong(72<<16); /* vres */
280
281 putashort(16); /* pixeltype */
282 putashort(32); /* pixelsize */
283 putashort(3); /* cmpcount */
284
285
286 putashort(8); /* cmpsize */
287 putalong(0); /* planebytes */
288 putalong(0); /* pmtable */
289 putalong(0); /* pmreserved */
290
291
292 putrect(0,0,xsize,ysize); /* scr rect */
293 putrect(0,0,xsize,ysize); /* dest rect */
294
295
296 putashort(0x40); /* transfer mode */
297
298 for(y=0; y<ysize; y++) {
299 getrow(stdin, cbuf, xsize);
300
301 nbytes = packbits(cbuf,pbuf,24*xsize);
302 if(rowbytes>250)
303 putashort(nbytes);
304 else
305 putbyte(nbytes);
306 putbytes(pbuf,nbytes);
307 }
308
309 if(outbytes&1)
310 putbyte(0);
311
312 free(cbuf);
313 free(pbuf);
314 }
315
316 static void
317 getrow(
318 FILE *in,
319 char *cbuf,
320 int xsize
321 )
322 {
323 COLR *scanin = NULL;
324 int x;
325
326 if ((scanin = (COLR *)tempbuffer(xsize*sizeof(COLR))) == NULL) {
327 fprintf(stderr, "%s: not enough memory\n", progname);
328 exit(1);
329 }
330
331 if (freadcolrs(scanin, xsize, in) < 0) {
332 fprintf(stderr, "%s: read error\n", progname);
333 exit(1);
334 }
335
336 if (bradj) /* Adjust exposure level */
337 shiftcolrs(scanin, xsize, bradj);
338
339
340 colrs_gambs(scanin, xsize); /* Gamma correct it */
341
342 for (x = 0; x < xsize; x++) {
343 cbuf[x] = scanin[x][RED];
344 cbuf[xsize + x] = scanin[x][GRN];
345 cbuf[2*xsize + x] = scanin[x][BLU];
346 }
347
348 }
349
350
351 static int
352 packbits(
353 unsigned char *ibits,
354 unsigned char *pbits,
355 int nbits
356 )
357 {
358 unsigned char *sptr;
359 unsigned char *ibitsend;
360 unsigned char *optr = pbits;
361 int nbytes, todo, cc, count;
362
363 nbytes = ((nbits-1)/8)+1;
364 ibitsend = ibits+nbytes;
365 while(ibits<ibitsend) {
366 sptr = ibits;
367 ibits += 2;
368 while((ibits<ibitsend)&&((ibits[-2]!=ibits[-1])||(ibits[-1]!=ibits[0])))
369 ibits++;
370 if(ibits != ibitsend) {
371 ibits -= 2;
372 }
373 count = ibits-sptr;
374 while(count) {
375 todo = count>127 ? 127:count;
376 count -= todo;
377 *optr++ = todo-1;
378 while(todo--)
379 *optr++ = *sptr++;
380 }
381 if(ibits == ibitsend)
382 break;
383 sptr = ibits;
384 cc = *ibits++;
385 while( (ibits<ibitsend) && (*ibits == cc) )
386 ibits++;
387 count = ibits-sptr;
388 while(count) {
389 todo = count>128 ? 128:count;
390 count -= todo;
391 *optr++ = 257-todo;
392 *optr++ = cc;
393 }
394 }
395 return optr-pbits;
396 }
397
398 static void
399 usage(void)
400 {
401 fprintf(stderr, "Usage: %s [-v] [-g gamma] [infile [outfile]]\n",
402 progname);
403 exit(2);
404 }