diff --git a/src/body/Body.js b/src/body/Body.js index 9e5d962..0ab4346 100644 --- a/src/body/Body.js +++ b/src/body/Body.js @@ -27,6 +27,7 @@ var Body = {}; force: { x: 0, y: 0 }, torque: 0, positionImpulse: { x: 0, y: 0 }, + constraintImpulse: { x: 0, y: 0, angle: 0 }, speed: 0, angularSpeed: 0, velocity: { x: 0, y: 0 }, diff --git a/src/constraint/Constraint.js b/src/constraint/Constraint.js index 0bcaa56..25c35a4 100644 --- a/src/constraint/Constraint.js +++ b/src/constraint/Constraint.js @@ -64,21 +64,21 @@ var Constraint = {}; /** * Description - * @method updateAll + * @method solveAll * @param {constraint[]} constraints */ - Constraint.updateAll = function(constraints) { + Constraint.solveAll = function(constraints) { for (var i = 0; i < constraints.length; i++) { - Constraint.update(constraints[i]); + Constraint.solve(constraints[i]); } }; /** * Description - * @method update + * @method solve * @param {constraint} constraint */ - Constraint.update = function(constraint) { + Constraint.solve = function(constraint) { var bodyA = constraint.bodyA, bodyB = constraint.bodyB, pointA = constraint.pointA, @@ -189,16 +189,15 @@ var Constraint = {}; // TODO: solve this properlly torque = Common.clamp(torque, -0.01, 0.01); + // keep track of applied impulses for post solving + bodyA.constraintImpulse.x -= force.x; + bodyA.constraintImpulse.y -= force.y; + bodyA.constraintImpulse.angle += torque; + // apply forces bodyA.position.x -= force.x; bodyA.position.y -= force.y; bodyA.angle += torque; - - // update geometry - Vertices.translate(bodyA.vertices, force, -1); - Vertices.rotate(bodyA.vertices, torque, bodyA.position); - Axes.rotate(bodyA.axes, torque); - Bounds.update(bodyA.bounds, bodyA.vertices, bodyA.velocity); } if (bodyB && !bodyB.isStatic) { @@ -209,21 +208,45 @@ var Constraint = {}; // clamp to prevent instabillity // TODO: solve this properlly torque = Common.clamp(torque, -0.01, 0.01); + + // keep track of applied impulses for post solving + bodyB.constraintImpulse.x += force.x; + bodyB.constraintImpulse.y += force.y; + bodyB.constraintImpulse.angle -= torque; // apply forces bodyB.position.x += force.x; bodyB.position.y += force.y; bodyB.angle -= torque; - - // update geometry - Vertices.translate(bodyB.vertices, force); - Vertices.rotate(bodyB.vertices, -torque, bodyB.position); - Axes.rotate(bodyB.axes, -torque); - Bounds.update(bodyB.bounds, bodyB.vertices, bodyB.velocity); } }; + /** + * Performs body updates required after solving constraints + * @method postSolveAll + * @param {body[]} bodies + */ + Constraint.postSolveAll = function(bodies) { + for (var i = 0; i < bodies.length; i++) { + var body = bodies[i], + impulse = body.constraintImpulse; + + if (impulse.x !== 0 || impulse.y !== 0 || impulse.angle !== 0) { + // update geometry + Vertices.translate(body.vertices, impulse); + Vertices.rotate(body.vertices, impulse.angle, body.position); + Axes.rotate(body.axes, impulse.angle); + Bounds.update(body.bounds, body.vertices); + + // reset body.constraintImpulse + impulse.x = 0; + impulse.y = 0; + impulse.angle = 0; + } + } + }; + /** * Returns the next unique constraintId * @method nextId diff --git a/src/core/Engine.js b/src/core/Engine.js index 249f91f..79e288d 100644 --- a/src/core/Engine.js +++ b/src/core/Engine.js @@ -255,8 +255,9 @@ var Engine = {}; // update all constraints for (i = 0; i < engine.constraintIterations; i++) { - Constraint.updateAll(allConstraints); + Constraint.solveAll(allConstraints); } + Constraint.postSolveAll(allBodies); // broadphase pass: find potential collision pairs if (broadphase.controller) {