Initial revision
[blender.git] / source / blender / render / intern / source / renderdatabase.c
1 /**
2  * $Id$
3  *
4  * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version. The Blender
10  * Foundation also sells licenses for use in proprietary software under
11  * the Blender License.  See http://www.blender.org/BL/ for information
12  * about this.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software Foundation,
21  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22  *
23  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
24  * All rights reserved.
25  *
26  * The Original Code is: all of this file.
27  *
28  * Contributor(s): none yet.
29  *
30  * ***** END GPL/BL DUAL LICENSE BLOCK *****
31  * Storage, retrieval and query of render specific data.
32  */
33
34 /*
35  * All data from a Blender scene is converter by the renderconverter/
36  * into a special format that is used by the render module to make
37  * images out of. These functions interface to the render-specific
38  * database.  
39  *
40  * The blo{ha/ve/vl} arrays store pointers to blocks of 256 data
41  * entries each.
42  *
43  * The index of an entry is >>8 (the highest 24 * bits), to find an
44  * offset in a 256-entry block.
45  *
46  * - If the 256-entry block entry has an entry in the
47  * blove/bloha/blovl array of the current block, the i-th entry in
48  * that block is allocated to this entry.
49  *
50  * - If the entry has no block allocated for it yet, memory is
51  * allocated.
52  *
53  * The pointer to the correct entry is returned. Memory is guarateed
54  * to exist (as long as the malloc does not break). Since guarded
55  * allocation is used, memory _must_ be available. Otherwise, an
56  * exit(0) would occur.
57  * 
58  */
59
60 #include <math.h>
61 #include "MEM_guardedalloc.h"
62 #include "BLI_arithb.h"
63
64 #include "DNA_texture_types.h" 
65 #include "BKE_texture.h" 
66
67 #include "render.h"
68 #include "render_intern.h"
69
70 /* ------------------------------------------------------------------------- */
71
72 VertRen *RE_findOrAddVert(int nr)
73 {
74         VertRen *v;
75         int a;
76
77         if(nr<0 || nr>MAXVERT ) {
78                 printf("error in findOrAddVert: %d\n",nr);
79                 return R.blove[0];
80         }
81         a= nr>>8;
82         v= R.blove[a];
83         if(v==0) {
84                 v= (VertRen *)MEM_callocN(256*sizeof(VertRen),"findOrAddVert");
85                 R.blove[a]= v;
86         }
87         v+= (nr & 255);
88         return v;
89 }
90
91 /* ------------------------------------------------------------------------ */
92
93 HaloRen *RE_findOrAddHalo(int nr)
94 {
95         HaloRen *h;
96         int a;
97
98         if(nr<0 || nr>MAXVERT ) {
99                 printf("error in findOrAddHalo: %d\n",nr);
100                 return R.bloha[0];
101         }
102         a= nr>>8;
103         h= R.bloha[a];
104         if(h==0) {
105                 h= (HaloRen *)MEM_callocN(256*sizeof(HaloRen),"findOrAdHalo");
106                 R.bloha[a]= h;
107         }
108         h+= (nr & 255);
109         return h;
110 }
111
112 /* ------------------------------------------------------------------------ */
113
114 VlakRen *RE_findOrAddVlak(int nr)
115 {
116         VlakRen *v;
117         int a;
118
119         if(nr<0 || nr>MAXVLAK ) {
120                 printf("error in findOrAddVlak: %d\n",nr);
121                 return R.blovl[0];
122         }
123         a= nr>>8;
124         v= R.blovl[a];
125         if(v==0) {
126                 v= (VlakRen *)MEM_callocN(256*sizeof(VlakRen),"findOrAddVlak");
127                 R.blovl[a]= v;
128         }
129         v+= (nr & 255);
130         return v;
131 }
132
133 /* ------------------------------------------------------------------------- */
134
135 extern float Tin, Tr, Tg, Tb;
136 HaloRen *RE_inithalo(Material *ma, 
137                                   float *vec, 
138                                   float *vec1, 
139                                   float *orco, 
140                                   float hasize, 
141                                   float vectsize)
142 {
143         HaloRen *har;
144         MTex *mtex;
145         float xn, yn, zn, texvec[3], hoco[4], hoco1[4];
146
147         if(hasize==0) return 0;
148
149         RE_projectverto(vec, hoco);
150         if(hoco[3]==0.0) return 0;
151         if(vec1) {
152                 RE_projectverto(vec1, hoco1);
153                 if(hoco1[3]==0.0) return 0;
154         }
155
156         har= RE_findOrAddHalo(R.tothalo++);
157         VECCOPY(har->co, vec);
158         har->hasize= hasize;
159
160         /* projectvert wordt in zbufvlaggen gedaan ivm parts/border/pano */
161
162         /* halovect */
163         if(vec1) {
164
165                 har->type |= HA_VECT;
166
167                 zn= hoco[3];
168                 har->xs= 0.5*R.rectx*(hoco[0]/zn);
169                 har->ys= 0.5*R.recty*(hoco[1]/zn);
170                 har->zs= 0x7FFFFF*(1.0+hoco[2]/zn);
171
172       har->zBufDist = 0x7FFFFFFF*(hoco[2]/zn); 
173
174                 xn=  har->xs - 0.5*R.rectx*(hoco1[0]/hoco1[3]);
175                 yn=  har->ys - 0.5*R.recty*(hoco1[1]/hoco1[3]);
176                 if(xn==0.0 || (xn==0.0 && yn==0.0)) zn= 0.0;
177                 else zn= atan2(yn, xn);
178
179                 har->sin= sin(zn);
180                 har->cos= cos(zn);
181                 zn= VecLenf(vec1, vec);
182
183                 har->hasize= vectsize*zn + (1.0-vectsize)*hasize;
184                 
185                 VecSubf(har->no, vec, vec1);
186                 Normalise(har->no);
187         }
188
189         if(ma->mode & MA_HALO_XALPHA) har->type |= HA_XALPHA;
190
191         har->alfa= ma->alpha;
192         har->r= 255.0*ma->r;
193         har->g= 255.0*ma->g;
194         har->b= 255.0*ma->b;
195         har->add= 255.0*ma->add;
196         har->mat= ma->ren;
197         har->hard= ma->har;
198         har->seed= ma->ren->seed1 % 256;
199
200         if(ma->mode & MA_STAR) har->starpoints= ma->starc;
201         if(ma->mode & MA_HALO_LINES) har->linec= ma->linec;
202         if(ma->mode & MA_HALO_RINGS) har->ringc= ma->ringc;
203         if(ma->mode & MA_HALO_FLARE) har->flarec= ma->flarec;
204
205
206         if(ma->mtex[0]) {
207
208                 if( (ma->mode & MA_HALOTEX) ) har->tex= 1;
209                 else {
210
211                         mtex= ma->mtex[0];
212                         VECCOPY(texvec, vec);
213
214                         if(mtex->texco & TEXCO_NORM) {
215                                 ;
216                         }
217                         else if(mtex->texco & TEXCO_OBJECT) {
218                                 /* texvec[0]+= imatbase->ivec[0]; */
219                                 /* texvec[1]+= imatbase->ivec[1]; */
220                                 /* texvec[2]+= imatbase->ivec[2]; */
221                                 /* Mat3MulVecfl(imatbase->imat, texvec); */
222                         }
223                         else {
224                                 if(orco) {
225                                         VECCOPY(texvec, orco);
226                                 }
227                         }
228
229                         externtex(mtex, texvec);
230
231                         yn= Tin*mtex->colfac;
232                         zn= Tin*mtex->varfac;
233
234                         if(mtex->mapto & MAP_COL) {
235                                 zn= 1.0-yn;
236                                 har->r= 255.0*(yn*Tr+ zn*ma->r);
237                                 har->g= 255.0*(yn*Tg+ zn*ma->g);
238                                 har->b= 255.0*(yn*Tb+ zn*ma->b);
239                         }
240                         if(mtex->texco & 16) {
241                                 har->alfa= 255.0*Tin;
242                         }
243                 }
244         }
245
246         return har;
247 }
248 /* ------------------------------------------------------------------------- */