6b4b77881cc1869ffe86befb80942bc8b4217f27
[blender.git] / intern / elbeem / intern / controlparticles.h
1 /** \file elbeem/intern/controlparticles.h
2  *  \ingroup elbeem
3  */
4 // --------------------------------------------------------------------------
5 //
6 // El'Beem - the visual lattice boltzmann freesurface simulator
7 // All code distributed as part of El'Beem is covered by the version 2 of the 
8 // GNU General Public License. See the file COPYING for details.  
9 //
10 // Copyright 2008 Nils Thuerey , Richard Keiser, Mark Pauly, Ulrich Ruede
11 //
12 // control particle classes
13 //
14 // --------------------------------------------------------------------------
15
16 #ifndef CONTROLPARTICLES_H
17 #define CONTROLPARTICLES_H
18
19 #include "ntl_geometrymodel.h"
20
21 // indicator for LBM inclusion
22 //#ifndef LBMDIM
23
24 //#include <NxFoundation.h>
25 //#include <vector>
26 //class MultisphGUI;
27 //#define NORMALIZE(a) a.normalize()
28 //#define MAGNITUDE(a) a.magnitude()
29 //#define CROSS(a,b,c) a.cross(b,c)
30 //#define ABS(a) (a>0. ? (a) : -(a))
31 //#include "cpdefines.h"
32
33 //#else // LBMDIM
34
35 // use compatibility defines
36 //#define NORMALIZE(a) normalize(a)
37 //#define MAGNITUDE(a) norm(a)
38 //#define CROSS(a,b,c) a=cross(b,c)
39
40 //#endif // LBMDIM
41
42 #define MAGNITUDE(a) norm(a)
43
44 // math.h compatibility
45 #define CP_PI ((LbmFloat)3.14159265358979323846)
46
47 // project 2d test cases onto plane?
48 // if not, 3d distance is used for 2d sim as well
49 #define CP_PROJECT2D 1
50
51
52 // default init for mincpdist, ControlForces::maxDistance
53 #define CPF_MAXDINIT 10000.
54
55 // storage of influence for a fluid cell/particle in lbm/sph
56 class ControlForces
57 {
58 public:
59         ControlForces() { };
60         ~ControlForces() {};
61
62         // attraction force
63         LbmFloat weightAtt;
64         LbmVec forceAtt;
65         // velocity influence
66         LbmFloat weightVel;
67         LbmVec forceVel;
68         // maximal distance influence, 
69         // first is max. distance to first control particle
70         // second attraction strength
71         LbmFloat maxDistance;
72         LbmVec forceMaxd;
73
74         LbmFloat compAvWeight;
75         LbmVec compAv;
76
77         void resetForces() {
78                 weightAtt = weightVel = 0.;
79                 maxDistance = CPF_MAXDINIT;
80                 forceAtt = forceVel = forceMaxd = LbmVec(0.,0.,0.);
81                 compAvWeight=0.; compAv=LbmVec(0.);
82         };
83 };
84
85
86 // single control particle
87 class ControlParticle
88 {
89 public:
90         ControlParticle() { reset(); };
91         ~ControlParticle() {};
92
93         // control parameters
94         
95         // position
96         LbmVec pos;
97         // size (influences influence radius)
98         LbmFloat size;
99         // overall strength of influence
100         LbmFloat influence;
101         // rotation axis
102         LbmVec rotaxis;
103
104         // computed values
105
106         // velocity
107         LbmVec vel;
108         // computed density
109         LbmFloat density;
110         LbmFloat densityWeight;
111
112         LbmVec avgVel;
113         LbmVec avgVelAcc;
114         LbmFloat avgVelWeight;
115
116         // init all zero / defaults
117         void reset();
118 };
119
120
121 // container for a particle configuration at time t
122 class ControlParticleSet
123 {
124 public:
125
126         // time of particle set
127         LbmFloat time;
128         // particle positions
129         std::vector<ControlParticle> particles;
130
131 };
132
133
134 // container & management of control particles
135 class ControlParticles
136 {
137 public:
138         ControlParticles();
139         ~ControlParticles();
140
141         // reset datastructures for next influence step
142         // if motion object is given, particle 1 of second system is used for overall 
143         // position and speed offset
144         void prepareControl(LbmFloat simtime, LbmFloat dt, ControlParticles *motion);
145         // post control operations
146         void finishControl(std::vector<ControlForces> &forces, LbmFloat iatt, LbmFloat ivel, LbmFloat imaxd);
147         // recalculate 
148         void calculateKernelWeight();
149
150         // calculate forces at given position, and modify velocity
151         // according to timestep (from initControl)
152         void calculateCpInfluenceOpt (ControlParticle *cp, LbmVec fluidpos, LbmVec fluidvel, ControlForces *force, LbmFloat fillFactor);
153         void calculateMaxdForce      (ControlParticle *cp, LbmVec fluidpos, ControlForces *force);
154
155         // no. of particles
156         inline int getSize() { return (int)_particles.size(); }
157         int getTotalSize();
158         // get particle [i]
159         inline ControlParticle* getParticle(int i){ return &_particles[i]; }
160
161         // set influence parameters
162         void setInfluenceTangential(LbmFloat set) { _influenceTangential=set; }
163         void setInfluenceAttraction(LbmFloat set) { _influenceAttraction=set; }
164         void setInfluenceMaxdist(LbmFloat set)    { _influenceMaxdist=set; }
165         // calculate for delta t
166         void setInfluenceVelocity(LbmFloat set, LbmFloat dt);
167         // get influence parameters
168         inline LbmFloat getInfluenceAttraction()    { return _influenceAttraction; }
169         inline LbmFloat getInfluenceTangential()    { return _influenceTangential; }
170         inline LbmFloat getInfluenceVelocity()      { return _influenceVelocity; }
171         inline LbmFloat getInfluenceMaxdist()       { return _influenceMaxdist; }
172         inline LbmFloat getCurrTimestep()           { return _currTimestep; }
173
174         void setRadiusAtt(LbmFloat set)       { _radiusAtt=set; }
175         inline LbmFloat getRadiusAtt()        { return _radiusAtt; }
176         void setRadiusVel(LbmFloat set)       { _radiusVel=set; }
177         inline LbmFloat getRadiusVel()        { return _radiusVel; }
178         void setRadiusMaxd(LbmFloat set)      { _radiusMaxd=set; }
179         inline LbmFloat getRadiusMaxd()       { return _radiusMaxd; }
180         void setRadiusMinMaxd(LbmFloat set)   { _radiusMinMaxd=set; }
181         inline LbmFloat getRadiusMinMaxd()    { return _radiusMinMaxd; }
182
183         LbmFloat getControlTimStart();
184         LbmFloat getControlTimEnd();
185
186         // set/get characteristic length (and inverse)
187         void setCharLength(LbmFloat set)      { _charLength=set; _charLengthInv=1./_charLength; }
188         inline LbmFloat getCharLength()       { return _charLength;}
189         inline LbmFloat getCharLengthInv()    { return _charLengthInv;}
190
191         // set init parameters
192         void setInitTimeScale(LbmFloat set)  { _initTimeScale = set; };
193         void setInitMirror(string set)  { _initMirror = set; };
194         string getInitMirror()          { return _initMirror; };
195
196         void setLastOffset(LbmVec set) { _initLastPartOffset = set; };
197         void setLastScale(LbmVec set)  { _initLastPartScale = set; };
198         void setOffset(LbmVec set) { _initPartOffset = set; };
199         void setScale(LbmVec set)  { _initPartScale = set; };
200
201         // set/get cps params
202         void setCPSWith(LbmFloat set)       { mCPSWidth = set; };
203         void setCPSTimestep(LbmFloat set)   { mCPSTimestep = set; };
204         void setCPSTimeStart(LbmFloat set)  { mCPSTimeStart = set; };
205         void setCPSTimeEnd(LbmFloat set)    { mCPSTimeEnd = set; };
206         void setCPSMvmWeightFac(LbmFloat set) { mCPSWeightFac = set; };
207
208         LbmFloat getCPSWith()       { return mCPSWidth; };
209         LbmFloat getCPSTimestep()   { return mCPSTimestep; };
210         LbmFloat getCPSTimeStart()  { return mCPSTimeStart; };
211         LbmFloat getCPSTimeEnd()    { return mCPSTimeEnd; };
212         LbmFloat getCPSMvmWeightFac() { return mCPSWeightFac; };
213
214         void setDebugInit(int set)       { mDebugInit = set; };
215
216         // set init parameters
217         void setFluidSpacing(LbmFloat set)  { _fluidSpacing = set; };
218
219         // load positions & timing from text file
220         int initFromTextFile(string filename);
221         int initFromTextFileOld(string filename);
222         // load positions & timing from gzipped binary file
223         int initFromBinaryFile(string filename);
224         int initFromMVCMesh(string filename);
225         // init an example test case
226         int initExampleSet();
227
228         // init for a given time
229         void initTime(LbmFloat t, LbmFloat dt);
230
231         // blender test init
232         void initBlenderTest();
233         
234         int initFromObject(ntlGeometryObjModel *model);
235
236 protected:
237         // sets influence params
238         friend class MultisphGUI;
239
240         // tangential and attraction influence
241         LbmFloat _influenceTangential, _influenceAttraction;
242         // direct velocity influence
243         LbmFloat _influenceVelocity;
244         // maximal distance influence
245         LbmFloat _influenceMaxdist;
246
247         // influence radii
248         LbmFloat _radiusAtt, _radiusVel, _radiusMinMaxd, _radiusMaxd;
249
250         // currently valid time & timestep
251         LbmFloat _currTime, _currTimestep;
252         // all particles
253         std::vector<ControlParticle> _particles;
254
255         // particle sets
256         std::vector<ControlParticleSet> mPartSets;
257
258         // additional parameters for initing particles
259         LbmFloat _initTimeScale;
260         LbmVec _initPartOffset;
261         LbmVec _initPartScale;
262         LbmVec _initLastPartOffset;
263         LbmVec _initLastPartScale;
264         // mirror particles for loading?
265         string _initMirror;
266
267         // row spacing paramter, e.g. use for approximation of kernel area/volume
268         LbmFloat _fluidSpacing;
269         // save current kernel weight
270         LbmFloat _kernelWeight;
271         // charateristic length in world coordinates for normalizatioon of forces
272         LbmFloat _charLength, _charLengthInv;
273
274
275         /*! do ani mesh CPS */
276         void calculateCPS(string filename);
277         //! ani mesh cps params 
278         ntlVec3Gfx mvCPSStart, mvCPSEnd;
279         gfxReal mCPSWidth, mCPSTimestep;
280         gfxReal mCPSTimeStart, mCPSTimeEnd;
281         gfxReal mCPSWeightFac;
282
283         int mDebugInit;
284
285         
286 protected:
287         // apply init transformations
288         void applyTrafos();
289
290         // helper function for init -> swap components everywhere
291         void swapCoords(int a,int b);
292         // helper function for init -> mirror time
293         void mirrorTime();
294
295         // helper, init given array
296         void initTimeArray(LbmFloat t, std::vector<ControlParticle> &parts);
297
298         bool checkPointInside(ntlTree *tree, ntlVec3Gfx org, gfxReal &distance);
299 };
300
301
302
303 #endif
304