Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/orxonox/trunk/src/lib/particles/particle_engine.cc @ 4619

Last change on this file since 4619 was 4597, checked in by bensch, 19 years ago

orxonox/trunk: setClassID implemented in all files

File size: 10.4 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   ### File Specific:
12   main-programmer: ...
13   co-programmer: ...
14*/
15
16#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_PARTICLE
17
18#include "particle_engine.h"
19
20#include "particle_system.h"
21#include "particle_emitter.h"
22
23#include "list.h"
24#include "debug.h"
25#include "stdlibincl.h"
26
27using namespace std;
28
29/**
30   \brief standard constructor
31*/
32ParticleEngine::ParticleEngine ()
33{
34   this->setClassID(CL_PARTICLE_ENGINE, "ParticleEngine");
35   this->setName("ParticleEngine");
36
37   this->systemList = new tList<ParticleSystem>;
38   this->emitterList = new tList<ParticleEmitter>;
39   this->connectionList = new tList<ParticleConnection>;
40}
41
42/**
43   \brief the singleton reference to this class
44*/
45ParticleEngine* ParticleEngine::singletonRef = NULL;
46
47/**
48   \brief deletes all the system, emitters, connections and Lists
49*/
50ParticleEngine::~ParticleEngine ()
51{
52  // delete all remaining systems
53  tIterator<ParticleSystem>* sysIt = this->systemList->getIterator();
54  ParticleSystem* tmpSys = sysIt->nextElement();
55  while(tmpSys)
56    {
57      delete tmpSys;
58      tmpSys = sysIt->nextElement();
59    }
60  delete sysIt;
61  delete this->systemList;
62
63  // delete all remaining emitters
64  tIterator<ParticleEmitter>* emitIt = this->emitterList->getIterator();
65  ParticleEmitter* tmpEmit = emitIt->nextElement();
66  while(tmpEmit)
67    {
68      delete tmpEmit;
69      tmpEmit = emitIt->nextElement();
70    }
71  delete emitIt;
72  delete this->emitterList;
73
74  // there should be no more Connections
75  if (this->connectionList->getSize() == 0)
76    delete this->connectionList;
77  else
78    PRINTF(2)("The Connection List is not empty. This should not happen.\n");
79
80  ParticleEngine::singletonRef = NULL;
81}
82
83/**
84   \brief Adds a System to the System list.
85
86   this is done automatically when creating a ParticleSystem
87*/
88void ParticleEngine::addSystem(ParticleSystem* system)
89{
90  this->systemList->add(system);
91}
92
93/**
94   \brief Adds an emitter to the emitterList
95
96   this is done automatically when creating a ParticleEmitter
97*/
98void ParticleEngine::addEmitter(ParticleEmitter* emitter)
99{
100  this->emitterList->add(emitter);
101}
102
103/**
104   \brief Connects a ParticleSystem to a ParticleSystem thus emitting Particles.
105   \param emitter the Emitter to connect to the System
106   \param system the System to connect to the Emitter
107*/
108void ParticleEngine::addConnection(ParticleEmitter* emitter, ParticleSystem* system)
109{
110  // look, if we have already added this connection
111  tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
112  ParticleConnection* tmpConnection = tmpConIt->nextElement();
113  while(tmpConnection)
114    {
115      if (tmpConnection->emitter == emitter && tmpConnection->system == system)
116        {
117          PRINTF(2)("Connection between Emitter and System already added\n");
118          delete tmpConIt;
119          return;
120        }
121
122      tmpConnection = tmpConIt->nextElement();
123    }
124  delete tmpConIt;
125
126
127
128  ParticleConnection* tmpCon = new ParticleConnection;
129  tmpCon->emitter = emitter;
130  tmpCon->system = system;
131
132  this->connectionList->add(tmpCon);
133}
134
135/**
136   \brief Removes a system from the systemList and also removes all Connections to the System
137   \param system The ParticleSystem to delete
138*/
139bool ParticleEngine::removeSystem(ParticleSystem* system)
140{
141  // remove any connections, that have this system within
142  tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
143  ParticleConnection* tmpConnection = tmpConIt->nextElement();
144  while(tmpConnection)
145    {
146      if (tmpConnection->system == system)
147        this->breakConnection(tmpConnection);
148      tmpConnection = tmpConIt->nextElement();
149    }
150  delete tmpConIt;
151
152  // remove the System from the systemList.
153  this->systemList->remove(system);
154}
155
156/**
157   \brief removes an emitter from the emitterList and also from all Connections it is attached to.
158   \param emitter the ParticleEmitter to remove.
159*/
160bool ParticleEngine::removeEmitter(ParticleEmitter* emitter)
161{
162  // remove any connections, that have this emitter within
163  tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
164  ParticleConnection* tmpConnection = tmpConIt->nextElement();
165  while(tmpConnection)
166    {
167      if (tmpConnection->emitter == emitter)
168        this->breakConnection(tmpConnection);
169      tmpConnection = tmpConIt->nextElement();
170    }
171  delete tmpConIt;
172
173  // remove the emitter from the emitterList
174  this->emitterList->remove(emitter);
175}
176
177/**
178   \brief removes a Connection between an Emitter and a System
179   \param emitter The emitter of the connection to remove
180   \param system The system of the connection to remove
181   \returns true, if the connection was broken, false if the conntection was not found
182
183   only if both system and emitter are in the connection the Connection will be broken
184*/
185bool ParticleEngine::breakConnection(ParticleEmitter* emitter, ParticleSystem* system)
186{
187  // look, if we have already added this connection
188  tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
189  ParticleConnection* tmpConnection = tmpConIt->nextElement();
190  while(tmpConnection)
191    {
192    if (tmpConnection->emitter == emitter && tmpConnection->system == system)
193      {
194        this->breakConnection(tmpConnection);
195        delete tmpConIt;
196        return true;
197      }
198    tmpConnection = tmpConIt->nextElement();
199    }
200  delete tmpConIt;
201  return false;
202}
203
204/**
205   \brief removes a Connection between an Emitter and a System
206   \param connection the connection to remove
207
208   \see bool ParticleEngine::breakConnection(ParticleEmitter* emitter, ParticleSystem* system)
209*/
210bool ParticleEngine::breakConnection(ParticleConnection* connection)
211{
212  this->connectionList->remove(connection);
213  return true;
214}
215
216
217/**
218   \brief this function ticks all the ParticleSystems, so an animation will flow
219   \param dt passed since last tick
220*/
221void ParticleEngine::tick(float dt)
222{
223  // ticks all the ParticleSystems
224  tIterator<ParticleSystem>* tmpIt = systemList->getIterator();
225  ParticleSystem* tmpSys = tmpIt->nextElement();
226  while(tmpSys)
227    {
228      tmpSys->tick(dt);
229      tmpSys = tmpIt->nextElement();
230    }
231  delete tmpIt;
232
233  // add new Particles to each System connected to an Emitter.
234  tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
235  ParticleConnection* tmpConnection = tmpConIt->nextElement();
236  while(tmpConnection)
237    {
238      tmpConnection->emitter->tick(dt, tmpConnection->system);
239      tmpConnection = tmpConIt->nextElement();
240    }
241  delete tmpConIt;
242}
243
244/**
245   \brief draws all the systems and their Particles.
246*/
247void ParticleEngine::draw() const
248{
249  tIterator<ParticleSystem>* tmpIt = systemList->getIterator();
250  ParticleSystem* tmpSys = tmpIt->nextElement();
251  while(tmpSys)
252    {
253      tmpSys->draw();
254      tmpSys = tmpIt->nextElement();
255    }
256  delete tmpIt;
257
258}
259
260/**
261   \param systemName the name of the system to search for
262   \returns the system called by systemName or NULL if not found
263*/
264ParticleSystem* ParticleEngine::getSystemByName(const char* systemName) const
265{
266  tIterator<ParticleSystem>* tmpIt = systemList->getIterator();
267  ParticleSystem* tmpSys = tmpIt->nextElement();
268  while(tmpSys)
269    {
270      if (!strcmp(systemName, tmpSys->getName()))
271        {
272          delete tmpIt;
273          return tmpSys;
274        }
275      tmpSys = tmpIt->nextElement();
276    }
277  delete tmpIt;
278  return NULL;
279}
280
281/**
282   \param number the n-th system to return
283   \returns the system called by number or NULL if not found
284*/
285ParticleSystem* ParticleEngine::getSystemByNumber(unsigned int number) const
286{
287  int count = 0;
288  tIterator<ParticleSystem>* tmpIt = systemList->getIterator();
289  ParticleSystem* tmpSys = tmpIt->nextElement();
290  while(tmpSys)
291    {
292      count++;
293      if ( count == number)
294        {
295          delete tmpIt;
296          return tmpSys;
297        }
298      tmpSys = tmpIt->nextElement();
299    }
300  delete tmpIt;
301  return NULL;
302}
303
304/**
305   \param emitterName the name of the emitter to search for
306   \returns the emitter called by emitterName or NULL if not found
307*/
308ParticleEmitter* ParticleEngine::getEmitterByName(const char* emitterName) const
309{
310  tIterator<ParticleEmitter>* tmpIt = emitterList->getIterator();
311  ParticleEmitter* tmpEmit = tmpIt->nextElement();
312  while(tmpEmit)
313    {
314      if (!strcmp(emitterName, tmpEmit->getName()))
315        {
316          delete tmpIt;
317          return tmpEmit;
318        }
319      tmpEmit = tmpIt->nextElement();
320    }
321  delete tmpIt;
322  return NULL;
323}
324
325
326/**
327   \param number the n-th emitter to return
328   \returns the emitter called by number or NULL if not found
329*/
330ParticleEmitter* ParticleEngine::getEmitterByNumber(unsigned int number) const
331{
332  int count = 0;
333  tIterator<ParticleEmitter>* tmpIt = emitterList->getIterator();
334  ParticleEmitter* tmpEmit = tmpIt->nextElement();
335  while(tmpEmit)
336    {
337      count++;
338      if ( count == number)
339        {
340          delete tmpIt;
341          return tmpEmit;
342        }
343      tmpEmit = tmpIt->nextElement();
344    }
345  delete tmpIt;
346  return NULL;
347}
348
349/**
350   \brief outputs some nice debug information
351*/
352void ParticleEngine::debug(void)
353{
354  PRINT(0)("+-----------------------------------+\n");
355  PRINT(0)("+ PARTICLE-ENGINE DEBUG INFORMATION +\n");
356  PRINT(0)("+-----------------------------------+\n");
357  PRINT(0)(" Reference: %p\n", ParticleEngine::singletonRef);
358  PRINT(0)(" Count: Emitters: %d; Systems: %d, Connections: %d\n",
359            this->emitterList->getSize(), this->systemList->getSize(), this->connectionList->getSize());
360  if (this->connectionList->getSize() > 0)
361    {
362      PRINT(0)(" Connections:\n");
363      PRINT(0)(" -----------------------------------\n");
364
365      tIterator<ParticleConnection>* tmpConIt = connectionList->getIterator();
366      ParticleConnection* tmpConnection = tmpConIt->nextElement();
367      while(tmpConnection)
368        {
369          PRINT(0)(" Emitter '%s' emitts into System '%s'\n", tmpConnection->emitter->getName(), tmpConnection->system->getName());
370          tmpConnection = tmpConIt->nextElement();
371        }
372      delete tmpConIt;
373    }
374  if (this->systemList->getSize() > 0)
375    {
376      tIterator<ParticleSystem>* tmpIt = systemList->getIterator();
377      ParticleSystem* tmpSys = tmpIt->nextElement();
378      while(tmpSys)
379        {
380          tmpSys->debug();
381          tmpSys = tmpIt->nextElement();
382        }
383      delete tmpIt;
384    }
385
386  PRINT(0)("+--------------------------------PE-+\n");
387
388}
Note: See TracBrowser for help on using the repository browser.