Przeglądaj źródła

allow particle systems to be placed under an instance

David Rose 19 lat temu
rodzic
commit
d202b5e0e2

+ 10 - 0
panda/src/particlesystem/baseParticleRenderer.I

@@ -26,6 +26,16 @@ get_render_node() const {
   return _render_node;
 }
 
+////////////////////////////////////////////////////////////////////
+//    Function : BaseParticleRender::get_render_node_path
+//       Class : Published
+// Description : Query the geomnode pointer
+////////////////////////////////////////////////////////////////////
+INLINE NodePath BaseParticleRenderer::
+get_render_node_path() const {
+  return _render_node_path;
+}
+
 ////////////////////////////////////////////////////////////////////
 //    Function : BaseParticleRender::set_alpha_mode
 //      Access : Published

+ 3 - 1
panda/src/particlesystem/baseParticleRenderer.cxx

@@ -31,6 +31,7 @@ BaseParticleRenderer::
 BaseParticleRenderer(ParticleRendererAlphaMode alpha_mode) :
   _alpha_mode(PR_NOT_INITIALIZED_YET) {
   _render_node = new GeomNode("BaseParticleRenderer render node");
+  _render_node_path = NodePath(_render_node);
 
   _user_alpha = 1.0f;
   _ignore_scale = false;
@@ -47,6 +48,7 @@ BaseParticleRenderer::
 BaseParticleRenderer(const BaseParticleRenderer& copy) :
   _alpha_mode(PR_ALPHA_NONE) {
   _render_node = new GeomNode("BaseParticleRenderer render node");
+  _render_node_path = NodePath(_render_node);
 
   _user_alpha = copy._user_alpha;
   set_ignore_scale(copy._ignore_scale);
@@ -110,7 +112,7 @@ void BaseParticleRenderer::
 write(ostream &out, int indent) const {
   #ifndef NDEBUG //[
   out.width(indent); out<<""; out<<"BaseParticleRenderer:\n";
-  out.width(indent+2); out<<""; out<<"_render_node "<<_render_node<<"\n";
+  out.width(indent+2); out<<""; out<<"_render_node "<<_render_node_path<<"\n";
   out.width(indent+2); out<<""; out<<"_user_alpha "<<_user_alpha<<"\n";
   //ReferenceCount::write(out, indent+2);
   #endif //] NDEBUG

+ 3 - 1
panda/src/particlesystem/baseParticleRenderer.h

@@ -25,7 +25,7 @@
 #include "renderState.h"
 #include "geomNode.h"
 #include "colorBlendAttrib.h"
-
+#include "nodePath.h"
 #include "particleCommonFuncs.h"
 #include "baseParticle.h"
 
@@ -55,6 +55,7 @@ PUBLISHED:
   virtual ~BaseParticleRenderer();
 
   INLINE GeomNode *get_render_node() const;
+  INLINE NodePath get_render_node_path() const;
 
   INLINE void set_alpha_mode(ParticleRendererAlphaMode am);
   INLINE ParticleRendererAlphaMode get_alpha_mode() const;
@@ -92,6 +93,7 @@ protected:
 
 private:
   PT(GeomNode) _render_node;
+  NodePath _render_node_path;
 
   float _user_alpha;
   bool _ignore_scale;

+ 36 - 14
panda/src/particlesystem/particleSystem.I

@@ -156,11 +156,9 @@ set_renderer(BaseParticleRenderer *r) {
   _renderer = r;
   _renderer->resize_pool(_particle_pool_size);
 
-  if (!_render_node.is_null())
-    _render_parent->remove_child(_render_node);
-
-  _render_node = _renderer->get_render_node();
-  _render_parent->add_child(_render_node);
+  _render_node_path.remove_node();
+  _render_node_path = _renderer->get_render_node_path();
+  _render_node_path.reparent_to(_render_parent);
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -254,25 +252,40 @@ set_system_age(float age) {
 //    Function : set_spawn_render_node
 //      Access : public
 ////////////////////////////////////////////////////////////////////
-
 INLINE void ParticleSystem::
 set_spawn_render_node(PandaNode *node) {
-  _spawn_render_node = node;
+  set_spawn_render_node_path(NodePath(node));
 }
 
 ////////////////////////////////////////////////////////////////////
-//    Function : set_render_parent
+//    Function : set_spawn_render_node_path
 //      Access : public
 ////////////////////////////////////////////////////////////////////
+INLINE void ParticleSystem::
+set_spawn_render_node_path(const NodePath &node) {
+  _spawn_render_node_path = node;
+}
 
+////////////////////////////////////////////////////////////////////
+//    Function : set_render_parent
+//      Access : public
+////////////////////////////////////////////////////////////////////
 INLINE void ParticleSystem::
 set_render_parent(PandaNode *node) {
-  if (!_render_node.is_null())
-    _render_parent->remove_child(_render_node);
+  set_render_parent(NodePath(node));
+}
+
+////////////////////////////////////////////////////////////////////
+//    Function : set_render_parent
+//      Access : public
+////////////////////////////////////////////////////////////////////
+INLINE void ParticleSystem::
+set_render_parent(const NodePath &node) {
+  _render_node_path.remove_node();
 
   _render_parent = node;
-  _render_node = _renderer->get_render_node();
-  _render_parent->add_child(_render_node);
+  _render_node_path = _renderer->get_render_node_path();
+  _render_node_path.reparent_to(_render_parent);
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -476,14 +489,23 @@ get_i_was_spawned_flag() const {
 ////////////////////////////////////////////////////////////////////
 INLINE PandaNode *ParticleSystem::
 get_spawn_render_node() const {
-  return _spawn_render_node;
+  return _spawn_render_node_path.node();
+}
+
+////////////////////////////////////////////////////////////////////
+//    Function : get_spawn_render_node_path
+//      Access : public
+////////////////////////////////////////////////////////////////////
+INLINE NodePath ParticleSystem::
+get_spawn_render_node_path() const {
+  return _spawn_render_node_path;
 }
 
 ////////////////////////////////////////////////////////////////////
 //    Function : get_render_parent
 //      Access : public
 ////////////////////////////////////////////////////////////////////
-INLINE PandaNode *ParticleSystem::
+INLINE NodePath ParticleSystem::
 get_render_parent() const {
   return _render_parent;
 }

+ 16 - 20
panda/src/particlesystem/particleSystem.cxx

@@ -67,8 +67,8 @@ ParticleSystem(int pool_size) :
   // set_emitter(), etc...) forces them to set themselves up for the
   // system, keeping the pool sizes consistent.
 
-  _render_node.clear();
-  _render_parent = new PandaNode("ParticleSystem default render parent");
+  _render_node_path = NodePath();
+  _render_parent = NodePath("ParticleSystem default render parent");
 
   set_emitter(new SphereSurfaceEmitter);
 
@@ -106,8 +106,8 @@ ParticleSystem(const ParticleSystem& copy) :
   _factory = copy._factory;
 
   _render_parent = copy._render_parent;
-  _render_node = _renderer->get_render_node();
-  _render_parent->add_child(_render_node);
+  _render_node_path = _renderer->get_render_node_path();
+  _render_node_path.reparent_to(_render_parent);
 
   _tics_since_birth = 0.0;
   _system_lifespan = copy._system_lifespan;
@@ -127,9 +127,7 @@ ParticleSystem::
 
   if (!_template_system_flag) {
     _renderer.clear();
-
-    if (!_render_node.is_null())
-      _render_parent->remove_child(_render_node);
+    _render_node_path.remove_node();
   }
 }
 
@@ -176,14 +174,12 @@ birth_particle() {
   // get the location of the new particle.
   LPoint3f new_pos, world_pos;
   LVector3f new_vel;
-  GeomNode *render_node;
 
   _emitter->generate(new_pos, new_vel);
-  render_node = _renderer->get_render_node();
 
   // go from birth space to render space
-  NodePath physical_np(get_physical_node());
-  NodePath render_np(render_node);
+  NodePath physical_np = get_physical_node_path();
+  NodePath render_np = _renderer->get_render_node_path();
 
   CPT(TransformState) transform = physical_np.get_transform(render_np);
   const LMatrix4f &birth_to_render_xform = transform->get_mat();
@@ -252,7 +248,10 @@ spawn_child_system(BaseParticle *bp) {
     return;
   }
 
-  PandaNode *parent = this_pn->get_parent(0);
+  NodePath physical_np = get_physical_node_path();
+  NodePath parent_np = physical_np.get_parent();
+
+  PandaNode *parent = parent_np.node();
 
   // handle the spawn templates
   int new_ps_index = rand() % _spawn_templates.size();
@@ -263,9 +262,9 @@ spawn_child_system(BaseParticle *bp) {
   new_ps->_i_was_spawned_flag = true;
 
   // first, set up the render node info.
-  new_ps->_render_parent = _spawn_render_node;
-  new_ps->_render_node = new_ps->_renderer->get_render_node();
-  new_ps->_render_parent->add_child(new_ps->_render_node);
+  new_ps->_render_parent = _spawn_render_node_path;
+  new_ps->_render_node_path = new_ps->_renderer->get_render_node_path();
+  new_ps->_render_node_path.reparent_to(new_ps->_render_parent);
 
   // now set up the new system's PhysicalNode.
   PT(PhysicalNode) new_pn = new PhysicalNode("new_pn");
@@ -276,9 +275,6 @@ spawn_child_system(BaseParticle *bp) {
   // down to the new child.
   parent->add_child(new_pn);
 
-  NodePath parent_np(parent);
-  NodePath physical_np(get_physical_node());
-
   CPT(TransformState) transform = physical_np.get_transform(parent_np);
   const LMatrix4f &old_system_to_parent_xform = transform->get_mat();
 
@@ -769,12 +765,12 @@ write(ostream &out, int indent) const {
   out.width(indent+2); out<<""; out<<"_manager "<<_manager<<"\n";
   out.width(indent+2); out<<""; out<<"_template_system_flag "<<_template_system_flag<<"\n";
   out.width(indent+2); out<<""; out<<"_render_parent "<<_render_parent<<"\n";
-  out.width(indent+2); out<<""; out<<"_render_node "<<_render_node<<"\n";
+  out.width(indent+2); out<<""; out<<"_render_node "<<_render_node_path<<"\n";
   out.width(indent+2); out<<""; out<<"_active_system_flag "<<_active_system_flag<<"\n";
   out.width(indent+2); out<<""; out<<"_local_velocity_flag "<<_local_velocity_flag<<"\n";
   out.width(indent+2); out<<""; out<<"_system_grows_older_flag "<<_system_grows_older_flag<<"\n";
   out.width(indent+2); out<<""; out<<"_spawn_on_death_flag "<<_spawn_on_death_flag<<"\n";
-  out.width(indent+2); out<<""; out<<"_spawn_render_node "<<_spawn_render_node<<"\n";
+  out.width(indent+2); out<<""; out<<"_spawn_render_node "<<_spawn_render_node_path<<"\n";
   out.width(indent+2); out<<""; out<<"_i_was_spawned_flag "<<_i_was_spawned_flag<<"\n";
   write_free_particle_fifo(out, indent+2);
   write_spawn_templates(out, indent+2);

+ 7 - 4
panda/src/particlesystem/particleSystem.h

@@ -65,8 +65,10 @@ PUBLISHED:
   INLINE void set_active_system_flag(bool a);
   INLINE void set_spawn_on_death_flag(bool sod);
   INLINE void set_spawn_render_node(PandaNode *node);
+  INLINE void set_spawn_render_node_path(const NodePath &node);
   INLINE void set_template_system_flag(bool tsf);
   INLINE void set_render_parent(PandaNode *node);
+  INLINE void set_render_parent(const NodePath &node);
   INLINE void set_renderer(BaseParticleRenderer *r);
   INLINE void set_emitter(BaseParticleEmitter *e);
   INLINE void set_factory(BaseParticleFactory *f);
@@ -86,9 +88,10 @@ PUBLISHED:
   INLINE bool get_active_system_flag() const;
   INLINE bool get_spawn_on_death_flag() const;
   INLINE PandaNode *get_spawn_render_node() const;
+  INLINE NodePath get_spawn_render_node_path() const;
   INLINE bool get_i_was_spawned_flag() const;
   INLINE int get_living_particles() const;
-  INLINE PandaNode *get_render_parent() const;
+  INLINE NodePath get_render_parent() const;
   INLINE BaseParticleRenderer *get_renderer() const;
   INLINE BaseParticleEmitter *get_emitter() const;
   INLINE BaseParticleFactory *get_factory() const;
@@ -147,8 +150,8 @@ private:
   // _render_parent is the ALREADY ALLOC'D node under which this
   // system will render its particles.
 
-  PT(PandaNode) _render_parent;
-  PT(PandaNode) _render_node;
+  NodePath _render_parent;
+  NodePath _render_node_path;
 
   bool _active_system_flag;
   bool _local_velocity_flag;
@@ -157,7 +160,7 @@ private:
   // information for systems that will spawn
 
   bool _spawn_on_death_flag;
-  PT(PandaNode) _spawn_render_node;
+  NodePath _spawn_render_node_path;
   pvector< PT(ParticleSystem) > _spawn_templates;
 
   void spawn_child_system(BaseParticle *bp);

+ 9 - 0
panda/src/physics/baseForce.I

@@ -25,6 +25,15 @@ get_force_node() const {
   return _force_node;
 }
 
+////////////////////////////////////////////////////////////////////
+//    Function : get_force_node_path
+//      Access : Public
+////////////////////////////////////////////////////////////////////
+INLINE NodePath BaseForce::
+get_force_node_path() const {
+  return _force_node_path;
+}
+
 ////////////////////////////////////////////////////////////////////
 //    Function : set_active
 //      Access : Public

+ 16 - 15
panda/src/physics/baseForce.cxx

@@ -17,6 +17,7 @@
 ////////////////////////////////////////////////////////////////////
 
 #include "baseForce.h"
+#include "indent.h"
 
 TypeHandle BaseForce::_type_handle;
 
@@ -27,7 +28,9 @@ TypeHandle BaseForce::_type_handle;
 ////////////////////////////////////////////////////////////////////
 BaseForce::
 BaseForce(bool active) :
-  _force_node(NULL), _active(active) {
+  _force_node(NULL), 
+  _active(active) 
+{
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -37,7 +40,8 @@ BaseForce(bool active) :
 ////////////////////////////////////////////////////////////////////
 BaseForce::
 BaseForce(const BaseForce &copy) :
-  TypedReferenceCount(copy) {
+  TypedReferenceCount(copy) 
+{
   _active = copy._active;
   _force_node = (ForceNode *) NULL;
 }
@@ -59,9 +63,7 @@ BaseForce::
 ////////////////////////////////////////////////////////////////////
 void BaseForce::
 output(ostream &out) const {
-  #ifndef NDEBUG //[
-  out<<"BaseForce (id "<<this<<")";
-  #endif //] NDEBUG
+  out << "BaseForce (id " << this << ")";
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -71,19 +73,18 @@ output(ostream &out) const {
 //                <out>.
 ////////////////////////////////////////////////////////////////////
 void BaseForce::
-write(ostream &out, unsigned int indent) const {
-  #ifndef NDEBUG //[
-  out.width(indent); out<<""; out<<"BaseForce (id "<<this<<"):\n";
+write(ostream &out, int indent_level) const {
+  indent(out, indent_level)
+    << "BaseForce (id " << this << "):\n";
   
-  out.width(indent+2); out<<""; out<<"_force_node ";
+  indent(out, indent_level + 2)
+    << "_force_node ";
   if (_force_node) {
-    out<<_force_node<<"\n";
-    //_force_node->write(out, indent+4);
+    out << _force_node_path << "\n";
   } else {
-    out.width(indent+4); out<<""<<"null\n";
+    out << "null\n";
   }
   
-  out.width(indent+2); out<<""; out<<"_active "<<_active<<"\n";
-  //TypedReferenceCount::write(out);
-  #endif //] NDEBUG
+  indent(out, indent_level + 2)
+    << "_active " << _active << "\n";
 }

+ 4 - 1
panda/src/physics/baseForce.h

@@ -22,6 +22,7 @@
 #include "pandabase.h"
 #include "typedReferenceCount.h"
 #include "luse.h"
+#include "nodePath.h"
 
 #include "physicsObject.h"
 
@@ -41,9 +42,10 @@ PUBLISHED:
   virtual bool is_linear() const = 0;
 
   INLINE ForceNode *get_force_node() const;
+  INLINE NodePath get_force_node_path() const;
 
   virtual void output(ostream &out) const;
-  virtual void write(ostream &out, unsigned int indent=0) const;
+  virtual void write(ostream &out, int indent_level=0) const;
 
 protected:
   BaseForce(bool active = true);
@@ -51,6 +53,7 @@ protected:
 
 private:
   ForceNode *_force_node;
+  NodePath _force_node_path;
   bool _active;
 
 public:

+ 6 - 6
panda/src/physics/baseIntegrator.cxx

@@ -68,7 +68,7 @@ precompute_linear_matrices(Physical *physical,
   _precomputed_linear_matrices.reserve(
       global_force_vec_size + local_force_vec_size);
 
-  NodePath physical_np(physical_node);
+  NodePath physical_np(physical->get_physical_node_path());
   NodePath parent_physical_np = physical_np.get_parent();
 
   // tally the global xforms
@@ -78,7 +78,7 @@ precompute_linear_matrices(Physical *physical,
     force_node = (*fi)->get_force_node();
     nassertv(force_node != (ForceNode *) NULL);
 
-    NodePath force_np(force_node);
+    NodePath force_np = (*fi)->get_force_node_path();
     _precomputed_linear_matrices.push_back(
         force_np.get_transform(parent_physical_np)->get_mat());
   }
@@ -89,7 +89,7 @@ precompute_linear_matrices(Physical *physical,
     force_node = (*fi)->get_force_node();
     nassertv(force_node != (ForceNode *) NULL);
 
-    NodePath force_np(force_node);
+    NodePath force_np = (*fi)->get_force_node_path();
     _precomputed_linear_matrices.push_back(
         force_np.get_transform(parent_physical_np)->get_mat());
   }
@@ -124,7 +124,7 @@ precompute_angular_matrices(Physical *physical,
   _precomputed_angular_matrices.reserve(
       global_force_vec_size + local_force_vec_size);
 
-  NodePath physical_np(physical_node);
+  NodePath physical_np(physical->get_physical_node_path());
   NodePath parent_physical_np = physical_np.get_parent();
 
   // tally the global xforms
@@ -133,7 +133,7 @@ precompute_angular_matrices(Physical *physical,
     force_node = (*fi)->get_force_node();
     nassertv(force_node != (ForceNode *) NULL);
 
-    NodePath force_np(force_node);
+    NodePath force_np = (*fi)->get_force_node_path();
     _precomputed_angular_matrices.push_back(
         force_np.get_transform(parent_physical_np)->get_mat());
   }
@@ -144,7 +144,7 @@ precompute_angular_matrices(Physical *physical,
     force_node = (*fi)->get_force_node();
     nassertv(force_node != (ForceNode *) NULL);
 
-    NodePath force_np(force_node);
+    NodePath force_np = (*fi)->get_force_node_path();
     _precomputed_angular_matrices.push_back(
         force_np.get_transform(parent_physical_np)->get_mat());
   }

+ 1 - 0
panda/src/physics/forceNode.I

@@ -53,4 +53,5 @@ INLINE void ForceNode::
 add_force(BaseForce *force) {
   _forces.push_back(force);
   force->_force_node = this;
+  force->_force_node_path = NodePath(this);
 }

+ 3 - 0
panda/src/physics/forceNode.cxx

@@ -72,8 +72,10 @@ add_forces_from(const ForceNode &other) {
   _forces.insert(_forces.end(),
                  other._forces.begin(), other._forces.end());
 
+  NodePath node_path(this);
   for (; last != _forces.end(); last++) {
     (*last)->_force_node = this;
+    (*last)->_force_node_path = node_path;
   }
 }
 
@@ -104,6 +106,7 @@ remove_force(int index) {
   pvector< PT(BaseForce) >::iterator remove;
   remove = _forces.begin() + index;
   (*remove)->_force_node = (ForceNode *) NULL;
+  (*remove)->_force_node_path = NodePath();
 
   _forces.erase(remove);
 }

+ 9 - 0
panda/src/physics/physical.I

@@ -146,6 +146,15 @@ get_physical_node() const {
   return _physical_node;
 }
 
+////////////////////////////////////////////////////////////////////
+//    Function : get_physical_node_path
+//      Access : Public
+////////////////////////////////////////////////////////////////////
+INLINE NodePath Physical::
+get_physical_node_path() const {
+  return _physical_node_path;
+}
+
 ////////////////////////////////////////////////////////////////////
 //    Function : get_object_vector
 //      Access : Public

+ 3 - 0
panda/src/physics/physical.h

@@ -30,6 +30,7 @@
 #include "physicsObjectCollection.h"
 #include "linearForce.h"
 #include "angularForce.h"
+#include "nodePath.h"
 
 class PhysicalNode;
 class PhysicsManager;
@@ -55,6 +56,7 @@ PUBLISHED:
   // helpers
   INLINE PhysicsManager *get_physics_manager() const;
   INLINE PhysicalNode *get_physical_node() const;
+  INLINE NodePath get_physical_node_path() const;
   INLINE PhysicsObject *get_phys_body() const;
 
   INLINE void clear_linear_forces();
@@ -110,6 +112,7 @@ protected:
 private:
   PhysicsManager *_physics_manager;
   PhysicalNode *_physical_node;
+  NodePath _physical_node_path;
 
 public:
   static TypeHandle get_class_type() {

+ 1 - 0
panda/src/physics/physicalNode.I

@@ -53,4 +53,5 @@ INLINE void PhysicalNode::
 add_physical(Physical *physical) {
   _physicals.push_back(physical);
   physical->_physical_node = this;
+  physical->_physical_node_path = NodePath(this);
 }

+ 5 - 1
panda/src/physics/physicalNode.cxx

@@ -73,8 +73,11 @@ add_physicals_from(const PhysicalNode &other) {
   _physicals.insert(_physicals.end(),
                     other._physicals.begin(), other._physicals.end());
 
-  for (; last != _physicals.end(); last++)
+  NodePath node_path(this);
+  for (; last != _physicals.end(); last++) {
     (*last)->_physical_node = this;
+    (*last)->_physical_node_path = node_path;
+  }
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -104,6 +107,7 @@ remove_physical(int index) {
   pvector< PT(Physical) >::iterator remove;
   remove = _physicals.begin() + index;
   (*remove)->_physical_node = (PhysicalNode *) NULL;
+  (*remove)->_physical_node_path = NodePath();
 
   _physicals.erase(remove);
 }