Didn't hear any complaints so I'm commiting the patch for bug:
[blender.git] / source / blender / blenkernel / intern / effect.c
1 /*  effect.c        MIX MODEL
2  * 
3  *  dec 95
4  * 
5  * $Id$
6  *
7  * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
8  *
9  * This program is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License
11  * as published by the Free Software Foundation; either version 2
12  * of the License, or (at your option) any later version. The Blender
13  * Foundation also sells licenses for use in proprietary software under
14  * the Blender License.  See http://www.blender.org/BL/ for information
15  * about this.
16  *
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20  * GNU General Public License for more details.
21  *
22  * You should have received a copy of the GNU General Public License
23  * along with this program; if not, write to the Free Software Foundation,
24  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
25  *
26  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
27  * All rights reserved.
28  *
29  * The Original Code is: all of this file.
30  *
31  * Contributor(s): none yet.
32  *
33  * ***** END GPL/BL DUAL LICENSE BLOCK *****
34  */
35
36 #include <math.h>
37 #include <stdlib.h>
38
39 #include "MEM_guardedalloc.h"
40 #include "DNA_listBase.h"
41 #include "DNA_effect_types.h"
42 #include "DNA_object_types.h"
43 #include "DNA_mesh_types.h"
44 #include "DNA_material_types.h"
45 #include "DNA_curve_types.h"
46 #include "DNA_key_types.h"
47 #include "DNA_texture_types.h"
48 #include "DNA_scene_types.h"
49 #include "DNA_lattice_types.h"
50
51 #include "BLI_blenlib.h"
52 #include "BLI_arithb.h"
53 #include "BLI_rand.h"
54
55 #include "BKE_utildefines.h"
56 #include "BKE_bad_level_calls.h"
57 #include "BKE_global.h"
58 #include "BKE_material.h"
59 #include "BKE_effect.h"
60 #include "BKE_key.h"
61 #include "BKE_ipo.h"
62 #include "BKE_screen.h"
63 #include "BKE_texture.h"
64 #include "BKE_blender.h"
65 #include "BKE_object.h"
66 #include "BKE_displist.h"
67 #include "BKE_lattice.h"
68
69 #ifdef HAVE_CONFIG_H
70 #include <config.h>
71 #endif
72
73 Effect *add_effect(int type)
74 {
75         Effect *eff=0;
76         BuildEff *bld;
77         PartEff *paf;
78         WaveEff *wav;
79         int a;
80         
81         switch(type) {
82         case EFF_BUILD:
83                 bld= MEM_callocN(sizeof(BuildEff), "neweff");
84                 eff= (Effect *)bld;
85                 
86                 bld->sfra= 1.0;
87                 bld->len= 100.0;
88                 break;
89                 
90         case EFF_PARTICLE:
91                 paf= MEM_callocN(sizeof(PartEff), "neweff");
92                 eff= (Effect *)paf;
93                 
94                 paf->sta= 1.0;
95                 paf->end= 100.0;
96                 paf->lifetime= 50.0;
97                 for(a=0; a<PAF_MAXMULT; a++) {
98                         paf->life[a]= 50.0;
99                         paf->child[a]= 4;
100                         paf->mat[a]= 1;
101                 }
102                 
103                 paf->totpart= 1000;
104                 paf->totkey= 8;
105                 paf->staticstep= 5;
106                 paf->defvec[2]= 1.0f;
107                 paf->nabla= 0.05f;
108                 
109                 break;
110                 
111         case EFF_WAVE:
112                 wav= MEM_callocN(sizeof(WaveEff), "neweff");
113                 eff= (Effect *)wav;
114                 
115                 wav->flag |= (WAV_X+WAV_Y+WAV_CYCL);
116                 
117                 wav->height= 0.5f;
118                 wav->width= 1.5f;
119                 wav->speed= 0.5f;
120                 wav->narrow= 1.5f;
121                 wav->lifetime= 0.0f;
122                 wav->damp= 10.0f;
123                 
124                 break;
125         }
126         
127         eff->type= eff->buttype= type;
128         eff->flag |= SELECT;
129         
130         return eff;
131 }
132
133 void free_effect(Effect *eff)
134 {
135         PartEff *paf;
136         
137         if(eff->type==EFF_PARTICLE) {
138                 paf= (PartEff *)eff;
139                 if(paf->keys) MEM_freeN(paf->keys);
140         }
141         MEM_freeN(eff); 
142 }
143
144
145 void free_effects(ListBase *lb)
146 {
147         Effect *eff;
148         
149         eff= lb->first;
150         while(eff) {
151                 BLI_remlink(lb, eff);
152                 free_effect(eff);
153                 eff= lb->first;
154         }
155 }
156
157 Effect *copy_effect(Effect *eff) 
158 {
159         Effect *effn;
160         
161         effn= MEM_dupallocN(eff);
162         if(effn->type==EFF_PARTICLE) ((PartEff *)effn)->keys= 0;
163
164         return effn;    
165 }
166
167 void copy_act_effect(Object *ob)
168 {
169         /* return de aktieve eff gekopieerd */
170         Effect *effn, *eff;
171         
172         eff= ob->effect.first;
173         while(eff) {
174                 if(eff->flag & SELECT) {
175                         
176                         effn= copy_effect(eff);
177                         BLI_addtail(&ob->effect, effn);
178                         
179                         eff->flag &= ~SELECT;
180                         return;
181                         
182                 }
183                 eff= eff->next;
184         }
185         
186         /* als tie hier komt: new effect */
187         eff= add_effect(EFF_BUILD);
188         BLI_addtail(&ob->effect, eff);
189                         
190 }
191
192 void copy_effects(ListBase *lbn, ListBase *lb)
193 {
194         Effect *eff, *effn;
195
196         lbn->first= lbn->last= 0;
197
198         eff= lb->first;
199         while(eff) {
200                 effn= copy_effect(eff);
201                 BLI_addtail(lbn, effn);
202                 
203                 eff= eff->next;
204         }
205         
206 }
207
208 void deselectall_eff(Object *ob)
209 {
210         Effect *eff= ob->effect.first;
211         
212         while(eff) {
213                 eff->flag &= ~SELECT;
214                 eff= eff->next;
215         }
216 }
217
218 void set_buildvars(Object *ob, int *start, int *end)
219 {
220         BuildEff *bld;
221         float ctime;
222         
223         bld= ob->effect.first;
224         while(bld) {
225                 if(bld->type==EFF_BUILD) {
226                         ctime= bsystem_time(ob, 0, (float)G.scene->r.cfra, bld->sfra-1.0f);
227                         if(ctime < 0.0) {
228                                 *end= *start;
229                         }
230                         else if(ctime < bld->len) {
231                                 *end= *start+ (int)((*end - *start)*ctime/bld->len);
232                         }
233                         
234                         return;
235                 }
236                 bld= bld->next;
237         }
238 }
239
240 /* ***************** PARTICLES ***************** */
241
242 Particle *new_particle(PartEff *paf)
243 {
244         static Particle *pa;
245         static int cur;
246
247         /* afspraak: als paf->keys==0: alloc */ 
248         if(paf->keys==0) {
249                 pa= paf->keys= MEM_callocN( paf->totkey*paf->totpart*sizeof(Particle), "particlekeys" );
250                 cur= 0;
251         }
252         else {
253                 if(cur && cur<paf->totpart) pa+=paf->totkey;
254                 cur++;
255         }
256         return pa;
257 }
258
259 PartEff *give_parteff(Object *ob)
260 {
261         PartEff *paf;
262         
263         paf= ob->effect.first;
264         while(paf) {
265                 if(paf->type==EFF_PARTICLE) return paf;
266                 paf= paf->next;
267         }
268         return 0;
269 }
270
271 void where_is_particle(PartEff *paf, Particle *pa, float ctime, float *vec)
272 {
273         Particle *p[4];
274         float dt, t[4];
275         int a;
276         
277         if(paf->totkey==1) {
278                 VECCOPY(vec, pa->co);
279                 return;
280         }
281         
282         /* eerst op zoek naar de eerste particlekey */
283         a= (int)((paf->totkey-1)*(ctime-pa->time)/pa->lifetime);
284         if(a>=paf->totkey) a= paf->totkey-1;
285         
286         pa+= a;
287         
288         if(a>0) p[0]= pa-1; else p[0]= pa;
289         p[1]= pa;
290         
291         if(a+1<paf->totkey) p[2]= pa+1; else p[2]= pa;
292         if(a+2<paf->totkey) p[3]= pa+2; else p[3]= p[2];
293         
294         if(p[1]==p[2]) dt= 0.0;
295         else dt= (ctime-p[1]->time)/(p[2]->time - p[1]->time);
296
297         if(paf->flag & PAF_BSPLINE) set_four_ipo(dt, t, KEY_BSPLINE);
298         else set_four_ipo(dt, t, KEY_CARDINAL);
299
300         vec[0]= t[0]*p[0]->co[0] + t[1]*p[1]->co[0] + t[2]*p[2]->co[0] + t[3]*p[3]->co[0];
301         vec[1]= t[0]*p[0]->co[1] + t[1]*p[1]->co[1] + t[2]*p[2]->co[1] + t[3]*p[3]->co[1];
302         vec[2]= t[0]*p[0]->co[2] + t[1]*p[1]->co[2] + t[2]*p[2]->co[2] + t[3]*p[3]->co[2];
303
304 }
305
306
307 void particle_tex(MTex *mtex, PartEff *paf, float *co, float *no)
308 {                               
309         extern float Tin, Tr, Tg, Tb;
310         float old;
311         
312         externtex(mtex, co);
313         
314         if(paf->texmap==PAF_TEXINT) {
315                 Tin*= paf->texfac;
316                 no[0]+= Tin*paf->defvec[0];
317                 no[1]+= Tin*paf->defvec[1];
318                 no[2]+= Tin*paf->defvec[2];
319         }
320         else if(paf->texmap==PAF_TEXRGB) {
321                 no[0]+= (Tr-0.5f)*paf->texfac;
322                 no[1]+= (Tg-0.5f)*paf->texfac;
323                 no[2]+= (Tb-0.5f)*paf->texfac;
324         }
325         else {  /* PAF_TEXGRAD */
326                 
327                 old= Tin;
328                 co[0]+= paf->nabla;
329                 externtex(mtex, co);
330                 no[0]+= (old-Tin)*paf->texfac;
331                 
332                 co[0]-= paf->nabla;
333                 co[1]+= paf->nabla;
334                 externtex(mtex, co);
335                 no[1]+= (old-Tin)*paf->texfac;
336                 
337                 co[1]-= paf->nabla;
338                 co[2]+= paf->nabla;
339                 externtex(mtex, co);
340                 no[2]+= (old-Tin)*paf->texfac;
341                 
342         }
343 }
344
345 void make_particle_keys(int depth, int nr, PartEff *paf, Particle *part, float *force, int deform, MTex *mtex)
346 {
347         Particle *pa, *opa = NULL;
348         float damp, deltalife;
349         int b, rt1, rt2;
350         
351         damp= 1.0f-paf->damp;
352         pa= part;
353         
354         /* startsnelheid: random */
355         if(paf->randfac!=0.0) {
356                 pa->no[0]+= (float)(paf->randfac*( BLI_drand() -0.5));
357                 pa->no[1]+= (float)(paf->randfac*( BLI_drand() -0.5));
358                 pa->no[2]+= (float)(paf->randfac*( BLI_drand() -0.5));
359         }
360         
361         /* startsnelheid: texture */
362         if(mtex && paf->texfac!=0.0) {
363                 particle_tex(mtex, paf, pa->co, pa->no);
364         }
365         
366         if(paf->totkey>1) deltalife= pa->lifetime/(paf->totkey-1);
367         else deltalife= pa->lifetime;
368
369         opa= pa;
370         pa++;
371                 
372         b= paf->totkey-1;
373         while(b--) {
374                 /* nieuwe tijd */
375                 pa->time= opa->time+deltalife;
376
377                 /* nieuwe plek */
378                 pa->co[0]= opa->co[0] + deltalife*opa->no[0];
379                 pa->co[1]= opa->co[1] + deltalife*opa->no[1];
380                 pa->co[2]= opa->co[2] + deltalife*opa->no[2];
381
382                 /* nieuwe snelheid */
383                 pa->no[0]= opa->no[0] + deltalife*force[0];
384                 pa->no[1]= opa->no[1] + deltalife*force[1];
385                 pa->no[2]= opa->no[2] + deltalife*force[2];
386
387                 /* snelheid: texture */
388                 if(mtex && paf->texfac!=0.0) {
389                         particle_tex(mtex, paf, pa->co, pa->no);
390                 }
391                 if(damp!=1.0) {
392                         pa->no[0]*= damp;
393                         pa->no[1]*= damp;
394                         pa->no[2]*= damp;
395                 }
396         
397                 opa= pa;
398                 pa++;
399                 /* opa wordt onderin ook gebruikt */
400         }
401
402         if(deform) {
403                 /* alle keys deformen */
404                 pa= part;
405                 b= paf->totkey;
406                 while(b--) {
407                         calc_latt_deform(pa->co);
408                         pa++;
409                 }
410         }
411         
412         /* the big multiplication */
413         if(depth<PAF_MAXMULT && paf->mult[depth]!=0.0) {
414                 
415                 /* new 'child' emerges from an average 'mult' part from 
416                         the particles */
417                 damp = (float)nr;
418                 rt1= (int)(damp*paf->mult[depth]);
419                 rt2= (int)((damp+1.0)*paf->mult[depth]);
420                 if(rt1!=rt2) {
421                         
422                         for(b=0; b<paf->child[depth]; b++) {
423                                 pa= new_particle(paf);
424                                 *pa= *opa;
425                                 pa->lifetime= paf->life[depth];
426                                 if(paf->randlife!=0.0) {
427                                         pa->lifetime*= 1.0f+ (float)(paf->randlife*( BLI_drand() - 0.5));
428                                 }
429                                 pa->mat_nr= paf->mat[depth];
430                                 
431                                 make_particle_keys(depth+1, b, paf, pa, force, deform, mtex);
432                         }
433                 }
434         }
435 }
436
437 void init_mv_jit(float *jit, int num)
438 {
439         float *jit2, x, rad1, rad2, rad3;
440         int i, num2;
441
442         if(num==0) return;
443
444         rad1= (float)(1.0/sqrt((float)num));
445         rad2= (float)(1.0/((float)num));
446         rad3= (float)sqrt((float)num)/((float)num);
447
448         BLI_srand(31415926 + num);
449         x= 0;
450         num2 = 2 * num;
451         for(i=0; i<num2; i+=2) {
452         
453                 jit[i]= x+ (float)(rad1*(0.5-BLI_drand()));
454                 jit[i+1]= ((float)i/2)/num +(float)(rad1*(0.5-BLI_drand()));
455                 
456                 jit[i]-= (float)floor(jit[i]);
457                 jit[i+1]-= (float)floor(jit[i+1]);
458                 
459                 x+= rad3;
460                 x -= (float)floor(x);
461         }
462
463         jit2= MEM_mallocN(12 + 2*sizeof(float)*num, "initjit");
464
465         for (i=0 ; i<4 ; i++) {
466                 RE_jitterate1(jit, jit2, num, rad1);
467                 RE_jitterate1(jit, jit2, num, rad1);
468                 RE_jitterate2(jit, jit2, num, rad2);
469         }
470         MEM_freeN(jit2);
471 }
472
473
474 void give_mesh_mvert(Mesh *me, int nr, float *co, short *no)
475 {
476         static float *jit=0;
477         static int jitlevel=1;
478         MVert *mvert;
479         MFace *mface;
480         float u, v, *v1, *v2, *v3, *v4;
481         int curface, curjit;
482         short *n1, *n2, *n3, *n4;
483         
484         /* signal */
485         if(me==0) {
486                 if(jit) MEM_freeN(jit);
487                 jit= 0;
488                 return;
489         }
490         
491         if(me->totface==0 || nr<me->totvert) {
492                 mvert= me->mvert + (nr % me->totvert);
493                 VECCOPY(co, mvert->co);
494                 VECCOPY(no, mvert->no);
495         }
496         else {
497                 
498                 nr-= me->totvert;
499                 
500                 if(jit==0) {
501                         jitlevel= nr/me->totface;
502                         if(jitlevel==0) jitlevel= 1;
503                         if(jitlevel>100) jitlevel= 100;
504                         
505                         jit= MEM_callocN(2+ jitlevel*2*sizeof(float), "jit");
506                         init_mv_jit(jit, jitlevel);
507                         
508                 }
509
510                 curjit= nr/me->totface;
511                 curjit= curjit % jitlevel;
512
513                 curface= nr % me->totface;
514                 
515                 mface= me->mface;
516                 mface+= curface;
517                 
518                 v1= (me->mvert+(mface->v1))->co;
519                 v2= (me->mvert+(mface->v2))->co;
520                 n1= (me->mvert+(mface->v1))->no;
521                 n2= (me->mvert+(mface->v2))->no;
522                 if(mface->v3==0) {
523                         v3= (me->mvert+(mface->v2))->co;
524                         v4= (me->mvert+(mface->v1))->co;
525                         n3= (me->mvert+(mface->v2))->no;
526                         n4= (me->mvert+(mface->v1))->no;
527                 }
528                 else if(mface->v4==0) {
529                         v3= (me->mvert+(mface->v3))->co;
530                         v4= (me->mvert+(mface->v1))->co;
531                         n3= (me->mvert+(mface->v3))->no;
532                         n4= (me->mvert+(mface->v1))->no;
533                 }
534                 else {
535                         v3= (me->mvert+(mface->v3))->co;
536                         v4= (me->mvert+(mface->v4))->co;
537                         n3= (me->mvert+(mface->v3))->no;
538                         n4= (me->mvert+(mface->v4))->no;
539                 }
540
541                 u= jit[2*curjit];
542                 v= jit[2*curjit+1];
543
544                 co[0]= (float)((1.0-u)*(1.0-v)*v1[0] + (1.0-u)*(v)*v2[0] + (u)*(v)*v3[0] + (u)*(1.0-v)*v4[0]);
545                 co[1]= (float)((1.0-u)*(1.0-v)*v1[1] + (1.0-u)*(v)*v2[1] + (u)*(v)*v3[1] + (u)*(1.0-v)*v4[1]);
546                 co[2]= (float)((1.0-u)*(1.0-v)*v1[2] + (1.0-u)*(v)*v2[2] + (u)*(v)*v3[2] + (u)*(1.0-v)*v4[2]);
547                 
548                 no[0]= (short)((1.0-u)*(1.0-v)*n1[0] + (1.0-u)*(v)*n2[0] + (u)*(v)*n3[0] + (u)*(1.0-v)*n4[0]);
549                 no[1]= (short)((1.0-u)*(1.0-v)*n1[1] + (1.0-u)*(v)*n2[1] + (u)*(v)*n3[1] + (u)*(1.0-v)*n4[1]);
550                 no[2]= (short)((1.0-u)*(1.0-v)*n1[2] + (1.0-u)*(v)*n2[2] + (u)*(v)*n3[2] + (u)*(1.0-v)*n4[2]);
551                 
552         }
553 }
554
555
556 void build_particle_system(Object *ob)
557 {
558         Object *par;
559         PartEff *paf;
560         Particle *pa;
561         Mesh *me;
562         MVert *mvert;
563         MTex *mtexmove=0;
564         Material *ma;
565         float framelenont, ftime, dtime, force[3], imat[3][3], vec[3];
566         float fac, prevobmat[4][4], sfraont, co[3];
567         int deform=0, a, cur, cfraont, cfralast, totpart;
568         short no[3];
569         
570         if(ob->type!=OB_MESH) return;
571         me= ob->data;
572         if(me->totvert==0) return;
573         
574         ma= give_current_material(ob, 1);
575         if(ma) {
576                 mtexmove= ma->mtex[7];
577         }
578         
579         paf= give_parteff(ob);
580         if(paf==0) return;
581
582         waitcursor(1);
583         
584         disable_speed_curve(1);
585         
586         /* alle particles genereren */
587         if(paf->keys) MEM_freeN(paf->keys);
588         paf->keys= 0;
589         new_particle(paf);      
590
591         cfraont= G.scene->r.cfra;
592         cfralast= -1000;
593         framelenont= G.scene->r.framelen;
594         G.scene->r.framelen= 1.0;
595         sfraont= ob->sf;
596         ob->sf= 0.0;
597         
598         /* mult generaties? */
599         totpart= paf->totpart;
600         for(a=0; a<PAF_MAXMULT; a++) {
601                 if(paf->mult[a]!=0.0) {
602                         /* interessante formule! opdezewijze is na 'x' generaties het totale aantal paf->totpart */
603                         totpart= (int)(totpart / (1.0+paf->mult[a]*paf->child[a]));
604                 }
605                 else break;
606         }
607
608         ftime= paf->sta;
609         dtime= (paf->end - paf->sta)/totpart;
610         
611         /* hele hiera onthouden */
612         par= ob;
613         while(par) {
614                 pushdata(par, sizeof(Object));
615                 par= par->parent;
616         }
617
618         /* alles op eerste frame zetten */
619         G.scene->r.cfra= cfralast= (int)floor(ftime);
620         par= ob;
621         while(par) {
622                 /* do_ob_ipo(par); */
623                 do_ob_key(par);
624                 par= par->parent;
625         }
626         do_mat_ipo(ma);
627         
628         if((paf->flag & PAF_STATIC)==0) {
629                 where_is_object(ob);
630                 Mat4CpyMat4(prevobmat, ob->obmat);
631                 Mat4Invert(ob->imat, ob->obmat);
632                 Mat3CpyMat4(imat, ob->imat);
633         }
634         else {
635                 Mat4One(prevobmat);
636                 Mat3One(imat);
637         }
638         
639         BLI_srand(paf->seed);
640         
641         /* gaat anders veuls te hard */
642         force[0]= paf->force[0]*0.05f;
643         force[1]= paf->force[1]*0.05f;
644         force[2]= paf->force[2]*0.05f;
645         
646         deform= (ob->parent && ob->parent->type==OB_LATTICE);
647         if(deform) init_latt_deform(ob->parent, 0);
648         
649         /* init */
650         give_mesh_mvert(me, totpart, co, no);
651         
652         for(a=0; a<totpart; a++, ftime+=dtime) {
653                 
654                 pa= new_particle(paf);
655                 pa->time= ftime;
656                 
657                 /* ob op juiste tijd zetten */
658                 
659                 if((paf->flag & PAF_STATIC)==0) {
660                 
661                         cur= (int)floor(ftime) + 1 ;            /* + 1 heeft een reden: (obmat/prevobmat) anders beginnen b.v. komeetstaartjes te laat */
662                         if(cfralast != cur) {
663                                 G.scene->r.cfra= cfralast= cur;
664         
665                                 /* later bijgevoegd: blur? */
666                                 bsystem_time(ob, ob->parent, (float)G.scene->r.cfra, 0.0);
667                                 
668                                 par= ob;
669                                 while(par) {
670                                         /* do_ob_ipo(par); */
671                                         par->ctime= -1234567.0;
672                                         do_ob_key(par);
673                                         par= par->parent;
674                                 }
675                                 do_mat_ipo(ma);
676                                 Mat4CpyMat4(prevobmat, ob->obmat);
677                                 where_is_object(ob);
678                                 Mat4Invert(ob->imat, ob->obmat);
679                                 Mat3CpyMat4(imat, ob->imat);
680                         }
681                 }
682                 /* coordinaat ophalen */
683                 if(paf->flag & PAF_FACE) give_mesh_mvert(me, a, co, no);
684                 else {
685                         mvert= me->mvert + (a % me->totvert);
686                         VECCOPY(co, mvert->co);
687                         VECCOPY(no, mvert->no);
688                 }
689                 
690                 VECCOPY(pa->co, co);
691                 
692                 if(paf->flag & PAF_STATIC);
693                 else {
694                         Mat4MulVecfl(ob->obmat, pa->co);
695                 
696                         VECCOPY(vec, co);
697                         Mat4MulVecfl(prevobmat, vec);
698                         
699                         /* eerst even startsnelheid: object */
700                         VecSubf(pa->no, pa->co, vec);
701                         VecMulf(pa->no, paf->obfac);
702                         
703                         /* nu juiste interframe co berekenen */ 
704                         fac= (ftime- (float)floor(ftime));
705                         pa->co[0]= fac*pa->co[0] + (1.0f-fac)*vec[0];
706                         pa->co[1]= fac*pa->co[1] + (1.0f-fac)*vec[1];
707                         pa->co[2]= fac*pa->co[2] + (1.0f-fac)*vec[2];
708                 }
709                 
710                 /* startsnelheid: normaal */
711                 if(paf->normfac!=0.0) {
712                         /* sp= mvert->no; */
713                                 /* transpose ! */
714                         vec[0]= imat[0][0]*no[0] + imat[0][1]*no[1] + imat[0][2]*no[2];
715                         vec[1]= imat[1][0]*no[0] + imat[1][1]*no[1] + imat[1][2]*no[2];
716                         vec[2]= imat[2][0]*no[0] + imat[2][1]*no[1] + imat[2][2]*no[2];         
717                 
718                         Normalise(vec);
719                         VecMulf(vec, paf->normfac);
720                         VecAddf(pa->no, pa->no, vec);
721                 }
722                 pa->lifetime= paf->lifetime;
723                 if(paf->randlife!=0.0) {
724                         pa->lifetime*= 1.0f+ (float)(paf->randlife*( BLI_drand() - 0.5));
725                 }
726                 pa->mat_nr= 1;
727                 
728                 make_particle_keys(0, a, paf, pa, force, deform, mtexmove);
729         }
730         
731         if(deform) end_latt_deform();
732                 
733         /* restore */
734         G.scene->r.cfra= cfraont;
735         G.scene->r.framelen= framelenont;
736         give_mesh_mvert(0, 0, 0, 0);
737
738
739         /* hele hiera terug */
740         par= ob;
741         while(par) {
742                 popfirst(par);
743                 /* geen ob->ipo doen: insertkey behouden */
744                 do_ob_key(par);
745                 par= par->parent;
746         }
747
748         /* restore: NA popfirst */
749         ob->sf= sfraont;
750
751         disable_speed_curve(0);
752
753         waitcursor(0);
754
755 }
756
757 /* ************* WAVE **************** */
758
759 void calc_wave_deform(WaveEff *wav, float ctime, float *co)
760 {
761         /* co is in lokale coords */
762         float lifefac, x, y, amplit;
763         
764         /* mag eigenlijk niet voorkomen */
765         if((wav->flag & (WAV_X+WAV_Y))==0) return;      
766
767         lifefac= wav->height;
768         
769         if( wav->lifetime!=0.0) {
770                 x= ctime - wav->timeoffs;
771                 if(x>wav->lifetime) {
772                         
773                         lifefac= x-wav->lifetime;
774                         
775                         if(lifefac > wav->damp) lifefac= 0.0;
776                         else lifefac= (float)(wav->height*(1.0 - sqrt(lifefac/wav->damp)));
777                 }
778         }
779         if(lifefac==0.0) return;
780
781         x= co[0]-wav->startx;
782         y= co[1]-wav->starty;
783
784         if(wav->flag & WAV_X) {
785                 if(wav->flag & WAV_Y) amplit= (float)sqrt( (x*x + y*y));
786                 else amplit= x;
787         }
788         else amplit= y;
789         
790         /* zo maaktie mooie cirkels */
791         amplit-= (ctime-wav->timeoffs)*wav->speed;
792
793         if(wav->flag & WAV_CYCL) {
794                 amplit = (float)fmod(amplit-wav->width, 2.0*wav->width) + wav->width;
795         }
796
797         /* GAUSSIAN */
798         
799         if(amplit> -wav->width && amplit<wav->width) {
800         
801                 amplit = amplit*wav->narrow;
802                 amplit= (float)(1.0/exp(amplit*amplit) - wav->minfac);
803
804                 co[2]+= lifefac*amplit;
805         }
806 }
807
808 void object_wave(Object *ob)
809 {
810         WaveEff *wav;
811         DispList *dl;
812         Mesh *me;
813         MVert *mvert;
814         float *fp, ctime;
815         int a, first;
816         
817         /* is er een mave */
818         wav= ob->effect.first;
819         while(wav) {
820                 if(wav->type==EFF_WAVE) break;
821                 wav= wav->next;
822         }
823         if(wav==0) return;
824         
825         if(ob->type==OB_MESH) {
826
827                 ctime= bsystem_time(ob, 0, (float)G.scene->r.cfra, 0.0);
828                 first= 1;
829                 
830                 me= ob->data;
831                 dl= find_displist_create(&ob->disp, DL_VERTS);
832
833                 if(dl->verts) MEM_freeN(dl->verts);
834                 dl->nr= me->totvert;
835                 dl->verts= MEM_mallocN(3*4*me->totvert, "wave");
836
837                 wav= ob->effect.first;
838                 while(wav) {
839                         if(wav->type==EFF_WAVE) {
840                                 
841                                 /* voorberekenen */
842                                 wav->minfac= (float)(1.0/exp(wav->width*wav->narrow*wav->width*wav->narrow));
843                                 if(wav->damp==0) wav->damp= 10.0f;
844                                 
845                                 mvert= me->mvert;
846                                 fp= dl->verts;
847                                 
848                                 for(a=0; a<me->totvert; a++, mvert++, fp+=3) {
849                                         if(first) VECCOPY(fp, mvert->co);
850                                         calc_wave_deform(wav, ctime, fp);
851                                 }
852                                 first= 0;
853                         }
854                         wav= wav->next;
855                 }
856         }
857 }