From 1432fb3408888ea442656a7aa737d0f2c1c6524c Mon Sep 17 00:00:00 2001 From: Darren Ranalli Date: Sat, 27 Jan 2001 02:22:36 +0000 Subject: [PATCH] *** empty log message *** --- .../particlesystem/lineParticleRenderer.cxx | 5 +- panda/src/particlesystem/particleSystem.I | 7 +- panda/src/particlesystem/particleSystem.cxx | 217 +++++++++++++++++- panda/src/particlesystem/particleSystem.h | 17 +- .../particlesystem/pointParticleRenderer.cxx | 4 +- .../sparkleParticleRenderer.cxx | 2 + .../particlesystem/spriteParticleRenderer.cxx | 2 + panda/src/physics/linearIntegrator.cxx | 2 +- panda/src/physics/linearRandomForce.cxx | 7 +- panda/src/testbed/test_particles.cxx | 6 +- 10 files changed, 240 insertions(+), 29 deletions(-) diff --git a/panda/src/particlesystem/lineParticleRenderer.cxx b/panda/src/particlesystem/lineParticleRenderer.cxx index b7064453ab..363dd2e568 100644 --- a/panda/src/particlesystem/lineParticleRenderer.cxx +++ b/panda/src/particlesystem/lineParticleRenderer.cxx @@ -145,7 +145,6 @@ render(vector< PT(PhysicsObject) >& po_vector, int ttl_particles) { int remaining_particles = ttl_particles; int i; - int num_lines_drawn = 0; Vertexf *cur_vert = &_vertex_array[0]; Colorf *cur_color = &_color_array[0]; @@ -207,14 +206,12 @@ render(vector< PT(PhysicsObject) >& po_vector, int ttl_particles) { *cur_color++ = head_color; *cur_color++ = tail_color; - num_lines_drawn++; - remaining_particles--; if (remaining_particles == 0) break; } - _line_primitive->set_num_prims(num_lines_drawn); + _line_primitive->set_num_prims(ttl_particles); // done filling geomline node, now do the bb stuff diff --git a/panda/src/particlesystem/particleSystem.I b/panda/src/particlesystem/particleSystem.I index fcdffeda33..197204cd94 100644 --- a/panda/src/particlesystem/particleSystem.I +++ b/panda/src/particlesystem/particleSystem.I @@ -27,8 +27,7 @@ render(void) { INLINE void ParticleSystem:: set_pool_size(int size) { - _particle_pool_size = size; - resize_pool(); + resize_pool(size); } //////////////////////////////////////////////////////////////////// @@ -95,9 +94,11 @@ set_emitter(BaseParticleEmitter *e) { INLINE void ParticleSystem:: set_factory(BaseParticleFactory *f) { + int pool_size = _particle_pool_size; + set_pool_size(0); _factory = f; clear_physics_objects(); - resize_pool(); + set_pool_size(pool_size); } //////////////////////////////////////////////////////////////////// diff --git a/panda/src/particlesystem/particleSystem.cxx b/panda/src/particlesystem/particleSystem.cxx index 7aa27b1ac4..38f0b72d7e 100644 --- a/panda/src/particlesystem/particleSystem.cxx +++ b/panda/src/particlesystem/particleSystem.cxx @@ -29,7 +29,7 @@ //////////////////////////////////////////////////////////////////// ParticleSystem:: ParticleSystem(int pool_size) : - Physical(pool_size, false), _particle_pool_size(pool_size) + Physical(pool_size, false) { _birth_rate = 0.5f; _tics_since_birth = _birth_rate; @@ -42,6 +42,7 @@ ParticleSystem(int pool_size) : _system_grows_older_flag = false; _system_lifespan = 0.0f; _i_was_spawned_flag = false; + _particle_pool_size = 0; // just in case someone tries to do something that requires the // use of an emitter, renderer, or factory before they've actually @@ -55,6 +56,8 @@ ParticleSystem(int pool_size) : set_emitter(new SphereSurfaceEmitter); set_renderer(new PointParticleRenderer); set_factory(new PointParticleFactory); + + set_pool_size(pool_size); } //////////////////////////////////////////////////////////////////// @@ -68,8 +71,6 @@ ParticleSystem(const ParticleSystem& copy) : _system_age(0.0f), _template_system_flag(false) { - - _particle_pool_size = copy._particle_pool_size; _birth_rate = copy._birth_rate; _litter_size = copy._litter_size; _litter_spread = copy._litter_spread; @@ -90,7 +91,7 @@ ParticleSystem(const ParticleSystem& copy) : _system_lifespan = copy._system_lifespan; _living_particles = 0; - resize_pool(); + set_pool_size(copy._particle_pool_size); } //////////////////////////////////////////////////////////////////// @@ -300,19 +301,20 @@ kill_particle(int pool_index) { //////////////////////////////////////////////////////////////////// // Function : resize_pool // Access : Private -// Description : Resizes the particle pool according to _particle_pool_size +// Description : Resizes the particle pool //////////////////////////////////////////////////////////////////// #ifdef PSDEBUG #define PARTICLE_SYSTEM_RESIZE_POOL_SENTRIES #endif void ParticleSystem:: -resize_pool(void) { +resize_pool(int size) { int i; - int delta = _particle_pool_size - _physics_objects.size(); + int delta = size - _particle_pool_size; + int po_delta = _particle_pool_size - _physics_objects.size(); #ifdef PARTICLE_SYSTEM_RESIZE_POOL_SENTRIES - cout << "resizing particle pool from " << _physics_objects.size() - << " to " << _particle_pool_size << endl; + cout << "resizing particle pool from " << _particle_pool_size + << " to " << size << endl; #endif if (_factory.is_null()) { @@ -327,6 +329,51 @@ resize_pool(void) { return; } + _particle_pool_size = size; + + // make sure the physics_objects array is OK + if (po_delta) { + if (po_delta > 0) { + for (i = 0; i < po_delta; i++) + { + int free_index = _physics_objects.size(); + + BaseParticle *new_particle = _factory->alloc_particle(); + if (new_particle) { + _factory->populate_particle(new_particle); + + _physics_objects.push_back(new_particle); + } else { +#ifdef PSDEBUG + cout << "Error allocating new particle" << endl; + _particle_pool_size--; +#endif + } + } + } else { +#ifdef PSDEBUG + cout << "physics_object array is too large??" << endl; + _particle_pool_size--; +#endif + po_delta = -po_delta; + for (i = 0; i < po_delta; i++) { + int delete_index = _physics_objects.size()-1; + BaseParticle *bp = (BaseParticle *) _physics_objects[delete_index].p(); + if (bp->get_alive()) { + kill_particle(delete_index); + _free_particle_fifo.pop_back(); + } else { + deque::iterator i; + i = find(_free_particle_fifo.begin(), _free_particle_fifo.end(), delete_index); + if (i != _free_particle_fifo.end()) { + _free_particle_fifo.erase(i); + } + } + _physics_objects.pop_back(); + } + } + } + // disregard no change if (delta == 0) return; @@ -414,6 +461,11 @@ update(float dt) { BaseParticle *bp; float age; +#ifdef PSSANITYCHECK + // check up on things + if (sanity_check()) return; +#endif + #ifdef PARTICLE_SYSTEM_UPDATE_SENTRIES cout << "UPDATE: pool size: " << _particle_pool_size << ", live particles: " << _living_particles << endl; @@ -472,3 +524,150 @@ update(float dt) { cout << "particle update complete" << endl; #endif } + +#ifdef PSSANITYCHECK +////////////////////////////////////////////////////////////////////// +// Function : sanity_check +// Access : Private +// Description : Checks consistency of live particle count, free +// particle list, etc. returns 0 if everything is normal +////////////////////////////////////////////////////////////////////// +#ifndef NDEBUG +#define PSSCVERBOSE +#endif + +class SC_valuenamepair : public ReferenceCount { +public: + int value; + char *name; + SC_valuenamepair(int v, char *s) : value(v), name(s) {} +}; + +// returns 0 if OK, # of errors if not OK +static int check_free_live_total_particles(vector live_counts, + vector dead_counts, vector total_counts, + int print_all = 0) { + + int val = 0; + int l, d, t; + + for(l = 0; l < live_counts.size(); l++) { + for(d = 0; d < dead_counts.size(); d++) { + for(t = 0; t < total_counts.size(); t++) { + int live = live_counts[l]->value; + int dead = dead_counts[d]->value; + int total = total_counts[t]->value; + if ((live + dead) != total) { +#ifdef PSSCVERBOSE + cout << "free/live/total count: " + << live_counts[l]->name << " (" << live << ") + " + << dead_counts[d]->name << " (" << dead << ") = " + << live + dead << ", != " + << total_counts[t]->name << " (" << total << ")" + << endl; +#endif + val++; + } + } + } + } + + return val; +} + +int ParticleSystem:: +sanity_check() { + int result = 0; + int i; + BaseParticle *bp; + int pool_size; + + /////////////////////////////////////////////////////////////////// + // check pool size + if (_particle_pool_size != _physics_objects.size()) { +#ifdef PSSCVERBOSE + cout << "_particle_pool_size (" << _particle_pool_size + << ") != particle array size (" << _physics_objects.size() << ")" << endl; +#endif + result++; + } + pool_size = min(_particle_pool_size, _physics_objects.size()); + /////////////////////////////////////////////////////////////////// + + /////////////////////////////////////////////////////////////////// + // find out how many particles are REALLY alive and dead + int real_live_particle_count = 0; + int real_dead_particle_count = 0; + + for (i = 0; i < _physics_objects.size(); i++) { + bp = (BaseParticle *) _physics_objects[i].p(); + if (true == bp->get_alive()) { + real_live_particle_count++; + } else { + real_dead_particle_count++; + } + } + + if (real_live_particle_count != _living_particles) { +#ifdef PSSCVERBOSE + cout << "manually counted live particle count (" << real_live_particle_count + << ") != _living_particles (" << _living_particles << ")" << endl; +#endif + result++; + } + + if (real_dead_particle_count != _free_particle_fifo.size()) { +#ifdef PSSCVERBOSE + cout << "manually counted dead particle count (" << real_dead_particle_count + << ") != free particle fifo size (" << _free_particle_fifo.size() << ")" << endl; +#endif + result++; + } + /////////////////////////////////////////////////////////////////// + + /////////////////////////////////////////////////////////////////// + // check the free particle pool + for (i = 0; i < _free_particle_fifo.size(); i++) { + int index = _free_particle_fifo[i]; + + // check that we're in bounds + if (index >= pool_size) { +#ifdef PSSCVERBOSE + cout << "index from free particle fifo (" << index + << ") is too large; pool size is " << pool_size << endl; +#endif + result++; + continue; + } + + // check that the particle is indeed dead + bp = (BaseParticle *) _physics_objects[index].p(); + if (true == bp->get_alive()) { +#ifdef PSSCVERBOSE + cout << "particle " << index << " in free fifo is not dead" << endl; +#endif + result++; + } + } + /////////////////////////////////////////////////////////////////// + + /////////////////////////////////////////////////////////////////// + // check the numbers of free particles, live particles, and total particles + vector live_counts; + vector dead_counts; + vector total_counts; + + live_counts.push_back(new SC_valuenamepair(real_live_particle_count, "real_live_particle_count")); + + dead_counts.push_back(new SC_valuenamepair(real_dead_particle_count, "real_dead_particle_count")); + dead_counts.push_back(new SC_valuenamepair(_free_particle_fifo.size(), "free particle fifo size")); + + total_counts.push_back(new SC_valuenamepair(_particle_pool_size, "_particle_pool_size")); + total_counts.push_back(new SC_valuenamepair(_physics_objects.size(), "actual particle pool size")); + + result += check_free_live_total_particles(live_counts, dead_counts, total_counts); + /////////////////////////////////////////////////////////////////// + + return result; +} +#endif diff --git a/panda/src/particlesystem/particleSystem.h b/panda/src/particlesystem/particleSystem.h index c95400ab09..dd9ae22e3b 100644 --- a/panda/src/particlesystem/particleSystem.h +++ b/panda/src/particlesystem/particleSystem.h @@ -7,6 +7,10 @@ //#define PSDEBUG #endif +#define PSSANITYCHECK + +#define DYNAMIC_POOL_RESIZING + #ifndef PARTICLESYSTEM_H #define PARTICLESYSTEM_H @@ -32,10 +36,19 @@ class ParticleSystemManager; //////////////////////////////////////////////////////////////////// class EXPCL_PANDAPHYSICS ParticleSystem : public Physical { private: + +#ifdef PSSANITYCHECK + int sanity_check(); +#endif + +#ifndef DYNAMIC_POOL_RESIZING + INLINE void set_pool_size(int size); +#endif + bool birth_particle(void); void kill_particle(int pool_index); void birth_litter(void); - void resize_pool(void); + void resize_pool(int size); deque< int > _free_particle_fifo; @@ -86,7 +99,9 @@ PUBLISHED: ~ParticleSystem(void); // access/queries +#ifdef DYNAMIC_POOL_RESIZING INLINE void set_pool_size(int size); +#endif INLINE void set_birth_rate(float new_br); INLINE void set_litter_size(int new_ls); INLINE void set_litter_spread(int new_ls); diff --git a/panda/src/particlesystem/pointParticleRenderer.cxx b/panda/src/particlesystem/pointParticleRenderer.cxx index f210239d2b..025a5c6328 100644 --- a/panda/src/particlesystem/pointParticleRenderer.cxx +++ b/panda/src/particlesystem/pointParticleRenderer.cxx @@ -18,7 +18,7 @@ PointParticleRenderer(ParticleRendererAlphaMode am, PointParticleBlendType bt, ParticleRendererBlendMethod bm, const Colorf& sc, const Colorf& ec) : - BaseParticleRenderer(am), + BaseParticleRenderer(am), _start_color(sc), _end_color(ec), _point_size(point_size), _blend_type(bt), _blend_method(bm) @@ -86,6 +86,8 @@ resize_pool(int new_size) { _point_primitive->set_coords(_vertex_array, G_PER_VERTEX); _point_primitive->set_colors(_color_array, G_PER_VERTEX); + + init_geoms(); } //////////////////////////////////////////////////////////////////// diff --git a/panda/src/particlesystem/sparkleParticleRenderer.cxx b/panda/src/particlesystem/sparkleParticleRenderer.cxx index a14a173249..675abc6265 100644 --- a/panda/src/particlesystem/sparkleParticleRenderer.cxx +++ b/panda/src/particlesystem/sparkleParticleRenderer.cxx @@ -119,6 +119,8 @@ resize_pool(int new_size) { _line_primitive->set_colors(_color_array, G_PER_VERTEX); _max_pool_size = new_size; + + init_geoms(); } //////////////////////////////////////////////////////////////////// diff --git a/panda/src/particlesystem/spriteParticleRenderer.cxx b/panda/src/particlesystem/spriteParticleRenderer.cxx index fd05fd2c1f..dfd5bedb66 100644 --- a/panda/src/particlesystem/spriteParticleRenderer.cxx +++ b/panda/src/particlesystem/spriteParticleRenderer.cxx @@ -125,6 +125,8 @@ resize_pool(int new_size) { _sprite_primitive->set_x_texel_ratio(_x_texel_array, _x_bind); _sprite_primitive->set_y_texel_ratio(_y_texel_array, _y_bind); _sprite_primitive->set_thetas(_theta_array, _theta_bind); + + init_geoms(); } //////////////////////////////////////////////////////////////////// diff --git a/panda/src/physics/linearIntegrator.cxx b/panda/src/physics/linearIntegrator.cxx index 4bd579da0e..c22f33084f 100644 --- a/panda/src/physics/linearIntegrator.cxx +++ b/panda/src/physics/linearIntegrator.cxx @@ -37,7 +37,7 @@ LinearIntegrator:: void LinearIntegrator:: integrate(Physical *physical, vector< PT(LinearForce) > &forces, float dt) { -/*// darren, 2000.10.06 +/* <-- darren, 2000.10.06 // cap dt so physics don't go flying off on lags if (dt > _max_linear_dt) dt = _max_linear_dt; diff --git a/panda/src/physics/linearRandomForce.cxx b/panda/src/physics/linearRandomForce.cxx index 7f46d9bd1c..6643304319 100644 --- a/panda/src/physics/linearRandomForce.cxx +++ b/panda/src/physics/linearRandomForce.cxx @@ -1,6 +1,6 @@ // Filename: LinearRandomForce.cxx // Created by: charles (19Jun00) -// +// //////////////////////////////////////////////////////////////////// #include "linearRandomForce.h" @@ -43,8 +43,5 @@ LinearRandomForce:: //////////////////////////////////////////////////////////////////// float LinearRandomForce:: bounded_rand(void) { - int val = rand() & 0x7fffffff; - float f_val = (float) val / (float) 0x7fffffff; - - return f_val; + return ((float)rand() / (float)RAND_MAX); } diff --git a/panda/src/testbed/test_particles.cxx b/panda/src/testbed/test_particles.cxx index 468b4efc01..111af1c38b 100644 --- a/panda/src/testbed/test_particles.cxx +++ b/panda/src/testbed/test_particles.cxx @@ -91,7 +91,7 @@ ///////////////////////////////////////////////// // particle factory params -#define PARTICLE_FACTORY_LIFESPAN_BASE 10.0f +#define PARTICLE_FACTORY_LIFESPAN_BASE 5.0f //#define PARTICLE_FACTORY_LIFESPAN_BASE 3.0f //#define PARTICLE_FACTORY_LIFESPAN_SPREAD 1.0f //#define PARTICLE_FACTORY_MASS_BASE 1.0f @@ -542,10 +542,6 @@ static void event_more_particles(CPT_Event) { static int index = 0; static int sizes[] = { - 999, - 1000, - 0, - 0, 10, 999, 998,