physical.h

00001 // Filename: physical.h
00002 // Created by:  charles (14Jun00)
00003 //
00004 ////////////////////////////////////////////////////////////////////
00005 //
00006 // PANDA 3D SOFTWARE
00007 // Copyright (c) Carnegie Mellon University.  All rights reserved.
00008 //
00009 // All use of this software is subject to the terms of the revised BSD
00010 // license.  You should have received a copy of this license along
00011 // with this source code in a file named "LICENSE."
00012 //
00013 ////////////////////////////////////////////////////////////////////
00014 
00015 #ifndef PHYSICAL_H
00016 #define PHYSICAL_H
00017 
00018 #include "pandabase.h"
00019 #include "pointerTo.h"
00020 #include "typedReferenceCount.h"
00021 
00022 #include "pvector.h"
00023 #include "plist.h"
00024 
00025 #include "physicsObject.h"
00026 #include "physicsObjectCollection.h"
00027 #include "linearForce.h"
00028 #include "angularForce.h"
00029 #include "nodePath.h"
00030 
00031 class PhysicalNode;
00032 class PhysicsManager;
00033 
00034 ////////////////////////////////////////////////////////////////////
00035 //       Class : Physical
00036 // Description : Defines a set of physically modeled attributes.
00037 //               If you want physics applied to your class, derive
00038 //               it from this.
00039 ////////////////////////////////////////////////////////////////////
00040 class EXPCL_PANDAPHYSICS Physical : public TypedReferenceCount {
00041 public:
00042   //typedef pvector<PT(PhysicsObject)> PhysicsObjectVector;
00043   typedef pvector<PT(LinearForce)> LinearForceVector;
00044   typedef pvector<PT(AngularForce)> AngularForceVector;
00045 
00046 PUBLISHED:
00047   Physical(int total_objects = 1, bool pre_alloc = false);
00048   Physical(const Physical& copy);
00049 
00050   virtual ~Physical();
00051 
00052   // helpers
00053   INLINE PhysicsManager *get_physics_manager() const;
00054   INLINE PhysicalNode *get_physical_node() const;
00055   INLINE NodePath get_physical_node_path() const;
00056   INLINE PhysicsObject *get_phys_body() const;
00057 
00058   INLINE void clear_linear_forces();
00059   INLINE void clear_angular_forces();
00060   INLINE void clear_physics_objects();
00061   INLINE void add_linear_force(LinearForce *f);
00062   INLINE void add_angular_force(AngularForce *f);
00063   INLINE void add_physics_object(PhysicsObject *po);
00064   INLINE void remove_linear_force(LinearForce *f);
00065   INLINE void remove_angular_force(AngularForce *f);
00066 
00067   INLINE int get_num_linear_forces() const;
00068   INLINE PT(LinearForce) get_linear_force(int index) const;
00069   MAKE_SEQ(get_linear_forces, get_num_linear_forces, get_linear_force);
00070   INLINE int get_num_angular_forces() const;
00071   INLINE PT(AngularForce) get_angular_force(int index) const;
00072   MAKE_SEQ(get_angular_forces, get_num_angular_forces, get_angular_force);
00073 
00074   INLINE void set_viscosity(float viscosity);
00075   INLINE float get_viscosity() const;
00076   
00077   const PhysicsObjectCollection get_objects() const;
00078 
00079   virtual void output(ostream &out = cout) const;
00080   virtual void write_physics_objects(
00081     ostream &out = cout, unsigned int indent=0) const;
00082   virtual void write_linear_forces(
00083     ostream &out = cout, unsigned int indent=0) const;
00084   virtual void write_angular_forces(
00085     ostream &out = cout, unsigned int indent=0) const;
00086   virtual void write(ostream &out = cout, unsigned int indent=0) const;
00087 
00088 public:
00089   INLINE const PhysicsObject::Vector &get_object_vector() const;
00090   INLINE const LinearForceVector &get_linear_forces() const;
00091   INLINE const AngularForceVector &get_angular_forces() const;
00092 
00093   friend class PhysicsManager;
00094   friend class PhysicalNode;
00095 
00096 protected:
00097   float _viscosity;
00098   // containers
00099   PhysicsObject::Vector _physics_objects;
00100   LinearForceVector _linear_forces;
00101   AngularForceVector _angular_forces;
00102 
00103   // this pointer exists to make life easy.  If a physical exists
00104   // with only one element (i.e. NOT a particle system or set-physical),
00105   // then this pointer points at the only PhysicsObject.  The object
00106   // is still of course contained in the _physics_objects vector, but
00107   // this is kind of a quicker way there.
00108   PhysicsObject *_phys_body;
00109 
00110 private:
00111   PhysicsManager *_physics_manager;
00112   PhysicalNode *_physical_node;
00113   NodePath _physical_node_path;
00114 
00115 public:
00116   static TypeHandle get_class_type() {
00117     return _type_handle;
00118   }
00119   static void init_type() {
00120     TypedReferenceCount::init_type();
00121     register_type(_type_handle, "Physical",
00122                   TypedReferenceCount::get_class_type());
00123   }
00124   virtual TypeHandle get_type() const {
00125     return get_class_type();
00126   }
00127   virtual TypeHandle force_init_type() {init_type(); return get_class_type();}
00128 
00129 private:
00130   static TypeHandle _type_handle;
00131 };
00132 
00133 #include "physical.I"
00134 
00135 #endif // __PHYSICAL_H__