ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/common/rglmat.c
Revision: 3.4
Committed: Wed Apr 23 02:28:06 2003 UTC (21 years ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 3.3: +19 -1 lines
Log Message:
Added check for mesh primitive and warning when encountered

File Contents

# User Rev Content
1 gwlarson 3.1 #ifndef lint
2 greg 3.2 static const char RCSid[] = "$Id$";
3 gwlarson 3.1 #endif
4     /*
5     * Routines for Radiance -> OpenGL materials.
6     */
7    
8 greg 3.3 #include "copyright.h"
9 greg 3.2
10 gwlarson 3.1 #include "radogl.h"
11    
12     int domats = 1; /* are we doing materials? */
13    
14     LUTAB mtab = LU_SINIT(free,freemtl);
15    
16    
17 greg 3.2 void
18 gwlarson 3.1 rgl_matclear() /* clean up materials */
19     {
20     lu_done(&mtab);
21     domats = 1;
22     }
23    
24    
25     MATREC *
26     getmatp(nam) /* find material record for modifier name */
27     char *nam;
28     {
29     register LUENT *lup;
30    
31     if (nam == NULL)
32     return(NULL);
33     if ((lup = lu_find(&mtab, nam)) == NULL)
34     return(NULL);
35     return((MATREC *)lup->data);
36     }
37    
38    
39 greg 3.2 int
40 gwlarson 3.1 o_default(o) /* default object is non-material modifier */
41     register OBJREC *o;
42     {
43     register LUENT *lup;
44     #ifdef DEBUG
45     if (o->otype >= 0 && !ismodifier(o->otype))
46     error(CONSISTENCY, "o_default handed non-modifier");
47     #endif
48     /* find name in lookup table */
49     if ((lup = lu_find(&mtab, o->oname)) == NULL)
50     goto memerr;
51     if (lup->key == NULL) { /* new entry? */
52     lup->key = (char *)malloc(strlen(o->oname)+1);
53     if (lup->key == NULL)
54     goto memerr;
55     strcpy(lup->key, o->oname);
56     } else if (lup->data != NULL)
57 greg 3.2 freemtl((MATREC *)lup->data);
58 gwlarson 3.1 if ((lup->data = o->os) != NULL) /* make material reference */
59     ((MATREC *)lup->data)->nlinks++;
60 greg 3.4 return(0);
61 gwlarson 3.1 memerr:
62     error(SYSTEM, "out of memory in o_default");
63 greg 3.4 return(0);
64     }
65    
66    
67     int
68     o_unsupported(o) /* unsupported object primitive */
69     OBJREC *o;
70     {
71     objerror(o, WARNING, "unsupported type");
72     return(0);
73 gwlarson 3.1 }
74    
75    
76     MATREC *
77     newmaterial(nam) /* get an entry for a new material */
78     char *nam;
79     {
80     register LUENT *lup;
81     /* look it up (assign entry) */
82     if ((lup = lu_find(&mtab, nam)) == NULL)
83     goto memerr;
84     if (lup->key == NULL) { /* new entry? */
85     lup->key = (char *)malloc(strlen(nam)+1);
86     if (lup->key == NULL)
87     goto memerr;
88     strcpy(lup->key, nam);
89     } else if (lup->data != NULL)
90 greg 3.2 freemtl((MATREC *)lup->data);
91 gwlarson 3.1 lup->data = (char *)malloc(sizeof(MATREC));
92     if (lup->data == NULL)
93     goto memerr;
94     ((MATREC *)lup->data)->nlinks = 1;
95     return((MATREC *)lup->data);
96     memerr:
97     error(SYSTEM, "out of memory in newmaterial");
98     }
99    
100    
101 greg 3.2 void
102 gwlarson 3.1 freemtl(mp) /* free a material */
103     register MATREC *mp;
104     {
105     if (!--mp->nlinks)
106 greg 3.2 free((void *)mp);
107 gwlarson 3.1 }
108    
109    
110 greg 3.2 int
111 gwlarson 3.1 m_normal(o) /* compute normal material parameters */
112     register OBJREC *o;
113     {
114     register MATREC *m;
115     /* check arguments */
116     if (o->oargs.nfargs != (o->otype == MAT_TRANS ? 7 : 5))
117     objerror(o, USER, "bad # of real arguments");
118     /* allocate/insert material */
119     m = newmaterial(o->oname);
120     /* assign parameters */
121     setcolor(m->u.m.ambdiff, o->oargs.farg[0],
122     o->oargs.farg[1], o->oargs.farg[2]);
123     if ((m->type = o->otype) == MAT_METAL)
124     copycolor(m->u.m.specular, m->u.m.ambdiff);
125     else
126     setcolor(m->u.m.specular, 1., 1., 1.);
127     scalecolor(m->u.m.specular, o->oargs.farg[3]);
128     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[3]);
129     if (m->type == MAT_TRANS) {
130     scalecolor(m->u.m.specular, 1.-o->oargs.farg[5]);
131     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[5]);
132     }
133     if (o->oargs.farg[4] <= FTINY)
134     m->u.m.specexp = MAXSPECEXP;
135     else
136     m->u.m.specexp = 2./(o->oargs.farg[4]*o->oargs.farg[4]);
137     if (m->u.m.specexp > MAXSPECEXP)
138     m->u.m.specexp = MAXSPECEXP;
139 greg 3.4 return(0);
140 gwlarson 3.1 }
141    
142    
143 greg 3.2 int
144 gwlarson 3.1 m_aniso(o) /* anisotropic material */
145     register OBJREC *o;
146     {
147     register MATREC *m;
148     /* check arguments */
149     if (o->oargs.nfargs < (o->otype == MAT_TRANS2 ? 8 : 6))
150     objerror(o, USER, "bad # of real arguments");
151     /* allocate/insert material */
152     m = newmaterial(o->oname);
153     /* assign parameters */
154     setcolor(m->u.m.ambdiff, o->oargs.farg[0],
155     o->oargs.farg[1], o->oargs.farg[2]);
156     if ((m->type = o->otype) == MAT_METAL2)
157     copycolor(m->u.m.specular, m->u.m.ambdiff);
158     else
159     setcolor(m->u.m.specular, 1., 1., 1.);
160     scalecolor(m->u.m.specular, o->oargs.farg[3]);
161     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[3]);
162     if (m->type == MAT_TRANS2) {
163     scalecolor(m->u.m.specular, 1.-o->oargs.farg[6]);
164     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[6]);
165     }
166     if (o->oargs.farg[4]*o->oargs.farg[5] <= FTINY*FTINY)
167     m->u.m.specexp = MAXSPECEXP;
168     else
169     m->u.m.specexp = 2./(o->oargs.farg[4]*o->oargs.farg[5]);
170     if (m->u.m.specexp > MAXSPECEXP)
171     m->u.m.specexp = MAXSPECEXP;
172 greg 3.4 return(0);
173 gwlarson 3.1 }
174    
175    
176 greg 3.2 int
177 gwlarson 3.1 m_glass(o) /* glass material (hopeless) */
178     OBJREC *o;
179     {
180     register MATREC *m;
181    
182     m = newmaterial(o->oname);
183     m->type = o->otype;
184     setcolor(m->u.m.ambdiff, 0., 0., 0.);
185     setcolor(m->u.m.specular, .08, .08, .08);
186     m->u.m.specexp = MAXSPECEXP;
187 greg 3.4 return(0);
188 gwlarson 3.1 }
189    
190    
191 greg 3.2 int
192 gwlarson 3.1 m_brdf(o) /* convert functional material */
193     register OBJREC *o;
194     {
195     register MATREC *m;
196     /* check arguments */
197     if (o->oargs.nfargs < (o->otype == MAT_TFUNC ? 6 : 4))
198     objerror(o, USER, "bad # of real arguments");
199     /* allocate/insert material */
200     m = newmaterial(o->oname);
201     /* assign parameters */
202     setcolor(m->u.m.ambdiff, o->oargs.farg[0],
203     o->oargs.farg[1], o->oargs.farg[2]);
204     if ((m->type = o->otype) == MAT_MFUNC)
205     copycolor(m->u.m.specular, m->u.m.ambdiff);
206     else
207     setcolor(m->u.m.specular, 1., 1., 1.);
208     scalecolor(m->u.m.specular, o->oargs.farg[3]);
209     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[3]);
210     if (m->type == MAT_TFUNC) {
211     scalecolor(m->u.m.specular, 1.-o->oargs.farg[4]);
212     scalecolor(m->u.m.ambdiff, 1.-o->oargs.farg[4]);
213     }
214     m->u.m.specexp = UNKSPECEXP;
215 greg 3.4 return(0);
216 gwlarson 3.1 }
217    
218    
219 greg 3.2 int
220 gwlarson 3.1 m_brdf2(o) /* convert advanced functional material */
221     register OBJREC *o;
222     {
223     register MATREC *m;
224    
225     if (o->oargs.nfargs < 9)
226     objerror(o, USER, "bad # of real arguments");
227     m = newmaterial(o->oname);
228     m->type = o->otype;
229     /* assign average diffuse front+back */
230     setcolor(m->u.m.ambdiff, (o->oargs.farg[0]+o->oargs.farg[3])*.5,
231     (o->oargs.farg[1]+o->oargs.farg[4])*.5,
232     (o->oargs.farg[2]+o->oargs.farg[5])*.5);
233     /* guess the rest */
234     setcolor(m->u.m.specular, .1, .1, .1);
235     m->u.m.specexp = UNKSPECEXP;
236 greg 3.4 return(0);
237 gwlarson 3.1 }
238    
239    
240 greg 3.2 int
241 gwlarson 3.1 m_light(o) /* convert light type */
242     register OBJREC *o;
243     {
244     FVECT v;
245     register MATREC *m;
246    
247     if (o->oargs.nfargs < (o->otype == MAT_SPOT ? 7 : 3))
248     objerror(o, USER, "bad # of real arguments");
249     m = newmaterial(o->oname);
250     setcolor(m->u.l.emission, o->oargs.farg[0],
251     o->oargs.farg[1], o->oargs.farg[2]);
252     if ((m->type = o->otype) == MAT_SPOT) {
253     if ((m->u.l.spotang = o->oargs.farg[3]/2.) > 90.)
254     m->u.l.spotang = 180.;
255     v[0] = o->oargs.farg[4];
256     v[1] = o->oargs.farg[5];
257     v[2] = o->oargs.farg[6];
258     if (normalize(v) == 0.)
259     objerror(o, USER, "illegal direction");
260     VCOPY(m->u.l.spotdir, v);
261     } else {
262     m->u.l.spotang = 180.;
263     m->u.l.spotdir[0] = m->u.l.spotdir[1] = 0.;
264     m->u.l.spotdir[2] = -1.;
265     }
266 greg 3.4 return(0);
267 gwlarson 3.1 }
268    
269    
270 greg 3.2 int
271 gwlarson 3.1 m_mirror(o) /* convert mirror type */
272     register OBJREC *o;
273     {
274     register MATREC *m;
275    
276     if (o->oargs.nfargs != 3)
277     objerror(o, USER, "bad # real arguments");
278     m = newmaterial(o->oname);
279     m->type = o->otype;
280     setcolor(m->u.m.ambdiff, 0., 0., 0.);
281     setcolor(m->u.m.specular, o->oargs.farg[0],
282     o->oargs.farg[1], o->oargs.farg[2]);
283     m->u.m.specexp = MAXSPECEXP;
284 greg 3.4 return(0);
285 gwlarson 3.1 }
286    
287    
288 greg 3.2 int
289 gwlarson 3.1 m_prism(o) /* convert prism type */
290     register OBJREC *o;
291     {
292     register MATREC *m;
293     /* can't really deal with this type */
294     m = newmaterial(o->oname);
295     m->type = o->otype;
296     setcolor(m->u.m.ambdiff, 0.2, 0.2, 0.2);
297     setcolor(m->u.m.specular, 0.1, 0.1, 0.1);
298     m->u.m.specexp = UNKSPECEXP;
299 greg 3.4 return(0);
300 gwlarson 3.1 }