diff options
Diffstat (limited to 'modules/bullet')
-rw-r--r-- | modules/bullet/bullet_physics_server.h | 2 | ||||
-rw-r--r-- | modules/bullet/collision_object_bullet.cpp | 9 | ||||
-rw-r--r-- | modules/bullet/generic_6dof_joint_bullet.cpp | 40 | ||||
-rw-r--r-- | modules/bullet/rigid_body_bullet.cpp | 26 | ||||
-rw-r--r-- | modules/bullet/rigid_body_bullet.h | 15 | ||||
-rw-r--r-- | modules/bullet/space_bullet.cpp | 10 |
6 files changed, 97 insertions, 5 deletions
diff --git a/modules/bullet/bullet_physics_server.h b/modules/bullet/bullet_physics_server.h index 6b7dcd86e6..c8c782267e 100644 --- a/modules/bullet/bullet_physics_server.h +++ b/modules/bullet/bullet_physics_server.h @@ -397,6 +397,8 @@ public: virtual void flush_queries(); virtual void finish(); + virtual bool is_flushing_queries() const { return false; } + virtual int get_process_info(ProcessInfo p_info); CollisionObjectBullet *get_collisin_object(RID p_object) const; diff --git a/modules/bullet/collision_object_bullet.cpp b/modules/bullet/collision_object_bullet.cpp index 402a276f95..441fa7c8af 100644 --- a/modules/bullet/collision_object_bullet.cpp +++ b/modules/bullet/collision_object_bullet.cpp @@ -304,7 +304,11 @@ bool RigidCollisionObjectBullet::is_shape_disabled(int p_index) { } void RigidCollisionObjectBullet::shape_changed(int p_shape_index) { - bulletdelete(shapes.write[p_shape_index].bt_shape); + ShapeWrapper &shp = shapes.write[p_shape_index]; + if (shp.bt_shape == mainShape) { + mainShape = NULL; + } + bulletdelete(shp.bt_shape); reload_shapes(); } @@ -366,5 +370,8 @@ void RigidCollisionObjectBullet::body_scale_changed() { void RigidCollisionObjectBullet::internal_shape_destroy(int p_index, bool p_permanentlyFromThisBody) { ShapeWrapper &shp = shapes.write[p_index]; shp.shape->remove_owner(this, p_permanentlyFromThisBody); + if (shp.bt_shape == mainShape) { + mainShape = NULL; + } bulletdelete(shp.bt_shape); } diff --git a/modules/bullet/generic_6dof_joint_bullet.cpp b/modules/bullet/generic_6dof_joint_bullet.cpp index a36f1123bc..a94b88d566 100644 --- a/modules/bullet/generic_6dof_joint_bullet.cpp +++ b/modules/bullet/generic_6dof_joint_bullet.cpp @@ -135,6 +135,15 @@ void Generic6DOFJointBullet::set_param(Vector3::Axis p_axis, PhysicsServer::G6DO case PhysicsServer::G6DOF_JOINT_LINEAR_MOTOR_FORCE_LIMIT: sixDOFConstraint->getTranslationalLimitMotor()->m_maxMotorForce.m_floats[p_axis] = p_value; break; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_DAMPING: + sixDOFConstraint->getTranslationalLimitMotor()->m_springDamping.m_floats[p_axis] = p_value; + break; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_STIFFNESS: + sixDOFConstraint->getTranslationalLimitMotor()->m_springStiffness.m_floats[p_axis] = p_value; + break; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_EQUILIBRIUM_POINT: + sixDOFConstraint->getTranslationalLimitMotor()->m_equilibriumPoint.m_floats[p_axis] = p_value; + break; case PhysicsServer::G6DOF_JOINT_ANGULAR_LOWER_LIMIT: limits_lower[1][p_axis] = p_value; set_flag(p_axis, PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_ANGULAR_LIMIT, flags[p_axis][PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_ANGULAR_LIMIT]); // Reload bullet parameter @@ -143,6 +152,9 @@ void Generic6DOFJointBullet::set_param(Vector3::Axis p_axis, PhysicsServer::G6DO limits_upper[1][p_axis] = p_value; set_flag(p_axis, PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_ANGULAR_LIMIT, flags[p_axis][PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_ANGULAR_LIMIT]); // Reload bullet parameter break; + case PhysicsServer::G6DOF_JOINT_ANGULAR_RESTITUTION: + sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_bounce = p_value; + break; case PhysicsServer::G6DOF_JOINT_ANGULAR_ERP: sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_stopERP = p_value; break; @@ -152,6 +164,15 @@ void Generic6DOFJointBullet::set_param(Vector3::Axis p_axis, PhysicsServer::G6DO case PhysicsServer::G6DOF_JOINT_ANGULAR_MOTOR_FORCE_LIMIT: sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_maxMotorForce = p_value; break; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_STIFFNESS: + sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_springStiffness = p_value; + break; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_DAMPING: + sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_springDamping = p_value; + break; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_EQUILIBRIUM_POINT: + sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_equilibriumPoint = p_value; + break; default: ERR_EXPLAIN("This parameter " + itos(p_param) + " is deprecated"); WARN_DEPRECATED @@ -170,6 +191,12 @@ real_t Generic6DOFJointBullet::get_param(Vector3::Axis p_axis, PhysicsServer::G6 return sixDOFConstraint->getTranslationalLimitMotor()->m_targetVelocity.m_floats[p_axis]; case PhysicsServer::G6DOF_JOINT_LINEAR_MOTOR_FORCE_LIMIT: return sixDOFConstraint->getTranslationalLimitMotor()->m_maxMotorForce.m_floats[p_axis]; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_DAMPING: + return sixDOFConstraint->getTranslationalLimitMotor()->m_springDamping.m_floats[p_axis]; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_STIFFNESS: + return sixDOFConstraint->getTranslationalLimitMotor()->m_springStiffness.m_floats[p_axis]; + case PhysicsServer::G6DOF_JOINT_LINEAR_SPRING_EQUILIBRIUM_POINT: + return sixDOFConstraint->getTranslationalLimitMotor()->m_equilibriumPoint.m_floats[p_axis]; case PhysicsServer::G6DOF_JOINT_ANGULAR_LOWER_LIMIT: return limits_lower[1][p_axis]; case PhysicsServer::G6DOF_JOINT_ANGULAR_UPPER_LIMIT: @@ -182,6 +209,12 @@ real_t Generic6DOFJointBullet::get_param(Vector3::Axis p_axis, PhysicsServer::G6 return sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_targetVelocity; case PhysicsServer::G6DOF_JOINT_ANGULAR_MOTOR_FORCE_LIMIT: return sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_maxMotorForce; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_STIFFNESS: + return sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_springStiffness; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_DAMPING: + return sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_springDamping; + case PhysicsServer::G6DOF_JOINT_ANGULAR_SPRING_EQUILIBRIUM_POINT: + return sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_equilibriumPoint; default: ERR_EXPLAIN("This parameter " + itos(p_param) + " is deprecated"); WARN_DEPRECATED; @@ -215,6 +248,12 @@ void Generic6DOFJointBullet::set_flag(Vector3::Axis p_axis, PhysicsServer::G6DOF case PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_LINEAR_MOTOR: sixDOFConstraint->getTranslationalLimitMotor()->m_enableMotor[p_axis] = flags[p_axis][p_flag]; break; + case PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_LINEAR_SPRING: + sixDOFConstraint->getTranslationalLimitMotor()->m_enableSpring[p_axis] = p_value; + break; + case PhysicsServer::G6DOF_JOINT_FLAG_ENABLE_ANGULAR_SPRING: + sixDOFConstraint->getRotationalLimitMotor(p_axis)->m_enableSpring = p_value; + break; default: ERR_EXPLAIN("This flag " + itos(p_flag) + " is deprecated"); WARN_DEPRECATED @@ -224,6 +263,5 @@ void Generic6DOFJointBullet::set_flag(Vector3::Axis p_axis, PhysicsServer::G6DOF bool Generic6DOFJointBullet::get_flag(Vector3::Axis p_axis, PhysicsServer::G6DOFJointAxisFlag p_flag) const { ERR_FAIL_INDEX_V(p_axis, 3, false); - return flags[p_axis][p_flag]; } diff --git a/modules/bullet/rigid_body_bullet.cpp b/modules/bullet/rigid_body_bullet.cpp index 37e7718969..9dd04100ed 100644 --- a/modules/bullet/rigid_body_bullet.cpp +++ b/modules/bullet/rigid_body_bullet.cpp @@ -268,6 +268,7 @@ RigidBodyBullet::RigidBodyBullet() : can_integrate_forces(false), maxCollisionsDetection(0), collisionsCount(0), + prev_collision_count(0), maxAreasWhereIam(10), areaWhereIamCount(0), countGravityPointSpaces(0), @@ -293,6 +294,9 @@ RigidBodyBullet::RigidBodyBullet() : areasWhereIam.write[i] = NULL; } btBody->setSleepingThresholds(0.2, 0.2); + + prev_collision_traces = &collision_traces_1; + curr_collision_traces = &collision_traces_2; } RigidBodyBullet::~RigidBodyBullet() { @@ -410,7 +414,14 @@ void RigidBodyBullet::on_collision_filters_change() { } void RigidBodyBullet::on_collision_checker_start() { + + prev_collision_count = collisionsCount; collisionsCount = 0; + + // Swap array + Vector<RigidBodyBullet *> *s = prev_collision_traces; + prev_collision_traces = curr_collision_traces; + curr_collision_traces = s; } void RigidBodyBullet::on_collision_checker_end() { @@ -433,10 +444,20 @@ bool RigidBodyBullet::add_collision_object(RigidBodyBullet *p_otherObject, const cd.other_object_shape = p_other_shape_index; cd.local_shape = p_local_shape_index; + curr_collision_traces->write[collisionsCount] = p_otherObject; + ++collisionsCount; return true; } +bool RigidBodyBullet::was_colliding(RigidBodyBullet *p_other_object) { + for (int i = prev_collision_count - 1; 0 <= i; --i) { + if ((*prev_collision_traces)[i] == p_other_object) + return true; + } + return false; +} + void RigidBodyBullet::assert_no_constraints() { if (btBody->getNumConstraintRefs()) { WARN_PRINT("A body with a joints is destroyed. Please check the implementation in order to destroy the joint before the body."); @@ -797,7 +818,10 @@ void RigidBodyBullet::reload_shapes() { const btScalar mass = invMass == 0 ? 0 : 1 / invMass; if (mainShape) { - btVector3 inertia; + // inertia initialised zero here because some of bullet's collision + // shapes incorrectly do not set the vector in calculateLocalIntertia. + // Arbitrary zero is preferable to undefined behaviour. + btVector3 inertia(0, 0, 0); mainShape->calculateLocalInertia(mass, inertia); btBody->setMassProps(mass, inertia); } diff --git a/modules/bullet/rigid_body_bullet.h b/modules/bullet/rigid_body_bullet.h index 26e5018c87..0696073d21 100644 --- a/modules/bullet/rigid_body_bullet.h +++ b/modules/bullet/rigid_body_bullet.h @@ -205,9 +205,15 @@ private: bool can_integrate_forces; Vector<CollisionData> collisions; + Vector<RigidBodyBullet *> collision_traces_1; + Vector<RigidBodyBullet *> collision_traces_2; + Vector<RigidBodyBullet *> *prev_collision_traces; + Vector<RigidBodyBullet *> *curr_collision_traces; + // these parameters are used to avoid vector resize int maxCollisionsDetection; int collisionsCount; + int prev_collision_count; Vector<AreaBullet *> areasWhereIam; // these parameters are used to avoid vector resize @@ -244,9 +250,17 @@ public: virtual void on_collision_checker_end(); void set_max_collisions_detection(int p_maxCollisionsDetection) { + + ERR_FAIL_COND(0 > p_maxCollisionsDetection); + maxCollisionsDetection = p_maxCollisionsDetection; + collisions.resize(p_maxCollisionsDetection); + collision_traces_1.resize(p_maxCollisionsDetection); + collision_traces_2.resize(p_maxCollisionsDetection); + collisionsCount = 0; + prev_collision_count = MIN(prev_collision_count, p_maxCollisionsDetection); } int get_max_collisions_detection() { return maxCollisionsDetection; @@ -254,6 +268,7 @@ public: bool can_add_collision() { return collisionsCount < maxCollisionsDetection; } bool add_collision_object(RigidBodyBullet *p_otherObject, const Vector3 &p_hitWorldLocation, const Vector3 &p_hitLocalLocation, const Vector3 &p_hitNormal, const float &p_appliedImpulse, int p_other_shape_index, int p_local_shape_index); + bool was_colliding(RigidBodyBullet *p_other_object); void assert_no_constraints(); diff --git a/modules/bullet/space_bullet.cpp b/modules/bullet/space_bullet.cpp index ab2d1781ad..fed12cd5ed 100644 --- a/modules/bullet/space_bullet.cpp +++ b/modules/bullet/space_bullet.cpp @@ -786,16 +786,22 @@ void SpaceBullet::check_body_collision() { } const int numContacts = contactManifold->getNumContacts(); + + /// Since I don't need report all contacts for these objects, + /// So report only the first #define REPORT_ALL_CONTACTS 0 #if REPORT_ALL_CONTACTS for (int j = 0; j < numContacts; j++) { btManifoldPoint &pt = contactManifold->getContactPoint(j); #else - // Since I don't need report all contacts for these objects, I'll report only the first if (numContacts) { btManifoldPoint &pt = contactManifold->getContactPoint(0); #endif - if (pt.getDistance() <= 0.0) { + if ( + pt.getDistance() <= 0.0 || + bodyA->was_colliding(bodyB) || + bodyB->was_colliding(bodyA)) { + Vector3 collisionWorldPosition; Vector3 collisionLocalPosition; Vector3 normalOnB; |