source: GTP/branches/IllumWPdeliver2008dec/IlluminationWP/demos/Standalone/Hierarchical Systems Demo [OpenGL]/RESOURCES/include/My3DGraphRes/ParticleSystem.cpp @ 3255

Revision 3255, 8.2 KB checked in by szirmay, 15 years ago (diff)
Line 
1#include ".\particlesystem.h"
2#include "includes.h"
3#include <GL/glext.h>
4#include <glh/glh_extensions.h>
5
6int CompareInc( const void *arg1, const void *arg2 )
7{
8        Particle* particle1=(Particle*) arg1;
9        Particle* particle2=(Particle*) arg2;
10
11        if(*particle1>*particle2)
12                return -1;
13        else
14                return 1;
15}
16
17int CompareDec( const void *arg1, const void *arg2 )
18{
19        Particle* particle1=(Particle*) arg1;
20        Particle* particle2=(Particle*) arg2;
21
22        if(*particle1>*particle2)
23                return 1;
24        else
25                return -1;
26}
27
28
29void ParticleSystem::SortParticles(bool increment)
30{
31        if(increment)
32                qsort( m_ParticleArray, (size_t)m_Count, sizeof(Particle), CompareInc );
33        else
34                qsort( m_ParticleArray, (size_t)m_Count, sizeof(Particle), CompareDec );
35}
36
37
38ParticleSystem::ParticleSystem(void)
39{
40        VertexBuffer=NULL;
41        TexcoordBuffer=NULL;
42        ColorBuffer=NULL;
43
44        m_LastParticle=NULL;
45        m_ParticleList=new Particle;
46
47        m_ParticleArray=NULL;
48
49        m_Count=0;
50        m_Quota=100;
51        m_Type=0;
52
53        m_UpVector=Vector(0,1,0);
54        m_RightVector=Vector(1,0,0);
55
56        m_refreshed=false;
57        m_refreshonce=false;
58
59        m_LittleSystemRadius=1.0;
60}
61
62ParticleSystem::~ParticleSystem(void)
63{
64}
65
66void ParticleSystem::RefreshParticles(unsigned int Dt,unsigned int TimefromSecond)
67{
68        if(!m_refreshed)
69        {
70                //Refresh particle ages, kill dead particles; refresh particle positions
71                Particle* thisParticle=m_ParticleList->m_NextParticle;
72                Particle* parentParticle=m_ParticleList;
73
74                while(thisParticle)
75                {
76                        if(thisParticle->LiveMore(Dt))
77                        {
78                                //refresh particle
79                                thisParticle->Refresh(Dt);
80                                //thisParticle->m_Distance=(thisParticle->getPosition()-m_CameraPosition).Length();
81                                m_LastParticle=thisParticle;
82                                parentParticle=thisParticle;
83                                thisParticle=thisParticle->m_NextParticle;
84                        }
85                        else
86                        {
87                                //kill particle
88                                parentParticle->m_NextParticle=thisParticle->m_NextParticle;
89                                delete thisParticle;
90                                thisParticle=parentParticle->m_NextParticle;
91                                m_LastParticle=parentParticle;
92                                m_Count--;
93                        }
94                       
95                }
96               
97                //Ask emitter to add new particles
98                Particle* Addto=m_LastParticle;
99                if(Addto==NULL)Addto=m_ParticleList;
100                unsigned int AddedCount=m_Emitter.Emit(TimefromSecond,m_Quota-m_Count,Addto,m_CameraPosition);
101                m_Count+=AddedCount;
102
103                //fill array ;update bounding radius
104                delete[] m_ParticleArray;
105                m_ParticleArray=new Particle[m_Count]; 
106               
107                //RefrBRadius_Dist();
108
109                       
110               
111        }
112}
113
114void ParticleSystem::RefrBRadius_Dist(bool refresh_rad)
115{
116        Particle* thisParticle=m_ParticleList->m_NextParticle;
117        if(refresh_rad||!m_refreshed)m_BoundingRadius=0;
118                double dist;
119                for(unsigned int i=0;i<m_Count;i++)
120                {
121                        thisParticle->m_Distance=(thisParticle->getPosition()-m_CameraPosition).Length();
122                        thisParticle->m_ID=i;
123                       
124                        double oldSize;
125                        if(refresh_rad||!m_refreshed)
126                        {
127                                if(m_refreshonce)
128                                m_refreshed=true;
129
130                                oldSize=thisParticle->getSize();
131                                thisParticle->setSize(oldSize*m_LittleSystemRadius);
132                                dist=thisParticle->getPosition().Length()+thisParticle->getSize();
133                                if(dist>m_BoundingRadius)
134                                        m_BoundingRadius=dist;
135                        }                                               
136                        m_ParticleArray[i]=*thisParticle;
137
138                        if(refresh_rad||!m_refreshed)thisParticle->setSize(oldSize);
139                        thisParticle=thisParticle->m_NextParticle;
140                }
141}
142
143void ParticleSystem::RefreshBuffer(bool billboard)
144{
145       
146        if(VertexBuffer!=NULL)delete VertexBuffer;
147        if(TexcoordBuffer!=NULL)delete TexcoordBuffer;
148        if(ColorBuffer!=NULL)delete ColorBuffer;
149
150        if(billboard)
151        {
152                double x,y,z;
153                Vector LeftDown=m_UpVector*-1-m_RightVector;
154                Vector RightDown=m_UpVector*-1+m_RightVector;
155                Vector RightUp=m_UpVector+m_RightVector;
156                Vector LeftUp=m_UpVector-m_RightVector;
157
158                VertexBuffer=new float[12*m_Count];
159                ColorBuffer=new float[16*m_Count];
160                TexcoordBuffer=new float[16*m_Count];
161
162                for(unsigned int i=0;i<m_Count;i++)
163                {
164                        m_ParticleArray[i].getPosition(x,y,z);
165                       
166                        float bbsize=2*m_ParticleArray[i].getSize();
167                        float t=m_ParticleArray[i].getSize()/m_BoundingRadius;
168                       
169                        TexcoordBuffer[i*16]=0;TexcoordBuffer[i*16+1]=0;
170                        TexcoordBuffer[i*16+2]=bbsize;TexcoordBuffer[i*16+3]=t;
171                        TexcoordBuffer[i*16+4]=1;TexcoordBuffer[i*16+5]=0;
172                        TexcoordBuffer[i*16+6]=bbsize;TexcoordBuffer[i*16+7]=t;
173                        TexcoordBuffer[i*16+8]=1;TexcoordBuffer[i*16+9]=1;
174                        TexcoordBuffer[i*16+10]=bbsize;TexcoordBuffer[i*16+11]=t;
175                        TexcoordBuffer[i*16+12]=0;TexcoordBuffer[i*16+13]=1;
176                        TexcoordBuffer[i*16+14]=bbsize;TexcoordBuffer[i*16+15]=t;
177
178                       
179                        ColorBuffer[i*16]=m_ParticleArray[i].m_Color.x;ColorBuffer[i*16+1]=m_ParticleArray[i].m_Color.y;
180                        ColorBuffer[i*16+2]=m_ParticleArray[i].m_Color.z;ColorBuffer[i*16+3]=m_ParticleArray[i].m_Color.w;
181                       
182                        ColorBuffer[i*16+4]=m_ParticleArray[i].m_Color.x;ColorBuffer[i*16+5]=m_ParticleArray[i].m_Color.y;
183                        ColorBuffer[i*16+6]=m_ParticleArray[i].m_Color.z;ColorBuffer[i*16+7]=m_ParticleArray[i].m_Color.w;
184                       
185                        ColorBuffer[i*16+8]=m_ParticleArray[i].m_Color.x;ColorBuffer[i*16+9]=m_ParticleArray[i].m_Color.y;
186                        ColorBuffer[i*16+10]=m_ParticleArray[i].m_Color.z;ColorBuffer[i*16+11]=m_ParticleArray[i].m_Color.w;
187                       
188                        ColorBuffer[i*16+12]=m_ParticleArray[i].m_Color.x;ColorBuffer[i*16+13]=m_ParticleArray[i].m_Color.y;
189                        ColorBuffer[i*16+14]=m_ParticleArray[i].m_Color.z;ColorBuffer[i*16+15]=m_ParticleArray[i].m_Color.w;
190
191                        VertexBuffer[i*12]=x+LeftDown.x*m_ParticleArray[i].getSize();
192                        VertexBuffer[i*12+1]=y+LeftDown.y*m_ParticleArray[i].getSize();
193                        VertexBuffer[i*12+2]=z+LeftDown.z*m_ParticleArray[i].getSize();
194                        VertexBuffer[i*12+3]=x+RightDown.x*m_ParticleArray[i].getSize();
195                        VertexBuffer[i*12+4]=y+RightDown.y*m_ParticleArray[i].getSize();
196                        VertexBuffer[i*12+5]=z+RightDown.z*m_ParticleArray[i].getSize();
197                        VertexBuffer[i*12+6]=x+RightUp.x*m_ParticleArray[i].getSize();
198                        VertexBuffer[i*12+7]=y+RightUp.y*m_ParticleArray[i].getSize();
199                        VertexBuffer[i*12+8]=z+RightUp.z*m_ParticleArray[i].getSize();
200                        VertexBuffer[i*12+9]=x+LeftUp.x*m_ParticleArray[i].getSize();
201                        VertexBuffer[i*12+10]=y+LeftUp.y*m_ParticleArray[i].getSize();
202                        VertexBuffer[i*12+11]=z+LeftUp.z*m_ParticleArray[i].getSize();         
203                       
204                }
205        }
206        else
207        {
208                double x,y,z;
209               
210                if(VertexBuffer==NULL)VertexBuffer=new float[3*m_Count];
211                if(ColorBuffer==NULL)ColorBuffer=new float[4*m_Count];
212                if(TexcoordBuffer==NULL)TexcoordBuffer=new float[m_Count*2];
213               
214                for(unsigned int i=0;i<m_Count;i++)
215                {
216                        m_ParticleArray[i].getPosition(x,y,z);
217                                                                       
218                        ColorBuffer[i*4]=m_ParticleArray[i].m_Color.y;
219                        ColorBuffer[4*i+1]=m_ParticleArray[i].m_Color.y;
220                        ColorBuffer[4*i+2]=m_ParticleArray[i].m_Color.z;
221                        ColorBuffer[4*i+3]=m_ParticleArray[i].m_Color.w;
222                                               
223                        VertexBuffer[i*3]=x;
224                        VertexBuffer[i*3+1]=y;
225                        VertexBuffer[i*3+2]=z; 
226
227                        TexcoordBuffer[2*i]=m_ParticleArray[i].m_ID;
228                        TexcoordBuffer[2*i+1]=m_ParticleArray[i].getSize();
229                       
230                }
231
232        }
233}
234
235void ParticleSystem::RenderAsPoints(bool sprites)
236{
237       
238        glEnableClientState(GL_VERTEX_ARRAY);
239        glEnableClientState(GL_TEXTURE_COORD_ARRAY);
240        glEnableClientState(GL_COLOR_ARRAY);
241                       
242        glVertexPointer (3, GL_FLOAT, 0, VertexBuffer);
243        glColorPointer(4,GL_FLOAT,0,ColorBuffer);
244        glTexCoordPointer(2,GL_FLOAT,0,TexcoordBuffer);
245       
246        if(sprites)
247        {
248          glEnable(GL_POINT_SPRITE_ARB);
249      glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE);
250      glEnable(GL_VERTEX_PROGRAM_POINT_SIZE_NV);
251     
252        }
253
254        glDrawArrays(GL_POINTS, 0, m_Count);
255
256        if(sprites)
257        {
258                glDisable(GL_POINT_SPRITE_ARB);
259                glDisable(GL_VERTEX_PROGRAM_POINT_SIZE_NV);
260                glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_FALSE);
261        }
262
263        glDisableClientState( GL_VERTEX_ARRAY );                                // Disable Vertex Arrays
264        glDisableClientState( GL_TEXTURE_COORD_ARRAY );
265        glDisableClientState( GL_COLOR_ARRAY );
266       
267}
268
269void ParticleSystem::RenderAsBillboard()
270{
271       
272        glEnableClientState(GL_VERTEX_ARRAY);
273        glEnableClientState(GL_TEXTURE_COORD_ARRAY);
274        glEnableClientState(GL_COLOR_ARRAY);
275                       
276        glVertexPointer (3, GL_FLOAT, 0, VertexBuffer);
277        glTexCoordPointer(4,GL_FLOAT,0,TexcoordBuffer);
278        glColorPointer(4,GL_FLOAT,0,ColorBuffer);
279       
280        glDrawArrays(GL_QUADS, 0, m_Count*4);
281
282        glDisableClientState( GL_VERTEX_ARRAY );                                // Disable Vertex Arrays
283        glDisableClientState( GL_TEXTURE_COORD_ARRAY );
284        glDisableClientState( GL_COLOR_ARRAY );
285
286       
287}
288
Note: See TracBrowser for help on using the repository browser.