diff --git a/box2D/common/B2Settings.hx b/box2D/common/B2Settings.hx index 99436cc..8dd9e01 100644 --- a/box2D/common/B2Settings.hx +++ b/box2D/common/B2Settings.hx @@ -101,12 +101,6 @@ class B2Settings */ static public var b2_maxTOIJointsPerIsland:Int = 32; - /** - * A velocity threshold for elastic collisions. Any collision with a relative linear - * velocity below this threshold will be treated as inelastic. - */ - static public var b2_velocityThreshold:Float = 1.0; // 1 m/s - /** * The maximum linear position correction used when solving constraints. This helps to * prevent overshoot. @@ -158,6 +152,14 @@ class B2Settings return restitution1 > restitution2 ? restitution1 : restitution2; } + /** + * Restitution mixing law. This picks the lowest value. + */ + public static function b2MixRestitutionThreshold(threshold1:Float, threshold2:Float):Float + { + return threshold1 < threshold2 ? threshold1 : threshold2; + } + // Sleep /** diff --git a/box2D/dynamics/B2Body.hx b/box2D/dynamics/B2Body.hx index fb00dfd..412dcf8 100644 --- a/box2D/dynamics/B2Body.hx +++ b/box2D/dynamics/B2Body.hx @@ -373,6 +373,11 @@ class B2Body { return; } + + if (v.lengthSquared() > 0) { + setAwake(true); + } + m_linearVelocity.setV(v); } @@ -395,6 +400,11 @@ class B2Body { return; } + + if (omega * omega > 0) { + setAwake(true); + } + m_angularVelocity = omega; } @@ -1084,6 +1094,7 @@ class B2Body f = f.m_next; } // Contacts are created the next time step. + m_world.m_flags |= B2World.e_newFixture; } else { diff --git a/box2D/dynamics/B2Fixture.hx b/box2D/dynamics/B2Fixture.hx index fa3cdad..8a63edb 100644 --- a/box2D/dynamics/B2Fixture.hx +++ b/box2D/dynamics/B2Fixture.hx @@ -241,6 +241,22 @@ class B2Fixture m_restitution = restitution; } + /** + * Get the coefficient of restitution. + */ + public function getRestitutionThreshold():Float + { + return m_restitutionThreshold; + } + + /** + * Set the restitution threshold. + */ + public function setRestitutionThreshold(threshold:Float):Void + { + m_restitutionThreshold = threshold; + } + /** * Get the fixture's AABB. This AABB may be enlarge and/or stale. * If you need a more accurate AABB, compute it using the shape and @@ -268,6 +284,7 @@ class B2Fixture m_friction = 0.0; m_restitution = 0.0; + m_restitutionThreshold = 0.0; } /** @@ -279,6 +296,7 @@ class B2Fixture m_userData = def.userData; m_friction = def.friction; m_restitution = def.restitution; + m_restitutionThreshold = def.restitutionThreshold; m_body = body; m_next = null; @@ -357,6 +375,7 @@ class B2Fixture public var m_friction:Float; public var m_restitution:Float; + public var m_restitutionThreshold:Float; public var m_proxy:Dynamic; public var m_filter:B2FilterData; diff --git a/box2D/dynamics/B2FixtureDef.hx b/box2D/dynamics/B2FixtureDef.hx index 46b4ad7..4a830b5 100644 --- a/box2D/dynamics/B2FixtureDef.hx +++ b/box2D/dynamics/B2FixtureDef.hx @@ -36,6 +36,7 @@ class B2FixtureDef userData = null; friction = 0.2; restitution = 0.0; + restitutionThreshold = 1.0; density = 0.0; filter.categoryBits = 0x0001; filter.maskBits = 0xFFFF; @@ -64,6 +65,12 @@ class B2FixtureDef */ public var restitution:Float; + /** + * The velocity threshold for elastic collisions. Any collision with a relative linear velocity below this + * will be treated as inelastic. + */ + public var restitutionThreshold:Float; + /** * The density, usually in kg/m^2. */ diff --git a/box2D/dynamics/contacts/B2ContactConstraint.hx b/box2D/dynamics/contacts/B2ContactConstraint.hx index dfe2cd0..953f5ab 100644 --- a/box2D/dynamics/contacts/B2ContactConstraint.hx +++ b/box2D/dynamics/contacts/B2ContactConstraint.hx @@ -56,6 +56,7 @@ class B2ContactConstraint public var radius:Float = 0; public var friction:Float = 0; public var restitution:Float = 0; + public var restitutionThreshold:Float = 0; public var pointCount:Int = 0; public var manifold:B2Manifold; } diff --git a/box2D/dynamics/contacts/B2ContactSolver.hx b/box2D/dynamics/contacts/B2ContactSolver.hx index 0704dfc..c930b5d 100644 --- a/box2D/dynamics/contacts/B2ContactSolver.hx +++ b/box2D/dynamics/contacts/B2ContactSolver.hx @@ -80,6 +80,7 @@ class B2ContactSolver var friction:Float = B2Settings.b2MixFriction(fixtureA.getFriction(), fixtureB.getFriction()); var restitution:Float = B2Settings.b2MixRestitution(fixtureA.getRestitution(), fixtureB.getRestitution()); + var restitutionThreshold:Float = B2Settings.b2MixRestitutionThreshold(fixtureA.getRestitutionThreshold(), fixtureB.getRestitutionThreshold()); // var vA:B2Vec2 = bodyA.m_linearVelocity.Copy(); var vAX:Float = bodyA.m_linearVelocity.x; @@ -107,6 +108,7 @@ class B2ContactSolver cc.pointCount = manifold.m_pointCount; cc.friction = friction; cc.restitution = restitution; + cc.restitutionThreshold = restitutionThreshold; cc.localPlaneNormal.x = manifold.m_localPlaneNormal.x; cc.localPlaneNormal.y = manifold.m_localPlaneNormal.y; @@ -168,7 +170,7 @@ class B2ContactSolver var tY:Float = vBY + (wB * rBX) - vAY - (wA * rAX); // var vRel:Float = b2Dot(cc.normal, t); var vRel:Float = cc.normal.x * tX + cc.normal.y * tY; - if (vRel < -B2Settings.b2_velocityThreshold) + if (vRel < -cc.restitutionThreshold) { ccp.velocityBias += -cc.restitution * vRel; }