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

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_BODY_H
0020 #define B2_BODY_H
0021 
0022 #include <Box2D/Common/b2Math.h>
0023 #include <Box2D/Collision/Shapes/b2Shape.h>
0024 #include <memory>
0025 
0026 class b2Fixture;
0027 class b2Joint;
0028 class b2Contact;
0029 class b2World;
0030 struct b2FixtureDef;
0031 struct b2JointEdge;
0032 struct b2ContactEdge;
0033 
0034 /// The body type.
0035 /// static: zero mass, zero velocity, may be manually moved
0036 /// kinematic: zero mass, non-zero velocity set by user, moved by solver
0037 /// dynamic: positive mass, non-zero velocity determined by forces, moved by solver
0038 enum b2BodyType
0039 {
0040     b2_staticBody = 0,
0041     b2_kinematicBody,
0042     b2_dynamicBody
0043 
0044     // TODO_ERIN
0045     //b2_bulletBody,
0046 };
0047 
0048 /// A body definition holds all the data needed to construct a rigid body.
0049 /// You can safely re-use body definitions. Shapes are added to a body after construction.
0050 struct b2BodyDef
0051 {
0052     /// This constructor sets the body definition default values.
0053     b2BodyDef()
0054     {
0055         userData = NULL;
0056         position.Set(0.0f, 0.0f);
0057         angle = 0.0f;
0058         linearVelocity.Set(0.0f, 0.0f);
0059         angularVelocity = 0.0f;
0060         linearDamping = 0.0f;
0061         angularDamping = 0.0f;
0062         allowSleep = true;
0063         awake = true;
0064         fixedRotation = false;
0065         bullet = false;
0066         type = b2_staticBody;
0067         active = true;
0068         inertiaScale = 1.0f;
0069     }
0070 
0071     /// The body type: static, kinematic, or dynamic.
0072     /// Note: if a dynamic body would have zero mass, the mass is set to one.
0073     b2BodyType type;
0074 
0075     /// The world position of the body. Avoid creating bodies at the origin
0076     /// since this can lead to many overlapping shapes.
0077     b2Vec2 position;
0078 
0079     /// The world angle of the body in radians.
0080     qreal angle;
0081 
0082     /// The linear velocity of the body's origin in world co-ordinates.
0083     b2Vec2 linearVelocity;
0084 
0085     /// The angular velocity of the body.
0086     qreal angularVelocity;
0087 
0088     /// Linear damping is use to reduce the linear velocity. The damping parameter
0089     /// can be larger than 1.0f but the damping effect becomes sensitive to the
0090     /// time step when the damping parameter is large.
0091     qreal linearDamping;
0092 
0093     /// Angular damping is use to reduce the angular velocity. The damping parameter
0094     /// can be larger than 1.0f but the damping effect becomes sensitive to the
0095     /// time step when the damping parameter is large.
0096     qreal angularDamping;
0097 
0098     /// Set this flag to false if this body should never fall asleep. Note that
0099     /// this increases CPU usage.
0100     bool allowSleep;
0101 
0102     /// Is this body initially awake or sleeping?
0103     bool awake;
0104 
0105     /// Should this body be prevented from rotating? Useful for characters.
0106     bool fixedRotation;
0107 
0108     /// Is this a fast moving body that should be prevented from tunneling through
0109     /// other moving bodies? Note that all bodies are prevented from tunneling through
0110     /// kinematic and static bodies. This setting is only considered on dynamic bodies.
0111     /// @warning You should use this flag sparingly since it increases processing time.
0112     bool bullet;
0113 
0114     /// Does this body start out active?
0115     bool active;
0116 
0117     /// Use this to store application specific body data.
0118     void* userData;
0119 
0120     /// Experimental: scales the inertia tensor.
0121     qreal inertiaScale;
0122 };
0123 
0124 /// A rigid body. These are created via b2World::CreateBody.
0125 class b2Body
0126 {
0127 public:
0128     /// Creates a fixture and attach it to this body. Use this function if you need
0129     /// to set some fixture parameters, like friction. Otherwise you can create the
0130     /// fixture directly from a shape.
0131     /// If the density is non-zero, this function automatically updates the mass of the body.
0132     /// Contacts are not created until the next time step.
0133     /// @param def the fixture definition.
0134     /// @warning This function is locked during callbacks.
0135     b2Fixture* CreateFixture(const b2FixtureDef* def);
0136 
0137     /// Creates a fixture from a shape and attach it to this body.
0138     /// This is a convenience function. Use b2FixtureDef if you need to set parameters
0139     /// like friction, restitution, user data, or filtering.
0140     /// If the density is non-zero, this function automatically updates the mass of the body.
0141     /// @param shape the shape to be cloned.
0142     /// @param density the shape density (set to zero for static bodies).
0143     /// @warning This function is locked during callbacks.
0144     b2Fixture* CreateFixture(const b2Shape* shape, qreal density);
0145 
0146     /// Destroy a fixture. This removes the fixture from the broad-phase and
0147     /// destroys all contacts associated with this fixture. This will
0148     /// automatically adjust the mass of the body if the body is dynamic and the
0149     /// fixture has positive density.
0150     /// All fixtures attached to a body are implicitly destroyed when the body is destroyed.
0151     /// @param fixture the fixture to be removed.
0152     /// @warning This function is locked during callbacks.
0153     void DestroyFixture(b2Fixture* fixture);
0154 
0155     /// Set the position of the body's origin and rotation.
0156     /// This breaks any contacts and wakes the other bodies.
0157     /// Manipulating a body's transform may cause non-physical behavior.
0158     /// @param position the world position of the body's local origin.
0159     /// @param angle the world rotation in radians.
0160     void SetTransform(const b2Vec2& position, qreal angle);
0161 
0162     /// Get the body transform for the body's origin.
0163     /// @return the world transform of the body's origin.
0164     const b2Transform& GetTransform() const;
0165 
0166     /// Get the world body origin position.
0167     /// @return the world position of the body's origin.
0168     const b2Vec2& GetPosition() const;
0169 
0170     /// Get the angle in radians.
0171     /// @return the current world rotation angle in radians.
0172     qreal GetAngle() const;
0173 
0174     /// Get the world position of the center of mass.
0175     const b2Vec2& GetWorldCenter() const;
0176 
0177     /// Get the local position of the center of mass.
0178     const b2Vec2& GetLocalCenter() const;
0179 
0180     /// Set the linear velocity of the center of mass.
0181     /// @param v the new linear velocity of the center of mass.
0182     void SetLinearVelocity(const b2Vec2& v);
0183 
0184     /// Get the linear velocity of the center of mass.
0185     /// @return the linear velocity of the center of mass.
0186     b2Vec2 GetLinearVelocity() const;
0187 
0188     /// Set the angular velocity.
0189     /// @param omega the new angular velocity in radians/second.
0190     void SetAngularVelocity(qreal omega);
0191 
0192     /// Get the angular velocity.
0193     /// @return the angular velocity in radians/second.
0194     qreal GetAngularVelocity() const;
0195 
0196     /// Apply a force at a world point. If the force is not
0197     /// applied at the center of mass, it will generate a torque and
0198     /// affect the angular velocity. This wakes up the body.
0199     /// @param force the world force vector, usually in Newtons (N).
0200     /// @param point the world position of the point of application.
0201     void ApplyForce(const b2Vec2& force, const b2Vec2& point);
0202 
0203     /// Apply a torque. This affects the angular velocity
0204     /// without affecting the linear velocity of the center of mass.
0205     /// This wakes up the body.
0206     /// @param torque about the z-axis (out of the screen), usually in N-m.
0207     void ApplyTorque(qreal torque);
0208 
0209     /// Apply an impulse at a point. This immediately modifies the velocity.
0210     /// It also modifies the angular velocity if the point of application
0211     /// is not at the center of mass. This wakes up the body.
0212     /// @param impulse the world impulse vector, usually in N-seconds or kg-m/s.
0213     /// @param point the world position of the point of application.
0214     void ApplyLinearImpulse(const b2Vec2& impulse, const b2Vec2& point);
0215 
0216     /// Apply an angular impulse.
0217     /// @param impulse the angular impulse in units of kg*m*m/s
0218     void ApplyAngularImpulse(qreal impulse);
0219 
0220     /// Get the total mass of the body.
0221     /// @return the mass, usually in kilograms (kg).
0222     qreal GetMass() const;
0223 
0224     /// Get the rotational inertia of the body about the local origin.
0225     /// @return the rotational inertia, usually in kg-m^2.
0226     qreal GetInertia() const;
0227 
0228     /// Get the mass data of the body.
0229     /// @return a struct containing the mass, inertia and center of the body.
0230     void GetMassData(b2MassData* data) const;
0231 
0232     /// Set the mass properties to override the mass properties of the fixtures.
0233     /// Note that this changes the center of mass position.
0234     /// Note that creating or destroying fixtures can also alter the mass.
0235     /// This function has no effect if the body isn't dynamic.
0236     /// @param massData the mass properties.
0237     void SetMassData(const b2MassData* data);
0238 
0239     /// This resets the mass properties to the sum of the mass properties of the fixtures.
0240     /// This normally does not need to be called unless you called SetMassData to override
0241     /// the mass and you later want to reset the mass.
0242     void ResetMassData();
0243 
0244     /// Get the world coordinates of a point given the local coordinates.
0245     /// @param localPoint a point on the body measured relative the the body's origin.
0246     /// @return the same point expressed in world coordinates.
0247     b2Vec2 GetWorldPoint(const b2Vec2& localPoint) const;
0248 
0249     /// Get the world coordinates of a vector given the local coordinates.
0250     /// @param localVector a vector fixed in the body.
0251     /// @return the same vector expressed in world coordinates.
0252     b2Vec2 GetWorldVector(const b2Vec2& localVector) const;
0253 
0254     /// Gets a local point relative to the body's origin given a world point.
0255     /// @param a point in world coordinates.
0256     /// @return the corresponding local point relative to the body's origin.
0257     b2Vec2 GetLocalPoint(const b2Vec2& worldPoint) const;
0258 
0259     /// Gets a local vector given a world vector.
0260     /// @param a vector in world coordinates.
0261     /// @return the corresponding local vector.
0262     b2Vec2 GetLocalVector(const b2Vec2& worldVector) const;
0263 
0264     /// Get the world linear velocity of a world point attached to this body.
0265     /// @param a point in world coordinates.
0266     /// @return the world velocity of a point.
0267     b2Vec2 GetLinearVelocityFromWorldPoint(const b2Vec2& worldPoint) const;
0268 
0269     /// Get the world velocity of a local point.
0270     /// @param a point in local coordinates.
0271     /// @return the world velocity of a point.
0272     b2Vec2 GetLinearVelocityFromLocalPoint(const b2Vec2& localPoint) const;
0273 
0274     /// Get the linear damping of the body.
0275     qreal GetLinearDamping() const;
0276 
0277     /// Set the linear damping of the body.
0278     void SetLinearDamping(qreal linearDamping);
0279 
0280     /// Get the angular damping of the body.
0281     qreal GetAngularDamping() const;
0282 
0283     /// Set the angular damping of the body.
0284     void SetAngularDamping(qreal angularDamping);
0285 
0286     /// Set the type of this body. This may alter the mass and velocity.
0287     void SetType(b2BodyType type);
0288 
0289     /// Get the type of this body.
0290     b2BodyType GetType() const;
0291 
0292     /// Should this body be treated like a bullet for continuous collision detection?
0293     void SetBullet(bool flag);
0294 
0295     /// Is this body treated like a bullet for continuous collision detection?
0296     bool IsBullet() const;
0297 
0298     /// You can disable sleeping on this body. If you disable sleeping, the
0299     /// body will be woken.
0300     void SetSleepingAllowed(bool flag);
0301 
0302     /// Is this body allowed to sleep
0303     bool IsSleepingAllowed() const;
0304 
0305     /// Set the sleep state of the body. A sleeping body has very
0306     /// low CPU cost.
0307     /// @param flag set to true to put body to sleep, false to wake it.
0308     void SetAwake(bool flag);
0309 
0310     /// Get the sleeping state of this body.
0311     /// @return true if the body is sleeping.
0312     bool IsAwake() const;
0313 
0314     /// Set the active state of the body. An inactive body is not
0315     /// simulated and cannot be collided with or woken up.
0316     /// If you pass a flag of true, all fixtures will be added to the
0317     /// broad-phase.
0318     /// If you pass a flag of false, all fixtures will be removed from
0319     /// the broad-phase and all contacts will be destroyed.
0320     /// Fixtures and joints are otherwise unaffected. You may continue
0321     /// to create/destroy fixtures and joints on inactive bodies.
0322     /// Fixtures on an inactive body are implicitly inactive and will
0323     /// not participate in collisions, ray-casts, or queries.
0324     /// Joints connected to an inactive body are implicitly inactive.
0325     /// An inactive body is still owned by a b2World object and remains
0326     /// in the body list.
0327     void SetActive(bool flag);
0328 
0329     /// Get the active state of the body.
0330     bool IsActive() const;
0331 
0332     /// Set this body to have fixed rotation. This causes the mass
0333     /// to be reset.
0334     void SetFixedRotation(bool flag);
0335 
0336     /// Does this body have fixed rotation?
0337     bool IsFixedRotation() const;
0338 
0339     /// Get the list of all fixtures attached to this body.
0340     b2Fixture* GetFixtureList();
0341     const b2Fixture* GetFixtureList() const;
0342 
0343     /// Get the list of all joints attached to this body.
0344     b2JointEdge* GetJointList();
0345     const b2JointEdge* GetJointList() const;
0346 
0347     /// Get the list of all contacts attached to this body.
0348     /// @warning this list changes during the time step and you may
0349     /// miss some collisions if you don't use b2ContactListener.
0350     b2ContactEdge* GetContactList();
0351     const b2ContactEdge* GetContactList() const;
0352 
0353     /// Get the next body in the world's body list.
0354     b2Body* GetNext();
0355     const b2Body* GetNext() const;
0356 
0357     /// Get the user data pointer that was provided in the body definition.
0358     void* GetUserData() const;
0359 
0360     /// Set the user data. Use this to store your application specific data.
0361     void SetUserData(void* data);
0362 
0363     /// Get the parent world of this body.
0364     b2World* GetWorld();
0365     const b2World* GetWorld() const;
0366 
0367 private:
0368 
0369     friend class b2World;
0370     friend class b2Island;
0371     friend class b2ContactManager;
0372     friend class b2ContactSolver;
0373     
0374     friend class b2DistanceJoint;
0375     friend class b2GearJoint;
0376     friend class b2LineJoint;
0377     friend class b2MouseJoint;
0378     friend class b2PrismaticJoint;
0379     friend class b2PulleyJoint;
0380     friend class b2RevoluteJoint;
0381     friend class b2WeldJoint;
0382     friend class b2FrictionJoint;
0383     friend class b2RopeJoint;
0384 
0385     // m_flags
0386     enum
0387     {
0388         e_islandFlag        = 0x0001,
0389         e_awakeFlag         = 0x0002,
0390         e_autoSleepFlag     = 0x0004,
0391         e_bulletFlag        = 0x0008,
0392         e_fixedRotationFlag = 0x0010,
0393         e_activeFlag        = 0x0020,
0394         e_toiFlag           = 0x0040
0395     };
0396 
0397     b2Body(const b2BodyDef* bd, b2World* world);
0398     ~b2Body();
0399 
0400     void SynchronizeFixtures();
0401     void SynchronizeTransform();
0402 
0403     // This is used to prevent connected bodies from colliding.
0404     // It may lie, depending on the collideConnected flag.
0405     bool ShouldCollide(const b2Body* other) const;
0406 
0407     void Advance(qreal t);
0408 
0409     b2BodyType m_type;
0410 
0411     uint16 m_flags;
0412 
0413     int32 m_islandIndex;
0414 
0415     b2Transform m_xf;       // the body origin transform
0416     b2Sweep m_sweep;        // the swept motion for CCD
0417 
0418     b2Vec2 m_linearVelocity;
0419     qreal m_angularVelocity;
0420 
0421     b2Vec2 m_force;
0422     qreal m_torque;
0423 
0424     b2World* m_world;
0425     b2Body* m_prev;
0426     b2Body* m_next;
0427 
0428     b2Fixture* m_fixtureList;
0429     int32 m_fixtureCount;
0430 
0431     b2JointEdge* m_jointList;
0432     b2ContactEdge* m_contactList;
0433 
0434     qreal m_mass, m_invMass;
0435 
0436     // Rotational inertia about the center of mass.
0437     qreal m_I, m_invI;
0438 
0439     qreal m_linearDamping;
0440     qreal m_angularDamping;
0441 
0442     qreal m_sleepTime;
0443 
0444     void* m_userData;
0445 };
0446 
0447 inline b2BodyType b2Body::GetType() const
0448 {
0449     return m_type;
0450 }
0451 
0452 inline const b2Transform& b2Body::GetTransform() const
0453 {
0454     return m_xf;
0455 }
0456 
0457 inline const b2Vec2& b2Body::GetPosition() const
0458 {
0459     return m_xf.position;
0460 }
0461 
0462 inline qreal b2Body::GetAngle() const
0463 {
0464     return m_sweep.a;
0465 }
0466 
0467 inline const b2Vec2& b2Body::GetWorldCenter() const
0468 {
0469     return m_sweep.c;
0470 }
0471 
0472 inline const b2Vec2& b2Body::GetLocalCenter() const
0473 {
0474     return m_sweep.localCenter;
0475 }
0476 
0477 inline void b2Body::SetLinearVelocity(const b2Vec2& v)
0478 {
0479     if (m_type == b2_staticBody)
0480     {
0481         return;
0482     }
0483 
0484     if (b2Dot(v,v) > 0.0f)
0485     {
0486         SetAwake(true);
0487     }
0488 
0489     m_linearVelocity = v;
0490 }
0491 
0492 inline b2Vec2 b2Body::GetLinearVelocity() const
0493 {
0494     return m_linearVelocity;
0495 }
0496 
0497 inline void b2Body::SetAngularVelocity(qreal w)
0498 {
0499     if (m_type == b2_staticBody)
0500     {
0501         return;
0502     }
0503 
0504     if (w * w > 0.0f)
0505     {
0506         SetAwake(true);
0507     }
0508 
0509     m_angularVelocity = w;
0510 }
0511 
0512 inline qreal b2Body::GetAngularVelocity() const
0513 {
0514     return m_angularVelocity;
0515 }
0516 
0517 inline qreal b2Body::GetMass() const
0518 {
0519     return m_mass;
0520 }
0521 
0522 inline qreal b2Body::GetInertia() const
0523 {
0524     return m_I + m_mass * b2Dot(m_sweep.localCenter, m_sweep.localCenter);
0525 }
0526 
0527 inline void b2Body::GetMassData(b2MassData* data) const
0528 {
0529     data->mass = m_mass;
0530     data->I = m_I + m_mass * b2Dot(m_sweep.localCenter, m_sweep.localCenter);
0531     data->center = m_sweep.localCenter;
0532 }
0533 
0534 inline b2Vec2 b2Body::GetWorldPoint(const b2Vec2& localPoint) const
0535 {
0536     return b2Mul(m_xf, localPoint);
0537 }
0538 
0539 inline b2Vec2 b2Body::GetWorldVector(const b2Vec2& localVector) const
0540 {
0541     return b2Mul(m_xf.R, localVector);
0542 }
0543 
0544 inline b2Vec2 b2Body::GetLocalPoint(const b2Vec2& worldPoint) const
0545 {
0546     return b2MulT(m_xf, worldPoint);
0547 }
0548 
0549 inline b2Vec2 b2Body::GetLocalVector(const b2Vec2& worldVector) const
0550 {
0551     return b2MulT(m_xf.R, worldVector);
0552 }
0553 
0554 inline b2Vec2 b2Body::GetLinearVelocityFromWorldPoint(const b2Vec2& worldPoint) const
0555 {
0556     return m_linearVelocity + b2Cross(m_angularVelocity, worldPoint - m_sweep.c);
0557 }
0558 
0559 inline b2Vec2 b2Body::GetLinearVelocityFromLocalPoint(const b2Vec2& localPoint) const
0560 {
0561     return GetLinearVelocityFromWorldPoint(GetWorldPoint(localPoint));
0562 }
0563 
0564 inline qreal b2Body::GetLinearDamping() const
0565 {
0566     return m_linearDamping;
0567 }
0568 
0569 inline void b2Body::SetLinearDamping(qreal linearDamping)
0570 {
0571     m_linearDamping = linearDamping;
0572 }
0573 
0574 inline qreal b2Body::GetAngularDamping() const
0575 {
0576     return m_angularDamping;
0577 }
0578 
0579 inline void b2Body::SetAngularDamping(qreal angularDamping)
0580 {
0581     m_angularDamping = angularDamping;
0582 }
0583 
0584 inline void b2Body::SetBullet(bool flag)
0585 {
0586     if (flag)
0587     {
0588         m_flags |= e_bulletFlag;
0589     }
0590     else
0591     {
0592         m_flags &= ~e_bulletFlag;
0593     }
0594 }
0595 
0596 inline bool b2Body::IsBullet() const
0597 {
0598     return (m_flags & e_bulletFlag) == e_bulletFlag;
0599 }
0600 
0601 inline void b2Body::SetAwake(bool flag)
0602 {
0603     if (flag)
0604     {
0605         if ((m_flags & e_awakeFlag) == 0)
0606         {
0607             m_flags |= e_awakeFlag;
0608             m_sleepTime = 0.0f;
0609         }
0610     }
0611     else
0612     {
0613         m_flags &= ~e_awakeFlag;
0614         m_sleepTime = 0.0f;
0615         m_linearVelocity.SetZero();
0616         m_angularVelocity = 0.0f;
0617         m_force.SetZero();
0618         m_torque = 0.0f;
0619     }
0620 }
0621 
0622 inline bool b2Body::IsAwake() const
0623 {
0624     return (m_flags & e_awakeFlag) == e_awakeFlag;
0625 }
0626 
0627 inline bool b2Body::IsActive() const
0628 {
0629     return (m_flags & e_activeFlag) == e_activeFlag;
0630 }
0631 
0632 inline void b2Body::SetFixedRotation(bool flag)
0633 {
0634     if (flag)
0635     {
0636         m_flags |= e_fixedRotationFlag;
0637     }
0638     else
0639     {
0640         m_flags &= ~e_fixedRotationFlag;
0641     }
0642 
0643     ResetMassData();
0644 }
0645 
0646 inline bool b2Body::IsFixedRotation() const
0647 {
0648     return (m_flags & e_fixedRotationFlag) == e_fixedRotationFlag;
0649 }
0650 
0651 inline void b2Body::SetSleepingAllowed(bool flag)
0652 {
0653     if (flag)
0654     {
0655         m_flags |= e_autoSleepFlag;
0656     }
0657     else
0658     {
0659         m_flags &= ~e_autoSleepFlag;
0660         SetAwake(true);
0661     }
0662 }
0663 
0664 inline bool b2Body::IsSleepingAllowed() const
0665 {
0666     return (m_flags & e_autoSleepFlag) == e_autoSleepFlag;
0667 }
0668 
0669 inline b2Fixture* b2Body::GetFixtureList()
0670 {
0671     return m_fixtureList;
0672 }
0673 
0674 inline const b2Fixture* b2Body::GetFixtureList() const
0675 {
0676     return m_fixtureList;
0677 }
0678 
0679 inline b2JointEdge* b2Body::GetJointList()
0680 {
0681     return m_jointList;
0682 }
0683 
0684 inline const b2JointEdge* b2Body::GetJointList() const
0685 {
0686     return m_jointList;
0687 }
0688 
0689 inline b2ContactEdge* b2Body::GetContactList()
0690 {
0691     return m_contactList;
0692 }
0693 
0694 inline const b2ContactEdge* b2Body::GetContactList() const
0695 {
0696     return m_contactList;
0697 }
0698 
0699 inline b2Body* b2Body::GetNext()
0700 {
0701     return m_next;
0702 }
0703 
0704 inline const b2Body* b2Body::GetNext() const
0705 {
0706     return m_next;
0707 }
0708 
0709 inline void b2Body::SetUserData(void* data)
0710 {
0711     m_userData = data;
0712 }
0713 
0714 inline void* b2Body::GetUserData() const
0715 {
0716     return m_userData;
0717 }
0718 
0719 inline void b2Body::ApplyForce(const b2Vec2& force, const b2Vec2& point)
0720 {
0721     if (m_type != b2_dynamicBody)
0722     {
0723         return;
0724     }
0725 
0726     if (IsAwake() == false)
0727     {
0728         SetAwake(true);
0729     }
0730 
0731     m_force += force;
0732     m_torque += b2Cross(point - m_sweep.c, force);
0733 }
0734 
0735 inline void b2Body::ApplyTorque(qreal torque)
0736 {
0737     if (m_type != b2_dynamicBody)
0738     {
0739         return;
0740     }
0741 
0742     if (IsAwake() == false)
0743     {
0744         SetAwake(true);
0745     }
0746 
0747     m_torque += torque;
0748 }
0749 
0750 inline void b2Body::ApplyLinearImpulse(const b2Vec2& impulse, const b2Vec2& point)
0751 {
0752     if (m_type != b2_dynamicBody)
0753     {
0754         return;
0755     }
0756 
0757     if (IsAwake() == false)
0758     {
0759         SetAwake(true);
0760     }
0761     m_linearVelocity += m_invMass * impulse;
0762     m_angularVelocity += m_invI * b2Cross(point - m_sweep.c, impulse);
0763 }
0764 
0765 inline void b2Body::ApplyAngularImpulse(qreal impulse)
0766 {
0767     if (m_type != b2_dynamicBody)
0768     {
0769         return;
0770     }
0771 
0772     if (IsAwake() == false)
0773     {
0774         SetAwake(true);
0775     }
0776     m_angularVelocity += m_invI * impulse;
0777 }
0778 
0779 inline void b2Body::SynchronizeTransform()
0780 {
0781     m_xf.R.Set(m_sweep.a);
0782     m_xf.position = m_sweep.c - b2Mul(m_xf.R, m_sweep.localCenter);
0783 }
0784 
0785 inline void b2Body::Advance(qreal alpha)
0786 {
0787     // Advance to the new safe time.
0788     m_sweep.Advance(alpha);
0789     m_sweep.c = m_sweep.c0;
0790     m_sweep.a = m_sweep.a0;
0791     SynchronizeTransform();
0792 }
0793 
0794 inline b2World* b2Body::GetWorld()
0795 {
0796     return m_world;
0797 }
0798 
0799 inline const b2World* b2Body::GetWorld() const
0800 {
0801     return m_world;
0802 }
0803 
0804 #endif