ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/px/pcond2.c
Revision: 3.8
Committed: Wed Feb 5 16:08:18 1997 UTC (27 years, 9 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 3.7: +34 -1 lines
Log Message:
changed -m option to read in color warp map (old -m now -d)

File Contents

# Content
1 /* Copyright (c) 1997 Regents of the University of California */
2
3 #ifndef lint
4 static char SCCSid[] = "$SunId$ LBL";
5 #endif
6
7 /*
8 * Input and output conditioning routines for pcond.
9 */
10
11 #include "pcond.h"
12 #include "warp3d.h"
13
14
15 RGBPRIMP inprims = stdprims; /* input primaries */
16 COLORMAT inrgb2xyz; /* convert input RGB to XYZ */
17 RGBPRIMP outprims = stdprims; /* output primaries */
18
19 double (*lumf)() = rgblum; /* input luminance function */
20 double inpexp = 1.0; /* input exposure value */
21
22 char *mbcalfile = NULL; /* macbethcal mapping file */
23 char *cwarpfile = NULL; /* color space warping file */
24
25 static struct mbc {
26 COLORMAT cmat;
27 float xa[3][6], ya[3][6];
28 COLOR cmin, cmax;
29 } mbcond; /* macbethcal conditioning struct */
30
31 static WARP3D *cwarp; /* color warping structure */
32
33 static COLOR *scanbuf; /* scanline processing buffer */
34 static int nread; /* number of scanlines processed */
35
36
37 double
38 rgblum(clr, scotopic) /* compute (scotopic) luminance of RGB color */
39 COLOR clr;
40 int scotopic;
41 {
42 if (scotopic) /* approximate */
43 return( WHTSEFFICACY * (colval(clr,RED)*.062 +
44 colval(clr,GRN)*.608 + colval(clr,BLU)*.330) );
45 return( WHTEFFICACY * (colval(clr,RED)*inrgb2xyz[1][0] +
46 colval(clr,GRN)*inrgb2xyz[1][1] +
47 colval(clr,BLU)*inrgb2xyz[1][2]) );
48 }
49
50
51 double
52 cielum(xyz, scotopic) /* compute (scotopic) luminance of CIE color */
53 COLOR xyz;
54 int scotopic;
55 {
56 if (scotopic) /* approximate */
57 return(colval(xyz,CIEY) *
58 (1.33*(1. + (colval(xyz,CIEY)+colval(xyz,CIEZ))/
59 colval(xyz,CIEX)) - 1.68));
60 return(colval(xyz,CIEY));
61 }
62
63
64 COLOR *
65 nextscan() /* read and condition next scanline */
66 {
67 if (nread >= numscans(&inpres)) {
68 if (cwarpfile != NULL)
69 free3dw(cwarp);
70 free((char *)scanbuf);
71 return(scanbuf = NULL);
72 }
73 if (what2do&DO_ACUITY)
74 acuscan(scanbuf, nread);
75 else if (freadscan(scanbuf, scanlen(&inpres), infp) < 0) {
76 fprintf(stderr, "%s: %s: scanline read error\n",
77 progname, infn);
78 exit(1);
79 }
80 if (what2do&DO_VEIL) /* add veiling */
81 addveil(scanbuf, nread);
82 if (what2do&DO_COLOR) /* scotopic color loss */
83 scotscan(scanbuf, scanlen(&inpres));
84 if (what2do&DO_LINEAR) /* map luminances */
85 sfscan(scanbuf, scanlen(&inpres), scalef);
86 else
87 mapscan(scanbuf, scanlen(&inpres));
88 if (mbcalfile != NULL) /* device color correction */
89 mbscan(scanbuf, scanlen(&inpres), &mbcond);
90 else if (cwarpfile != NULL) /* device color space warp */
91 cwscan(scanbuf, scanlen(&inpres), cwarp);
92 else if (lumf == cielum | inprims != outprims)
93 matscan(scanbuf, scanlen(&inpres), mbcond.cmat);
94 nread++;
95 return(scanbuf);
96 }
97
98
99 COLOR *
100 firstscan() /* return first processed scanline */
101 {
102 if (mbcalfile != NULL) /* load macbethcal file */
103 getmbcalfile(mbcalfile, &mbcond);
104 else if (cwarpfile != NULL) {
105 if ((cwarp = load3dw(cwarpfile, NULL)) == NULL)
106 syserror(cwarpfile);
107 } else
108 if (lumf == rgblum)
109 comprgb2rgbmat(mbcond.cmat, inprims, outprims);
110 else
111 compxyz2rgbmat(mbcond.cmat, outprims);
112 if (what2do&DO_ACUITY)
113 initacuity();
114 scanbuf = (COLOR *)malloc(scanlen(&inpres)*sizeof(COLOR));
115 if (scanbuf == NULL)
116 syserror("malloc");
117 nread = 0;
118 return(nextscan());
119 }
120
121
122 sfscan(sl, len, sf) /* apply scalefactor to scanline */
123 register COLOR *sl;
124 int len;
125 double sf;
126 {
127 while (len--) {
128 scalecolor(sl[0], sf);
129 sl++;
130 }
131 }
132
133
134 matscan(sl, len, mat) /* apply color matrix to scaline */
135 register COLOR *sl;
136 int len;
137 COLORMAT mat;
138 {
139 while (len--) {
140 colortrans(sl[0], mat, sl[0]);
141 clipgamut(sl[0], bright(sl[0]), CGAMUT, cblack, cwhite);
142 sl++;
143 }
144 }
145
146
147 mbscan(sl, len, mb) /* apply macbethcal adj. to scaline */
148 COLOR *sl;
149 int len;
150 register struct mbc *mb;
151 {
152 double d;
153 register int i, j;
154
155 while (len--) {
156 colortrans(sl[0], mb->cmat, sl[0]);
157 clipgamut(sl[0], bright(sl[0]), CGAMUT, mb->cmin, mb->cmax);
158 for (i = 0; i < 3; i++) {
159 d = colval(sl[0],i);
160 for (j = 0; j < 4 && mb->xa[i][j+1] <= d; j++)
161 ;
162 colval(sl[0],i) = ( (mb->xa[i][j+1] - d)*mb->ya[i][j] +
163 (d - mb->xa[i][j])*mb->ya[i][j+1] ) /
164 (mb->xa[i][j+1] - mb->xa[i][j]);
165 }
166 sl++;
167 }
168 }
169
170
171 cwscan(sl, len, wp) /* apply color space warp to scaline */
172 COLOR *sl;
173 int len;
174 WARP3D *wp;
175 {
176 int rval;
177
178 while (len--) {
179 rval = warp3d(sl[0], sl[0], wp);
180 if (rval & W3ERROR)
181 syserror("warp3d");
182 if (rval & W3BADMAP) {
183 fprintf(stderr, "%s: %s: bad color space map\n",
184 progname, cwarpfile);
185 exit(1);
186 }
187 clipgamut(sl[0], bright(sl[0]), CGAMUT, cblack, cwhite);
188 sl++;
189 }
190 }
191
192
193 getmbcalfile(fn, mb) /* load macbethcal file */
194 char *fn;
195 register struct mbc *mb;
196 {
197 extern char *fgets();
198 char buf[128];
199 FILE *fp;
200 int inpflags = 0;
201 register int i;
202
203 if ((fp = fopen(fn, "r")) == NULL)
204 syserror(fn);
205 while (fgets(buf, sizeof(buf), fp) != NULL) {
206 if (!(inpflags & 01) &&
207 sscanf(buf,
208 "rxa(i) : select(i,%f,%f,%f,%f,%f,%f)",
209 &mb->xa[0][0], &mb->xa[0][1],
210 &mb->xa[0][2], &mb->xa[0][3],
211 &mb->xa[0][4], &mb->xa[0][5]
212 ) == 6)
213 inpflags |= 01;
214 else if (!(inpflags & 02) &&
215 sscanf(buf,
216 "rya(i) : select(i,%f,%f,%f,%f,%f,%f)",
217 &mb->ya[0][0], &mb->ya[0][1],
218 &mb->ya[0][2], &mb->ya[0][3],
219 &mb->ya[0][4], &mb->ya[0][5]
220 ) == 6)
221 inpflags |= 02;
222 else if (!(inpflags & 04) &&
223 sscanf(buf,
224 "gxa(i) : select(i,%f,%f,%f,%f,%f,%f)",
225 &mb->xa[1][0], &mb->xa[1][1],
226 &mb->xa[1][2], &mb->xa[1][3],
227 &mb->xa[1][4], &mb->xa[1][5]
228 ) == 6)
229 inpflags |= 04;
230 else if (!(inpflags & 010) &&
231 sscanf(buf,
232 "gya(i) : select(i,%f,%f,%f,%f,%f,%f)",
233 &mb->ya[1][0], &mb->ya[1][1],
234 &mb->ya[1][2], &mb->ya[1][3],
235 &mb->ya[1][4], &mb->ya[1][5]
236 ) == 6)
237 inpflags |= 010;
238 else if (!(inpflags & 020) &&
239 sscanf(buf,
240 "bxa(i) : select(i,%f,%f,%f,%f,%f,%f)",
241 &mb->xa[2][0], &mb->xa[2][1],
242 &mb->xa[2][2], &mb->xa[2][3],
243 &mb->xa[2][4], &mb->xa[2][5]
244 ) == 6)
245 inpflags |= 020;
246 else if (!(inpflags & 040) &&
247 sscanf(buf,
248 "bya(i) : select(i,%f,%f,%f,%f,%f,%f)",
249 &mb->ya[2][0], &mb->ya[2][1],
250 &mb->ya[2][2], &mb->ya[2][3],
251 &mb->ya[2][4], &mb->ya[2][5]
252 ) == 6)
253 inpflags |= 040;
254 else if (!(inpflags & 0100) &&
255 sscanf(buf,
256 "r = %f*r1 + %f*g1 + %f*b1",
257 &mb->cmat[0][0], &mb->cmat[0][1],
258 &mb->cmat[0][2]) == 3)
259 inpflags |= 0100;
260 else if (!(inpflags & 0200) &&
261 sscanf(buf,
262 "g = %f*r1 + %f*g1 + %f*b1",
263 &mb->cmat[1][0], &mb->cmat[1][1],
264 &mb->cmat[1][2]) == 3)
265 inpflags |= 0200;
266 else if (!(inpflags & 0400) &&
267 sscanf(buf,
268 "b = %f*r1 + %f*g1 + %f*b1",
269 &mb->cmat[2][0], &mb->cmat[2][1],
270 &mb->cmat[2][2]) == 3)
271 inpflags |= 0400;
272 }
273 if (inpflags != 0777) {
274 fprintf(stderr,
275 "%s: cannot grok macbethcal file \"%s\" (inpflags==0%o)\n",
276 progname, fn, inpflags);
277 exit(1);
278 }
279 fclose(fp);
280 /* compute gamut */
281 for (i = 0; i < 3; i++) {
282 colval(mb->cmin,i) = mb->xa[i][0] -
283 mb->ya[i][0] *
284 (mb->xa[i][1]-mb->xa[i][0]) /
285 (mb->ya[i][1]-mb->ya[i][0]);
286 colval(mb->cmax,i) = mb->xa[i][4] +
287 (1.-mb->ya[i][4]) *
288 (mb->xa[i][5] - mb->xa[i][4]) /
289 (mb->ya[i][5] - mb->ya[i][4]);
290 }
291 }