File indexing completed on 2025-08-03 03:50:01

0001 /*
0002 * Copyright (c) 2006-2009 Erin Catto http://www.gphysics.com
0003 *
0004 * This software is provided 'as-is', without any express or implied
0005 * warranty.  In no event will the authors be held liable for any damages
0006 * arising from the use of this software.
0007 * Permission is granted to anyone to use this software for any purpose,
0008 * including commercial applications, and to alter it and redistribute it
0009 * freely, subject to the following restrictions:
0010 * 1. The origin of this software must not be misrepresented; you must not
0011 * claim that you wrote the original software. If you use this software
0012 * in a product, an acknowledgment in the product documentation would be
0013 * appreciated but is not required.
0014 * 2. Altered source versions must be plainly marked as such, and must not be
0015 * misrepresented as being the original software.
0016 * 3. This notice may not be removed or altered from any source distribution.
0017 */
0018 
0019 #ifndef B2_WORLD_H
0020 #define B2_WORLD_H
0021 
0022 #include <Box2D/Common/b2Math.h>
0023 #include <Box2D/Common/b2BlockAllocator.h>
0024 #include <Box2D/Common/b2StackAllocator.h>
0025 #include <Box2D/Dynamics/b2ContactManager.h>
0026 #include <Box2D/Dynamics/b2WorldCallbacks.h>
0027 
0028 struct b2AABB;
0029 struct b2BodyDef;
0030 struct b2JointDef;
0031 struct b2TimeStep;
0032 class b2Body;
0033 class b2Fixture;
0034 class b2Joint;
0035 
0036 /// The world class manages all physics entities, dynamic simulation,
0037 /// and asynchronous queries. The world also contains efficient memory
0038 /// management facilities.
0039 class b2World
0040 {
0041 public:
0042     /// Construct a world object.
0043     /// @param gravity the world gravity vector.
0044     /// @param doSleep improve performance by not simulating inactive bodies.
0045     b2World(const b2Vec2& gravity, bool doSleep);
0046 
0047     /// Destruct the world. All physics entities are destroyed and all heap memory is released.
0048     ~b2World();
0049 
0050     /// Register a destruction listener. The listener is owned by you and must
0051     /// remain in scope.
0052     void SetDestructionListener(b2DestructionListener* listener);
0053 
0054     /// Register a contact filter to provide specific control over collision.
0055     /// Otherwise the default filter is used (b2_defaultFilter). The listener is
0056     /// owned by you and must remain in scope. 
0057     void SetContactFilter(b2ContactFilter* filter);
0058 
0059     /// Register a contact event listener. The listener is owned by you and must
0060     /// remain in scope.
0061     void SetContactListener(b2ContactListener* listener);
0062 
0063     /// Register a routine for debug drawing. The debug draw functions are called
0064     /// inside with b2World::DrawDebugData method. The debug draw object is owned
0065     /// by you and must remain in scope.
0066     void SetDebugDraw(b2DebugDraw* debugDraw);
0067 
0068     /// Create a rigid body given a definition. No reference to the definition
0069     /// is retained.
0070     /// @warning This function is locked during callbacks.
0071     b2Body* CreateBody(const b2BodyDef* def);
0072 
0073     /// Destroy a rigid body given a definition. No reference to the definition
0074     /// is retained. This function is locked during callbacks.
0075     /// @warning This automatically deletes all associated shapes and joints.
0076     /// @warning This function is locked during callbacks.
0077     void DestroyBody(b2Body* body);
0078 
0079     /// Create a joint to constrain bodies together. No reference to the definition
0080     /// is retained. This may cause the connected bodies to cease colliding.
0081     /// @warning This function is locked during callbacks.
0082     b2Joint* CreateJoint(const b2JointDef* def);
0083 
0084     /// Destroy a joint. This may cause the connected bodies to begin colliding.
0085     /// @warning This function is locked during callbacks.
0086     void DestroyJoint(b2Joint* joint);
0087 
0088     /// Take a time step. This performs collision detection, integration,
0089     /// and constraint solution.
0090     /// @param timeStep the amount of time to simulate, this should not vary.
0091     /// @param velocityIterations for the velocity constraint solver.
0092     /// @param positionIterations for the position constraint solver.
0093     void Step(  qreal timeStep,
0094                 int32 velocityIterations,
0095                 int32 positionIterations);
0096 
0097     /// Manually clear the force buffer on all bodies. By default, forces are cleared automatically
0098     /// after each call to Step. The default behavior is modified by calling SetAutoClearForces.
0099     /// The purpose of this function is to support sub-stepping. Sub-stepping is often used to maintain
0100     /// a fixed sized time step under a variable frame-rate.
0101     /// When you perform sub-stepping you will disable auto clearing of forces and instead call
0102     /// ClearForces after all sub-steps are complete in one pass of your game loop.
0103     /// @see SetAutoClearForces
0104     void ClearForces();
0105 
0106     /// Call this to draw shapes and other debug draw data.
0107     void DrawDebugData();
0108 
0109     /// Query the world for all fixtures that potentially overlap the
0110     /// provided AABB.
0111     /// @param callback a user implemented callback class.
0112     /// @param aabb the query box.
0113     void QueryAABB(b2QueryCallback* callback, const b2AABB& aabb) const;
0114 
0115     /// Ray-cast the world for all fixtures in the path of the ray. Your callback
0116     /// controls whether you get the closest point, any point, or n-points.
0117     /// The ray-cast ignores shapes that contain the starting point.
0118     /// @param callback a user implemented callback class.
0119     /// @param point1 the ray starting point
0120     /// @param point2 the ray ending point
0121     void RayCast(b2RayCastCallback* callback, const b2Vec2& point1, const b2Vec2& point2) const;
0122 
0123     /// Get the world body list. With the returned body, use b2Body::GetNext to get
0124     /// the next body in the world list. A NULL body indicates the end of the list.
0125     /// @return the head of the world body list.
0126     b2Body* GetBodyList();
0127     const b2Body* GetBodyList() const;
0128 
0129     /// Get the world joint list. With the returned joint, use b2Joint::GetNext to get
0130     /// the next joint in the world list. A NULL joint indicates the end of the list.
0131     /// @return the head of the world joint list.
0132     b2Joint* GetJointList();
0133     const b2Joint* GetJointList() const;
0134 
0135     /// Get the world contact list. With the returned contact, use b2Contact::GetNext to get
0136     /// the next contact in the world list. A NULL contact indicates the end of the list.
0137     /// @return the head of the world contact list.
0138     /// @warning contacts are 
0139     b2Contact* GetContactList();
0140     const b2Contact* GetContactList() const;
0141 
0142     /// Enable/disable warm starting. For testing.
0143     void SetWarmStarting(bool flag) { m_warmStarting = flag; }
0144 
0145     /// Enable/disable continuous physics. For testing.
0146     void SetContinuousPhysics(bool flag) { m_continuousPhysics = flag; }
0147 
0148     /// Enable/disable single stepped continuous physics. For testing.
0149     void SetSubStepping(bool flag) { m_subStepping = flag; }
0150 
0151     /// Get the number of broad-phase proxies.
0152     int32 GetProxyCount() const;
0153 
0154     /// Get the number of bodies.
0155     int32 GetBodyCount() const;
0156 
0157     /// Get the number of joints.
0158     int32 GetJointCount() const;
0159 
0160     /// Get the number of contacts (each may have 0 or more contact points).
0161     int32 GetContactCount() const;
0162 
0163     /// Change the global gravity vector.
0164     void SetGravity(const b2Vec2& gravity);
0165     
0166     /// Get the global gravity vector.
0167     b2Vec2 GetGravity() const;
0168 
0169     /// Is the world locked (in the middle of a time step).
0170     bool IsLocked() const;
0171 
0172     /// Set flag to control automatic clearing of forces after each time step.
0173     void SetAutoClearForces(bool flag);
0174 
0175     /// Get the flag that controls automatic clearing of forces after each time step.
0176     bool GetAutoClearForces() const;
0177 
0178     /// Get the contact manager for testing.
0179     const b2ContactManager& GetContactManager() const;
0180 
0181 private:
0182 
0183     // m_flags
0184     enum
0185     {
0186         e_newFixture    = 0x0001,
0187         e_locked        = 0x0002,
0188         e_clearForces   = 0x0004
0189     };
0190 
0191     friend class b2Body;
0192     friend class b2ContactManager;
0193     friend class b2Controller;
0194 
0195     void Solve(const b2TimeStep& step);
0196     void SolveTOI(const b2TimeStep& step);
0197 
0198     void DrawJoint(b2Joint* joint);
0199     void DrawShape(b2Fixture* shape, const b2Transform& xf, const b2Color& color);
0200 
0201     b2BlockAllocator m_blockAllocator;
0202     b2StackAllocator m_stackAllocator;
0203 
0204     int32 m_flags;
0205 
0206     b2ContactManager m_contactManager;
0207 
0208     b2Body* m_bodyList;
0209     b2Joint* m_jointList;
0210 
0211     int32 m_bodyCount;
0212     int32 m_jointCount;
0213 
0214     b2Vec2 m_gravity;
0215     bool m_allowSleep;
0216 
0217     b2DestructionListener* m_destructionListener;
0218     b2DebugDraw* m_debugDraw;
0219 
0220     // This is used to compute the time step ratio to
0221     // support a variable time step.
0222     qreal m_inv_dt0;
0223 
0224     // These are for debugging the solver.
0225     bool m_warmStarting;
0226     bool m_continuousPhysics;
0227     bool m_subStepping;
0228 
0229     bool m_stepComplete;
0230 };
0231 
0232 inline b2Body* b2World::GetBodyList()
0233 {
0234     return m_bodyList;
0235 }
0236 
0237 inline const b2Body* b2World::GetBodyList() const
0238 {
0239     return m_bodyList;
0240 }
0241 
0242 inline b2Joint* b2World::GetJointList()
0243 {
0244     return m_jointList;
0245 }
0246 
0247 inline const b2Joint* b2World::GetJointList() const
0248 {
0249     return m_jointList;
0250 }
0251 
0252 inline b2Contact* b2World::GetContactList()
0253 {
0254     return m_contactManager.m_contactList;
0255 }
0256 
0257 inline const b2Contact* b2World::GetContactList() const
0258 {
0259     return m_contactManager.m_contactList;
0260 }
0261 
0262 inline int32 b2World::GetBodyCount() const
0263 {
0264     return m_bodyCount;
0265 }
0266 
0267 inline int32 b2World::GetJointCount() const
0268 {
0269     return m_jointCount;
0270 }
0271 
0272 inline int32 b2World::GetContactCount() const
0273 {
0274     return m_contactManager.m_contactCount;
0275 }
0276 
0277 inline void b2World::SetGravity(const b2Vec2& gravity)
0278 {
0279     m_gravity = gravity;
0280 }
0281 
0282 inline b2Vec2 b2World::GetGravity() const
0283 {
0284     return m_gravity;
0285 }
0286 
0287 inline bool b2World::IsLocked() const
0288 {
0289     return (m_flags & e_locked) == e_locked;
0290 }
0291 
0292 inline void b2World::SetAutoClearForces(bool flag)
0293 {
0294     if (flag)
0295     {
0296         m_flags |= e_clearForces;
0297     }
0298     else
0299     {
0300         m_flags &= ~e_clearForces;
0301     }
0302 }
0303 
0304 /// Get the flag that controls automatic clearing of forces after each time step.
0305 inline bool b2World::GetAutoClearForces() const
0306 {
0307     return (m_flags & e_clearForces) == e_clearForces;
0308 }
0309 
0310 inline const b2ContactManager& b2World::GetContactManager() const
0311 {
0312     return m_contactManager;
0313 }
0314 
0315 #endif