ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/rt/func.c
Revision: 1.12
Committed: Sat Dec 15 15:03:26 1990 UTC (33 years, 4 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 1.11: +37 -35 lines
Log Message:
changed handling of matrix transformations with new MAT4 & XF types
dynamic allocation of ray transformations with newrayxf()
added missing light source vector transformation to m_brdf.c

File Contents

# User Rev Content
1 greg 1.12 /* Copyright (c) 1990 Regents of the University of California */
2 greg 1.1
3     #ifndef lint
4     static char SCCSid[] = "$SunId$ LBL";
5     #endif
6    
7     /*
8     * func.c - interface to calcomp functions.
9     *
10     * 4/7/86
11     */
12    
13     #include "ray.h"
14    
15     #include "otypes.h"
16    
17    
18 greg 1.12 XF funcxf; /* current transformation */
19     static OBJREC *fobj = NULL; /* current function object */
20     static RAY *fray = NULL; /* current function ray */
21 greg 1.1
22    
23 greg 1.12 setmap(m, r, bx) /* set channels for function call */
24 greg 1.1 OBJREC *m;
25     register RAY *r;
26 greg 1.12 XF *bx;
27 greg 1.1 {
28     extern double l_noise3(), l_noise3a(), l_noise3b(), l_noise3c();
29     extern double l_hermite(), l_fnoise3(), l_arg();
30     extern long eclock;
31     static char *initfile = "rayinit.cal";
32 greg 1.12 static long lastrno = -1;
33     /* check to see if already set */
34     if (m == fobj && r->rno == lastrno)
35     return;
36     /* initialize if first call */
37 greg 1.1 if (initfile != NULL) {
38     loadfunc(initfile);
39 greg 1.9 scompile("Dx=$1;Dy=$2;Dz=$3;", NULL, 0);
40     scompile("Nx=$4;Ny=$5;Nz=$6;", NULL, 0);
41     scompile("Px=$7;Py=$8;Pz=$9;", NULL, 0);
42     scompile("T=$10;Rdot=$11;", NULL, 0);
43     scompile("S=$12;Tx=$13;Ty=$14;Tz=$15;", NULL, 0);
44     scompile("Ix=$16;Iy=$17;Iz=$18;", NULL, 0);
45     scompile("Jx=$19;Jy=$20;Jz=$21;", NULL, 0);
46     scompile("Kx=$22;Ky=$23;Kz=$24;", NULL, 0);
47 greg 1.1 funset("arg", 1, l_arg);
48     funset("noise3", 3, l_noise3);
49     funset("noise3a", 3, l_noise3a);
50     funset("noise3b", 3, l_noise3b);
51     funset("noise3c", 3, l_noise3c);
52     funset("hermite", 5, l_hermite);
53     funset("fnoise3", 3, l_fnoise3);
54     initfile = NULL;
55     }
56     fobj = m;
57     fray = r;
58 greg 1.12 lastrno = r->rno;
59     if (r->rox != NULL) {
60     funcxf.sca = r->rox->b.sca * bx->sca;
61     multmat4(funcxf.xfm, r->rox->b.xfm, bx->xfm);
62     } else
63     copystruct(&funcxf, bx);
64 greg 1.1 eclock++; /* notify expression evaluator */
65     }
66    
67    
68     setfunc(m, r) /* simplified interface to setmap */
69     register OBJREC *m;
70     RAY *r;
71     {
72 greg 1.2 register XF *mxf;
73 greg 1.1
74 greg 1.2 if ((mxf = (XF *)m->os) == NULL) {
75 greg 1.5 register int n;
76     register char **sa;
77 greg 1.1
78 greg 1.5 for (n = m->oargs.nsargs, sa = m->oargs.sarg;
79     n > 0 && **sa != '-'; n--, sa++)
80     ;
81 greg 1.1 mxf = (XF *)malloc(sizeof(XF));
82     if (mxf == NULL)
83     goto memerr;
84 greg 1.12 if (invxf(mxf, n, sa) != n)
85 greg 1.1 objerror(m, USER, "bad transform");
86     if (mxf->sca < 0.0)
87     mxf->sca = -mxf->sca;
88 greg 1.2 m->os = (char *)mxf;
89 greg 1.1 }
90 greg 1.12 setmap(m, r, mxf);
91 greg 1.1 return;
92     memerr:
93     error(SYSTEM, "out of memory in setfunc");
94     }
95    
96    
97     loadfunc(fname) /* load definition file */
98     char *fname;
99     {
100     extern char *libpath; /* library search path */
101     char *ffname;
102    
103 greg 1.6 if ((ffname = getpath(fname, libpath, R_OK)) == NULL) {
104 greg 1.1 sprintf(errmsg, "cannot find function file \"%s\"", fname);
105     error(USER, errmsg);
106     }
107     fcompile(ffname);
108     }
109    
110    
111     double
112     l_arg() /* return nth real argument */
113     {
114     extern double argument();
115     register int n;
116    
117     n = argument(1) + .5; /* round to integer */
118    
119     if (n < 1)
120     return(fobj->oargs.nfargs);
121    
122     if (n > fobj->oargs.nfargs) {
123     sprintf(errmsg, "missing real argument %d", n);
124     objerror(fobj, USER, errmsg);
125     }
126     return(fobj->oargs.farg[n-1]);
127     }
128    
129    
130     double
131     chanvalue(n) /* return channel n to calcomp */
132     register int n;
133     {
134 greg 1.8 double sum;
135 greg 1.1 register RAY *r;
136    
137 greg 1.10 if (--n < 0)
138     goto badchan;
139 greg 1.1
140 greg 1.8 if (n < 3) /* ray direction */
141 greg 1.1
142 greg 1.12 return( ( fray->rdir[0]*funcxf.xfm[0][n] +
143     fray->rdir[1]*funcxf.xfm[1][n] +
144     fray->rdir[2]*funcxf.xfm[2][n] )
145     / funcxf.sca );
146 greg 1.1
147 greg 1.8 if (n < 6) /* surface normal */
148    
149 greg 1.12 return( ( fray->ron[0]*funcxf.xfm[0][n-3] +
150     fray->ron[1]*funcxf.xfm[1][n-3] +
151     fray->ron[2]*funcxf.xfm[2][n-3] )
152     / funcxf.sca );
153 greg 1.8
154     if (n < 9) /* intersection */
155    
156 greg 1.12 return( fray->rop[0]*funcxf.xfm[0][n-6] +
157     fray->rop[1]*funcxf.xfm[1][n-6] +
158     fray->rop[2]*funcxf.xfm[2][n-6] +
159     funcxf.xfm[3][n-6] );
160 greg 1.8
161 greg 1.10 if (n == 9) { /* distance */
162    
163     sum = fray->rot;
164     for (r = fray->parent; r != NULL; r = r->parent)
165     sum += r->rot;
166 greg 1.12 return(sum * funcxf.sca);
167 greg 1.10
168     }
169     if (n == 10) /* dot product */
170     return(fray->rod);
171    
172 greg 1.8 if (n == 11) /* scale */
173 greg 1.12 return(funcxf.sca);
174 greg 1.8
175     if (n < 15) /* origin */
176 greg 1.12 return(funcxf.xfm[3][n-12]);
177 greg 1.8
178     if (n < 18) /* i unit vector */
179 greg 1.12 return(funcxf.xfm[0][n-15] / funcxf.sca);
180 greg 1.8
181     if (n < 21) /* j unit vector */
182 greg 1.12 return(funcxf.xfm[1][n-15] / funcxf.sca);
183 greg 1.8
184     if (n < 24) /* k unit vector */
185 greg 1.12 return(funcxf.xfm[2][n-21] / funcxf.sca);
186 greg 1.10 badchan:
187     error(USER, "illegal channel number");
188 greg 1.1 }