2013-09-03 14:35:40 +00:00
|
|
|
Phaser.Physics = {};
|
|
|
|
|
|
|
|
Phaser.Physics.Arcade = function (game) {
|
2013-10-09 03:31:08 +00:00
|
|
|
|
|
|
|
this.game = game;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this.gravity = new Phaser.Point;
|
|
|
|
this.bounds = new Phaser.Rectangle(0, 0, game.world.width, game.world.height);
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
/**
|
|
|
|
* Used by the QuadTree to set the maximum number of objects
|
|
|
|
* @type {number}
|
|
|
|
*/
|
|
|
|
this.maxObjects = 10;
|
2013-09-04 02:48:15 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
/**
|
|
|
|
* Used by the QuadTree to set the maximum number of levels
|
|
|
|
* @type {number}
|
|
|
|
*/
|
|
|
|
this.maxLevels = 4;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this.OVERLAP_BIAS = 4;
|
|
|
|
this.TILE_OVERLAP = false;
|
2013-09-03 18:34:38 +00:00
|
|
|
|
2013-09-06 14:00:05 +00:00
|
|
|
this.quadTree = new Phaser.QuadTree(this, this.game.world.bounds.x, this.game.world.bounds.y, this.game.world.bounds.width, this.game.world.bounds.height, this.maxObjects, this.maxLevels);
|
2013-10-09 03:31:08 +00:00
|
|
|
this.quadTreeID = 0;
|
|
|
|
|
|
|
|
// Avoid gc spikes by caching these values for re-use
|
|
|
|
this._bounds1 = new Phaser.Rectangle;
|
|
|
|
this._bounds2 = new Phaser.Rectangle;
|
|
|
|
this._overlap = 0;
|
|
|
|
this._maxOverlap = 0;
|
|
|
|
this._velocity1 = 0;
|
|
|
|
this._velocity2 = 0;
|
|
|
|
this._newVelocity1 = 0;
|
|
|
|
this._newVelocity2 = 0;
|
|
|
|
this._average = 0;
|
2013-09-13 01:07:58 +00:00
|
|
|
this._mapData = [];
|
2013-10-16 05:33:39 +00:00
|
|
|
this._mapTiles = 0;
|
2013-09-13 01:07:58 +00:00
|
|
|
this._result = false;
|
|
|
|
this._total = 0;
|
2013-10-08 20:09:46 +00:00
|
|
|
this._angle = 0;
|
2013-10-09 03:31:08 +00:00
|
|
|
this._dx = 0;
|
|
|
|
this._dy = 0;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-03 14:35:40 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
Phaser.Physics.Arcade.prototype = {
|
|
|
|
|
|
|
|
updateMotion: function (body) {
|
|
|
|
|
2013-10-04 13:41:15 +00:00
|
|
|
// If you're wondering why the velocity is halved and applied twice, read this: http://www.niksula.hut.fi/~hkankaan/Homepages/gravity.html
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
// Rotation
|
2013-10-07 23:58:20 +00:00
|
|
|
this._velocityDelta = (this.computeVelocity(0, body, body.angularVelocity, body.angularAcceleration, body.angularDrag, body.maxAngular) - body.angularVelocity) / 2;
|
2013-09-03 14:35:40 +00:00
|
|
|
body.angularVelocity += this._velocityDelta;
|
2013-10-07 23:58:20 +00:00
|
|
|
body.rotation += (body.angularVelocity * this.game.time.physicsElapsed);
|
2013-10-04 13:41:15 +00:00
|
|
|
body.angularVelocity += this._velocityDelta;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
// Horizontal
|
2013-09-30 11:17:07 +00:00
|
|
|
this._velocityDelta = (this.computeVelocity(1, body, body.velocity.x, body.acceleration.x, body.drag.x, body.maxVelocity.x) - body.velocity.x) / 2;
|
2013-09-03 14:35:40 +00:00
|
|
|
body.velocity.x += this._velocityDelta;
|
2013-10-04 13:41:15 +00:00
|
|
|
body.x += (body.velocity.x * this.game.time.physicsElapsed);
|
|
|
|
body.velocity.x += this._velocityDelta;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
// Vertical
|
2013-09-30 11:17:07 +00:00
|
|
|
this._velocityDelta = (this.computeVelocity(2, body, body.velocity.y, body.acceleration.y, body.drag.y, body.maxVelocity.y) - body.velocity.y) / 2;
|
2013-09-03 14:35:40 +00:00
|
|
|
body.velocity.y += this._velocityDelta;
|
2013-10-04 13:41:15 +00:00
|
|
|
body.y += (body.velocity.y * this.game.time.physicsElapsed);
|
|
|
|
body.velocity.y += this._velocityDelta;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
/**
|
2013-09-03 14:35:40 +00:00
|
|
|
* A tween-like function that takes a starting velocity and some other factors and returns an altered velocity.
|
|
|
|
*
|
|
|
|
* @param {number} Velocity Any component of velocity (e.g. 20).
|
|
|
|
* @param {number} Acceleration Rate at which the velocity is changing.
|
|
|
|
* @param {number} Drag Really kind of a deceleration, this is how much the velocity changes if Acceleration is not set.
|
|
|
|
* @param {number} Max An absolute value cap for the velocity.
|
|
|
|
*
|
|
|
|
* @return {number} The altered Velocity value.
|
|
|
|
*/
|
2013-09-04 00:10:01 +00:00
|
|
|
computeVelocity: function (axis, body, velocity, acceleration, drag, max) {
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
max = max || 10000;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
if (axis == 1 && body.allowGravity)
|
2013-09-04 00:10:01 +00:00
|
|
|
{
|
2013-10-09 03:31:08 +00:00
|
|
|
velocity += this.gravity.x + body.gravity.x;
|
2013-09-04 00:10:01 +00:00
|
|
|
}
|
2013-10-09 03:31:08 +00:00
|
|
|
else if (axis == 2 && body.allowGravity)
|
2013-09-04 00:10:01 +00:00
|
|
|
{
|
2013-10-09 03:31:08 +00:00
|
|
|
velocity += this.gravity.y + body.gravity.y;
|
2013-09-04 00:10:01 +00:00
|
|
|
}
|
|
|
|
|
2013-09-03 14:35:40 +00:00
|
|
|
if (acceleration !== 0)
|
|
|
|
{
|
2013-09-04 00:10:01 +00:00
|
|
|
velocity += acceleration * this.game.time.physicsElapsed;
|
2013-09-03 14:35:40 +00:00
|
|
|
}
|
|
|
|
else if (drag !== 0)
|
|
|
|
{
|
2013-09-03 16:07:05 +00:00
|
|
|
this._drag = drag * this.game.time.physicsElapsed;
|
2013-09-03 14:35:40 +00:00
|
|
|
|
|
|
|
if (velocity - this._drag > 0)
|
|
|
|
{
|
2013-10-07 23:58:20 +00:00
|
|
|
velocity -= this._drag;
|
2013-09-03 14:35:40 +00:00
|
|
|
}
|
|
|
|
else if (velocity + this._drag < 0)
|
|
|
|
{
|
|
|
|
velocity += this._drag;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
velocity = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-10-04 13:41:15 +00:00
|
|
|
if (velocity > max)
|
2013-09-03 14:35:40 +00:00
|
|
|
{
|
2013-10-04 13:41:15 +00:00
|
|
|
velocity = max;
|
|
|
|
}
|
|
|
|
else if (velocity < -max)
|
|
|
|
{
|
|
|
|
velocity = -max;
|
2013-09-03 14:35:40 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return velocity;
|
|
|
|
|
2013-09-04 02:48:15 +00:00
|
|
|
},
|
|
|
|
|
|
|
|
preUpdate: function () {
|
|
|
|
|
2013-09-06 14:00:05 +00:00
|
|
|
// Clear the tree
|
|
|
|
this.quadTree.clear();
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
// Create our tree which all of the Physics bodies will add themselves to
|
2013-09-04 12:54:55 +00:00
|
|
|
this.quadTreeID = 0;
|
2013-10-09 03:31:08 +00:00
|
|
|
this.quadTree = new Phaser.QuadTree(this, this.game.world.bounds.x, this.game.world.bounds.y, this.game.world.bounds.width, this.game.world.bounds.height, this.maxObjects, this.maxLevels);
|
2013-09-04 02:48:15 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
postUpdate: function () {
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
// Clear the tree ready for the next update
|
|
|
|
this.quadTree.clear();
|
2013-09-04 02:48:15 +00:00
|
|
|
|
2013-09-03 14:35:40 +00:00
|
|
|
},
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
/**
|
2013-09-13 03:22:12 +00:00
|
|
|
* Checks for collision between two game objects. The objects can be Sprites, Groups, Emitters or Tilemaps.
|
2013-09-13 01:07:58 +00:00
|
|
|
* You can perform Sprite vs. Sprite, Sprite vs. Group, Group vs. Group, Sprite vs. Tilemap or Group vs. Tilemap collisions.
|
|
|
|
*
|
2013-09-13 03:22:12 +00:00
|
|
|
* @param object1 The first object to check. Can be an instance of Phaser.Sprite, Phaser.Group, Phaser.Particles.Emitter, or Phaser.Tilemap
|
|
|
|
* @param object2 The second object to check. Can be an instance of Phaser.Sprite, Phaser.Group, Phaser.Particles.Emitter or Phaser.Tilemap
|
2013-09-13 01:07:58 +00:00
|
|
|
* @param collideCallback An optional callback function that is called if the objects overlap. The two objects will be passed to this function in the same order in which you passed them to Collision.overlap.
|
|
|
|
* @param processCallback A callback function that lets you perform additional checks against the two objects if they overlap. If this is set then collideCallback will only be called if processCallback returns true.
|
|
|
|
* @param callbackContext The context in which to run the callbacks.
|
|
|
|
* @returns {boolean} true if any collisions were detected, otherwise false.
|
|
|
|
**/
|
2013-09-12 23:53:03 +00:00
|
|
|
collide: function (object1, object2, collideCallback, processCallback, callbackContext) {
|
|
|
|
|
|
|
|
collideCallback = collideCallback || null;
|
|
|
|
processCallback = processCallback || null;
|
|
|
|
callbackContext = callbackContext || collideCallback;
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
this._result = false;
|
|
|
|
this._total = 0;
|
2013-09-12 23:53:03 +00:00
|
|
|
|
|
|
|
// Only collide valid objects
|
|
|
|
if (object1 && object2 && object1.exists && object2.exists)
|
|
|
|
{
|
|
|
|
// Can expand to support Buttons, Text, etc at a later date. For now these are the essentials.
|
|
|
|
|
2013-09-13 03:22:12 +00:00
|
|
|
// SPRITES
|
|
|
|
if (object1.type == Phaser.SPRITE)
|
2013-09-12 23:53:03 +00:00
|
|
|
{
|
2013-09-13 03:22:12 +00:00
|
|
|
if (object2.type == Phaser.SPRITE)
|
|
|
|
{
|
|
|
|
this.collideSpriteVsSprite(object1, object2, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
|
|
|
else if (object2.type == Phaser.GROUP || object2.type == Phaser.EMITTER)
|
|
|
|
{
|
|
|
|
this.collideSpriteVsGroup(object1, object2, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
2013-10-16 05:33:39 +00:00
|
|
|
else if (object2.type == Phaser.TILEMAPLAYER)
|
2013-09-13 03:22:12 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideSpriteVsTilemapLayer(object1, object2, collideCallback, processCallback, callbackContext);
|
2013-09-13 03:22:12 +00:00
|
|
|
}
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
2013-09-13 03:22:12 +00:00
|
|
|
// GROUPS
|
|
|
|
else if (object1.type == Phaser.GROUP)
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
2013-09-13 03:22:12 +00:00
|
|
|
if (object2.type == Phaser.SPRITE)
|
|
|
|
{
|
|
|
|
this.collideSpriteVsGroup(object2, object1, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
|
|
|
else if (object2.type == Phaser.GROUP || object2.type == Phaser.EMITTER)
|
|
|
|
{
|
|
|
|
this.collideGroupVsGroup(object1, object2, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
2013-10-16 05:33:39 +00:00
|
|
|
else if (object2.type == Phaser.TILEMAPLAYER)
|
2013-09-13 03:22:12 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideGroupVsTilemapLayer(object1, object2, collideCallback, processCallback, callbackContext);
|
2013-09-13 03:22:12 +00:00
|
|
|
}
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
2013-10-16 05:33:39 +00:00
|
|
|
// TILEMAP LAYERS
|
|
|
|
else if (object1.type == Phaser.TILEMAPLAYER)
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
2013-09-13 03:22:12 +00:00
|
|
|
if (object2.type == Phaser.SPRITE)
|
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideSpriteVsTilemapLayer(object2, object1, collideCallback, processCallback, callbackContext);
|
2013-09-13 03:22:12 +00:00
|
|
|
}
|
|
|
|
else if (object2.type == Phaser.GROUP || object2.type == Phaser.EMITTER)
|
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideGroupVsTilemapLayer(object2, object1, collideCallback, processCallback, callbackContext);
|
2013-09-13 03:22:12 +00:00
|
|
|
}
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
2013-09-13 03:22:12 +00:00
|
|
|
// EMITTER
|
|
|
|
else if (object1.type == Phaser.EMITTER)
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
2013-09-13 03:22:12 +00:00
|
|
|
if (object2.type == Phaser.SPRITE)
|
|
|
|
{
|
|
|
|
this.collideSpriteVsGroup(object2, object1, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
|
|
|
else if (object2.type == Phaser.GROUP || object2.type == Phaser.EMITTER)
|
|
|
|
{
|
|
|
|
this.collideGroupVsGroup(object1, object2, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
2013-10-16 05:33:39 +00:00
|
|
|
else if (object2.type == Phaser.TILEMAPLAYER)
|
2013-09-13 03:22:12 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideGroupVsTilemapLayer(object1, object2, collideCallback, processCallback, callbackContext);
|
2013-09-13 03:22:12 +00:00
|
|
|
}
|
2013-09-12 23:53:03 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
return (this._total > 0);
|
2013-09-12 23:53:03 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
collideSpriteVsTilemapLayer: function (sprite, tilemapLayer, collideCallback, processCallback, callbackContext) {
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
this._mapData = tilemapLayer.getTiles(sprite.body.x, sprite.body.y, sprite.body.width, sprite.body.height, true);
|
2013-09-13 01:07:58 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
if (this._mapData.length > 1)
|
2013-09-12 23:53:03 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
for (var i = 1; i < this._mapData.length; i++)
|
2013-09-12 23:53:03 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.separateTile(sprite.body, this._mapData[i]);
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
if (this._result)
|
|
|
|
{
|
|
|
|
// They collided, is there a custom process callback?
|
|
|
|
if (processCallback)
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
if (processCallback.call(callbackContext, sprite, this._mapData[i]))
|
|
|
|
{
|
|
|
|
this._total++;
|
|
|
|
|
|
|
|
if (collideCallback)
|
|
|
|
{
|
|
|
|
collideCallback.call(callbackContext, sprite, this._mapData[i]);
|
|
|
|
}
|
|
|
|
}
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
2013-10-16 05:33:39 +00:00
|
|
|
else
|
|
|
|
{
|
|
|
|
this._total++;
|
2013-09-13 01:07:58 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
if (collideCallback)
|
|
|
|
{
|
|
|
|
collideCallback.call(callbackContext, sprite, this._mapData[i]);
|
|
|
|
}
|
|
|
|
}
|
2013-09-12 23:53:03 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
},
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
collideGroupVsTilemapLayer: function (group, tilemapLayer, collideCallback, processCallback, callbackContext) {
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-09-24 14:28:29 +00:00
|
|
|
if (group.length == 0)
|
|
|
|
{
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2013-09-12 23:53:03 +00:00
|
|
|
if (group._container.first._iNext)
|
|
|
|
{
|
|
|
|
var currentNode = group._container.first._iNext;
|
|
|
|
|
|
|
|
do
|
|
|
|
{
|
2013-09-13 01:07:58 +00:00
|
|
|
if (currentNode.exists)
|
2013-09-12 23:53:03 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
this.collideSpriteVsTilemapLayer(currentNode, tilemapLayer, collideCallback, processCallback, callbackContext);
|
2013-09-12 23:53:03 +00:00
|
|
|
}
|
|
|
|
currentNode = currentNode._iNext;
|
|
|
|
}
|
|
|
|
while (currentNode != group._container.last._iNext);
|
|
|
|
}
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
},
|
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
collideSpriteVsSprite: function (sprite1, sprite2, collideCallback, processCallback, callbackContext) {
|
2013-09-13 01:07:58 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
this.separate(sprite1.body, sprite2.body);
|
2013-09-13 01:07:58 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
if (this._result)
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
// They collided, is there a custom process callback?
|
2013-09-13 01:07:58 +00:00
|
|
|
if (processCallback)
|
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
if (processCallback.call(callbackContext, sprite1, sprite2))
|
2013-09-13 01:07:58 +00:00
|
|
|
{
|
|
|
|
this._total++;
|
|
|
|
|
|
|
|
if (collideCallback)
|
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
collideCallback.call(callbackContext, sprite1, sprite2);
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
this._total++;
|
|
|
|
|
|
|
|
if (collideCallback)
|
|
|
|
{
|
2013-10-16 05:33:39 +00:00
|
|
|
collideCallback.call(callbackContext, sprite1, sprite2);
|
2013-09-13 01:07:58 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
collideSpriteVsGroup: function (sprite, group, collideCallback, processCallback, callbackContext) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-09-24 14:28:29 +00:00
|
|
|
if (group.length == 0)
|
|
|
|
{
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
// What is the sprite colliding with in the quadtree?
|
|
|
|
this._potentials = this.quadTree.retrieve(sprite);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
for (var i = 0, len = this._potentials.length; i < len; i++)
|
2013-09-04 15:12:58 +00:00
|
|
|
{
|
2013-09-13 01:07:58 +00:00
|
|
|
// We have our potential suspects, are they in this group?
|
|
|
|
if (this._potentials[i].sprite.group == group)
|
2013-09-04 15:12:58 +00:00
|
|
|
{
|
2013-09-13 01:07:58 +00:00
|
|
|
this.separate(sprite.body, this._potentials[i]);
|
|
|
|
|
|
|
|
if (this._result && processCallback)
|
2013-09-04 15:12:58 +00:00
|
|
|
{
|
2013-09-13 01:07:58 +00:00
|
|
|
this._result = processCallback.call(callbackContext, sprite, this._potentials[i].sprite);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (this._result)
|
|
|
|
{
|
|
|
|
this._total++;
|
|
|
|
|
|
|
|
if (collideCallback)
|
2013-09-04 15:12:58 +00:00
|
|
|
{
|
2013-09-13 01:07:58 +00:00
|
|
|
collideCallback.call(callbackContext, sprite, this._potentials[i].sprite);
|
2013-09-04 15:12:58 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
collideGroupVsGroup: function (group1, group2, collideCallback, processCallback, callbackContext) {
|
|
|
|
|
2013-09-24 14:28:29 +00:00
|
|
|
if (group1.length == 0 || group2.length == 0)
|
|
|
|
{
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2013-09-13 01:07:58 +00:00
|
|
|
if (group1._container.first._iNext)
|
|
|
|
{
|
|
|
|
var currentNode = group1._container.first._iNext;
|
|
|
|
|
|
|
|
do
|
|
|
|
{
|
|
|
|
if (currentNode.exists)
|
|
|
|
{
|
|
|
|
this.collideSpriteVsGroup(currentNode, group2, collideCallback, processCallback, callbackContext);
|
|
|
|
}
|
|
|
|
currentNode = currentNode._iNext;
|
|
|
|
}
|
|
|
|
while (currentNode != group1._container.last._iNext);
|
|
|
|
}
|
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
/**
|
2013-09-13 03:22:12 +00:00
|
|
|
* The core separation function to separate two physics bodies.
|
2013-09-12 23:53:03 +00:00
|
|
|
* @param body1 The first Sprite.Body to separate
|
|
|
|
* @param body2 The second Sprite.Body to separate
|
|
|
|
* @returns {boolean} Returns true if the bodies were separated, otherwise false.
|
2013-09-03 16:28:12 +00:00
|
|
|
*/
|
2013-09-12 23:53:03 +00:00
|
|
|
separate: function (body1, body2) {
|
|
|
|
|
2013-09-13 02:07:39 +00:00
|
|
|
this._result = (this.separateX(body1, body2) || this.separateY(body1, body2));
|
|
|
|
|
2013-09-03 16:28:12 +00:00
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-09-12 23:53:03 +00:00
|
|
|
* Separates the two physics bodies on their X axis
|
|
|
|
* @param body1 The first Sprite.Body to separate
|
|
|
|
* @param body2 The second Sprite.Body to separate
|
2013-09-03 16:28:12 +00:00
|
|
|
* @returns {boolean} Whether the objects in fact touched and were separated along the X axis.
|
|
|
|
*/
|
2013-09-12 23:53:03 +00:00
|
|
|
separateX: function (body1, body2) {
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// Can't separate two immovable bodies
|
2013-09-12 23:53:03 +00:00
|
|
|
if (body1.immovable && body2.immovable)
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2013-09-03 18:34:38 +00:00
|
|
|
this._overlap = 0;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// Check if the hulls actually overlap
|
|
|
|
if (Phaser.Rectangle.intersects(body1, body2))
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
this._maxOverlap = body1.deltaAbsX() + body2.deltaAbsX() + this.OVERLAP_BIAS;
|
2013-09-03 18:34:38 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (body1.deltaX() == 0 && body2.deltaX() == 0)
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
// They overlap but neither of them are moving
|
|
|
|
body1.embedded = true;
|
|
|
|
body2.embedded = true;
|
|
|
|
}
|
|
|
|
else if (body1.deltaX() > body2.deltaX())
|
|
|
|
{
|
|
|
|
// Body1 is moving right and/or Body2 is moving left
|
|
|
|
this._overlap = body1.x + body1.width - body2.x;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body1.allowCollision.right == false || body2.allowCollision.left == false)
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
this._overlap = 0;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
else
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.touching.right = true;
|
|
|
|
body2.touching.left = true;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
else if (body1.deltaX() < body2.deltaX())
|
|
|
|
{
|
|
|
|
// Body1 is moving left and/or Body2 is moving right
|
|
|
|
this._overlap = body1.x - body2.width - body2.x;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if ((-this._overlap > this._maxOverlap) || body1.allowCollision.left == false || body2.allowCollision.right == false)
|
|
|
|
{
|
|
|
|
this._overlap = 0;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
body1.touching.left = true;
|
|
|
|
body2.touching.right = true;
|
|
|
|
}
|
|
|
|
}
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// Then adjust their positions and velocities accordingly (if there was any overlap)
|
|
|
|
if (this._overlap != 0)
|
2013-09-13 02:07:39 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.overlapX = this._overlap;
|
|
|
|
body2.overlapX = this._overlap;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (body1.customSeparateX || body2.customSeparateX)
|
|
|
|
{
|
|
|
|
return true;
|
|
|
|
}
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
this._velocity1 = body1.velocity.x;
|
|
|
|
this._velocity2 = body2.velocity.x;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (!body1.immovable && !body2.immovable)
|
|
|
|
{
|
|
|
|
this._overlap *= 0.5;
|
2013-09-03 18:34:38 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.x = body1.x - this._overlap;
|
|
|
|
body2.x += this._overlap;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
this._newVelocity1 = Math.sqrt((this._velocity2 * this._velocity2 * body2.mass) / body1.mass) * ((this._velocity2 > 0) ? 1 : -1);
|
|
|
|
this._newVelocity2 = Math.sqrt((this._velocity1 * this._velocity1 * body1.mass) / body2.mass) * ((this._velocity1 > 0) ? 1 : -1);
|
|
|
|
this._average = (this._newVelocity1 + this._newVelocity2) * 0.5;
|
|
|
|
this._newVelocity1 -= this._average;
|
|
|
|
this._newVelocity2 -= this._average;
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.velocity.x = this._average + this._newVelocity1 * body1.bounce.x;
|
|
|
|
body2.velocity.x = this._average + this._newVelocity2 * body2.bounce.x;
|
|
|
|
}
|
|
|
|
else if (!body1.immovable)
|
|
|
|
{
|
|
|
|
body1.x = body1.x - this._overlap;
|
|
|
|
body1.velocity.x = this._velocity2 - this._velocity1 * body1.bounce.x;
|
|
|
|
}
|
|
|
|
else if (!body2.immovable)
|
|
|
|
{
|
|
|
|
body2.x += this._overlap;
|
|
|
|
body2.velocity.x = this._velocity1 - this._velocity2 * body2.bounce.x;
|
|
|
|
}
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
return false;
|
|
|
|
|
2013-09-03 16:28:12 +00:00
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-09-12 23:53:03 +00:00
|
|
|
* Separates the two physics bodies on their Y axis
|
|
|
|
* @param body1 The first Sprite.Body to separate
|
|
|
|
* @param body2 The second Sprite.Body to separate
|
|
|
|
* @returns {boolean} Whether the bodys in fact touched and were separated along the Y axis.
|
2013-09-03 16:28:12 +00:00
|
|
|
*/
|
2013-09-12 23:53:03 +00:00
|
|
|
separateY: function (body1, body2) {
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-12 23:53:03 +00:00
|
|
|
// Can't separate two immovable or non-existing bodys
|
|
|
|
if (body1.immovable && body2.immovable)
|
2013-09-04 00:10:01 +00:00
|
|
|
{
|
2013-09-03 16:28:12 +00:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2013-09-04 00:10:01 +00:00
|
|
|
this._overlap = 0;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// Check if the hulls actually overlap
|
|
|
|
if (Phaser.Rectangle.intersects(body1, body2))
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
this._maxOverlap = body1.deltaAbsY() + body2.deltaAbsY() + this.OVERLAP_BIAS;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (body1.deltaY() == 0 && body2.deltaY() == 0)
|
|
|
|
{
|
|
|
|
// They overlap but neither of them are moving
|
|
|
|
body1.embedded = true;
|
|
|
|
body2.embedded = true;
|
|
|
|
}
|
|
|
|
else if (body1.deltaY() > body2.deltaY())
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
// Body1 is moving down and/or Body2 is moving up
|
|
|
|
this._overlap = body1.y + body1.height - body2.y;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body1.allowCollision.down == false || body2.allowCollision.up == false)
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
this._overlap = 0;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
else
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.touching.down = true;
|
|
|
|
body2.touching.up = true;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
else if (body1.deltaY() < body2.deltaY())
|
|
|
|
{
|
|
|
|
// Body1 is moving up and/or Body2 is moving down
|
|
|
|
this._overlap = body1.y - body2.height - body2.y;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if ((-this._overlap > this._maxOverlap) || body1.allowCollision.up == false || body2.allowCollision.down == false)
|
|
|
|
{
|
|
|
|
this._overlap = 0;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
body1.touching.up = true;
|
|
|
|
body2.touching.down = true;
|
|
|
|
}
|
|
|
|
}
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// Then adjust their positions and velocities accordingly (if there was any overlap)
|
|
|
|
if (this._overlap != 0)
|
2013-09-13 02:07:39 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.overlapY = this._overlap;
|
|
|
|
body2.overlapY = this._overlap;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (body1.customSeparateY || body2.customSeparateY)
|
|
|
|
{
|
|
|
|
return true;
|
|
|
|
}
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
this._velocity1 = body1.velocity.y;
|
|
|
|
this._velocity2 = body2.velocity.y;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
if (!body1.immovable && !body2.immovable)
|
|
|
|
{
|
|
|
|
this._overlap *= 0.5;
|
2013-09-03 16:28:12 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.y = body1.y - this._overlap;
|
|
|
|
body2.y += this._overlap;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
this._newVelocity1 = Math.sqrt((this._velocity2 * this._velocity2 * body2.mass) / body1.mass) * ((this._velocity2 > 0) ? 1 : -1);
|
|
|
|
this._newVelocity2 = Math.sqrt((this._velocity1 * this._velocity1 * body1.mass) / body2.mass) * ((this._velocity1 > 0) ? 1 : -1);
|
|
|
|
this._average = (this._newVelocity1 + this._newVelocity2) * 0.5;
|
|
|
|
this._newVelocity1 -= this._average;
|
|
|
|
this._newVelocity2 -= this._average;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
body1.velocity.y = this._average + this._newVelocity1 * body1.bounce.y;
|
|
|
|
body2.velocity.y = this._average + this._newVelocity2 * body2.bounce.y;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
else if (!body1.immovable)
|
|
|
|
{
|
|
|
|
body1.y = body1.y - this._overlap;
|
|
|
|
body1.velocity.y = this._velocity2 - this._velocity1 * body1.bounce.y;
|
2013-09-13 02:07:39 +00:00
|
|
|
|
2013-09-23 02:26:08 +00:00
|
|
|
// This is special case code that handles things like horizontal moving platforms you can ride
|
|
|
|
if (body2.active && body2.moves && (body1.deltaY() > body2.deltaY()))
|
|
|
|
{
|
|
|
|
body1.x += body2.x - body2.lastX;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if (!body2.immovable)
|
2013-09-03 16:28:12 +00:00
|
|
|
{
|
2013-09-23 02:26:08 +00:00
|
|
|
body2.y += this._overlap;
|
|
|
|
body2.velocity.y = this._velocity1 - this._velocity2 * body2.bounce.y;
|
|
|
|
|
|
|
|
// This is special case code that handles things like horizontal moving platforms you can ride
|
|
|
|
if (body1.sprite.active && body1.moves && (body1.deltaY() < body2.deltaY()))
|
|
|
|
{
|
|
|
|
body2.x += body1.x - body1.lastX;
|
|
|
|
}
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
|
|
|
|
return true;
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-12 23:53:03 +00:00
|
|
|
|
2013-09-03 16:28:12 +00:00
|
|
|
}
|
2013-09-23 02:26:08 +00:00
|
|
|
|
|
|
|
return false;
|
|
|
|
|
2013-09-03 16:28:12 +00:00
|
|
|
},
|
|
|
|
|
2013-09-12 14:39:52 +00:00
|
|
|
/**
|
|
|
|
* The core Collision separation function used by Collision.overlap.
|
|
|
|
* @param object1 The first GameObject to separate
|
|
|
|
* @param object2 The second GameObject to separate
|
|
|
|
* @returns {boolean} Returns true if the objects were separated, otherwise false.
|
|
|
|
*/
|
2013-10-15 03:28:16 +00:00
|
|
|
separateTile: function (body, tile) {
|
2013-09-12 14:39:52 +00:00
|
|
|
|
2013-10-16 05:33:39 +00:00
|
|
|
this._result = (this.separateTileX(body, tile, true) || this.separateTileY(body, tile, true));
|
2013-09-12 14:39:52 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-09-24 14:28:29 +00:00
|
|
|
/**
|
|
|
|
* Separates the two objects on their x axis
|
|
|
|
* @param object The GameObject to separate
|
|
|
|
* @param tile The Tile to separate
|
|
|
|
* @returns {boolean} Whether the objects in fact touched and were separated along the X axis.
|
|
|
|
*/
|
2013-10-15 03:28:16 +00:00
|
|
|
separateTileX: function (body, tile, separate) {
|
2013-09-24 14:28:29 +00:00
|
|
|
|
|
|
|
// Can't separate two immovable objects (tiles are always immovable)
|
2013-10-15 14:24:07 +00:00
|
|
|
if (body.immovable || body.deltaX() == 0 || Phaser.Rectangle.intersects(body.hullX, tile) == false)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
this._overlap = 0;
|
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
// The hulls overlap, let's process it
|
|
|
|
this._maxOverlap = body.deltaAbsX() + this.OVERLAP_BIAS;
|
|
|
|
|
|
|
|
if (body.deltaX() < 0)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 14:24:07 +00:00
|
|
|
// Moving left
|
|
|
|
this._overlap = tile.right - body.hullX.x;
|
2013-09-24 14:28:29 +00:00
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body.allowCollision.left == false || tile.tile.collideRight == false)
|
|
|
|
{
|
|
|
|
this._overlap = 0;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
2013-10-15 03:28:16 +00:00
|
|
|
else
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 14:24:07 +00:00
|
|
|
body.touching.left = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Moving right
|
|
|
|
this._overlap = body.hullX.right - tile.x;
|
2013-09-24 14:28:29 +00:00
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body.allowCollision.right == false || tile.tile.collideLeft == false)
|
|
|
|
{
|
|
|
|
this._overlap = 0;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
body.touching.right = true;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
// Then adjust their positions and velocities accordingly (if there was any overlap)
|
|
|
|
if (this._overlap != 0)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
if (separate)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
if (body.deltaX() < 0)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.x = body.x + this._overlap;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.x = body.x - this._overlap;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
if (body.bounce.x == 0)
|
2013-09-24 14:28:29 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.velocity.x = 0;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.velocity.x = -body.velocity.x * body.bounce.x;
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
2013-10-15 14:24:07 +00:00
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
body.updateHulls();
|
2013-09-24 14:28:29 +00:00
|
|
|
}
|
2013-10-15 14:24:07 +00:00
|
|
|
|
2013-09-24 14:28:29 +00:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
},
|
2013-09-24 14:28:29 +00:00
|
|
|
|
2013-09-12 14:39:52 +00:00
|
|
|
/**
|
|
|
|
* Separates the two objects on their x axis
|
|
|
|
* @param object The GameObject to separate
|
|
|
|
* @param tile The Tile to separate
|
|
|
|
* @returns {boolean} Whether the objects in fact touched and were separated along the X axis.
|
|
|
|
*/
|
2013-10-15 03:28:16 +00:00
|
|
|
separateTileY: function (body, tile, separate) {
|
2013-09-12 14:39:52 +00:00
|
|
|
|
|
|
|
// Can't separate two immovable objects (tiles are always immovable)
|
2013-10-15 14:24:07 +00:00
|
|
|
if (body.immovable || body.deltaY() == 0 || Phaser.Rectangle.intersects(body.hullY, tile) == false)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
this._overlap = 0;
|
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
// The hulls overlap, let's process it
|
|
|
|
this._maxOverlap = body.deltaAbsY() + this.OVERLAP_BIAS;
|
|
|
|
|
|
|
|
if (body.deltaY() < 0)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 14:24:07 +00:00
|
|
|
// Moving up
|
|
|
|
this._overlap = tile.bottom - body.hullY.y;
|
2013-09-12 14:39:52 +00:00
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body.allowCollision.up == false || tile.tile.collideDown == false)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 14:24:07 +00:00
|
|
|
this._overlap = 0;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
2013-10-15 03:28:16 +00:00
|
|
|
else
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 14:24:07 +00:00
|
|
|
body.touching.up = true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Moving down
|
|
|
|
this._overlap = body.hullY.bottom - tile.y;
|
2013-09-12 14:39:52 +00:00
|
|
|
|
2013-10-15 14:24:07 +00:00
|
|
|
if ((this._overlap > this._maxOverlap) || body.allowCollision.down == false || tile.tile.collideUp == false)
|
|
|
|
{
|
|
|
|
this._overlap = 0;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
body.touching.down = true;
|
2013-09-23 02:26:08 +00:00
|
|
|
}
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
// Then adjust their positions and velocities accordingly (if there was any overlap)
|
|
|
|
if (this._overlap != 0)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
if (separate)
|
2013-09-23 02:26:08 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
if (body.deltaY() < 0)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.y = body.y + this._overlap;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.y = body.y - this._overlap;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
if (body.bounce.y == 0)
|
2013-09-12 14:39:52 +00:00
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.velocity.y = 0;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-10-15 03:28:16 +00:00
|
|
|
body.velocity.y = -body.velocity.y * body.bounce.y;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
2013-10-15 14:24:07 +00:00
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
body.updateHulls();
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
2013-10-15 14:24:07 +00:00
|
|
|
|
2013-10-15 03:28:16 +00:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return false;
|
2013-09-12 14:39:52 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-09-04 15:12:58 +00:00
|
|
|
/**
|
2013-10-09 06:11:36 +00:00
|
|
|
* Move the given display object towards the destination object at a steady velocity.
|
2013-10-08 20:09:46 +00:00
|
|
|
* If you specify a maxTime then it will adjust the speed (over-writing what you set) so it arrives at the destination in that number of seconds.
|
|
|
|
* Timings are approximate due to the way browser timers work. Allow for a variance of +- 50ms.
|
2013-10-09 03:31:08 +00:00
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
2013-10-08 20:09:46 +00:00
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
|
|
|
* Note: Doesn't take into account acceleration, maxVelocity or drag (if you've set drag or acceleration too high this object may not move at all)
|
2013-09-04 15:12:58 +00:00
|
|
|
*
|
2013-10-09 03:31:08 +00:00
|
|
|
* @method Phaser.Physics.Arcade#moveToObject
|
2013-10-08 20:09:46 +00:00
|
|
|
* @param {any} displayObject - The display object to move.
|
|
|
|
* @param {any} destination - The display object to move towards. Can be any object but must have visible x/y properties.
|
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second (default is 60 pixels/sec)
|
|
|
|
* @param {number} [maxTime=0] - Time given in milliseconds (1000 = 1 sec). If set the speed is adjusted so the object will arrive at destination in the given number of ms.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new velocity.
|
|
|
|
*/
|
2013-10-09 03:31:08 +00:00
|
|
|
moveToObject: function (displayObject, destination, speed, maxTime) {
|
2013-10-08 20:09:46 +00:00
|
|
|
|
|
|
|
speed = speed || 60;
|
|
|
|
maxTime = maxTime || 0;
|
|
|
|
|
2013-10-09 06:11:36 +00:00
|
|
|
this._angle = Math.atan2(destination.y - displayObject.y, destination.x - displayObject.x);
|
2013-10-08 20:09:46 +00:00
|
|
|
|
|
|
|
if (maxTime > 0)
|
|
|
|
{
|
|
|
|
// We know how many pixels we need to move, but how fast?
|
2013-10-09 03:31:08 +00:00
|
|
|
speed = this.distanceBetween(displayObject, destination) / (maxTime / 1000);
|
2013-10-08 20:09:46 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
displayObject.body.velocity.x = Math.cos(this._angle) * speed;
|
|
|
|
displayObject.body.velocity.y = Math.sin(this._angle) * speed;
|
|
|
|
|
|
|
|
return this._angle;
|
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Move the given display object towards the pointer at a steady velocity. If no pointer is given it will use Phaser.Input.activePointer.
|
|
|
|
* If you specify a maxTime then it will adjust the speed (over-writing what you set) so it arrives at the destination in that number of seconds.
|
|
|
|
* Timings are approximate due to the way browser timers work. Allow for a variance of +- 50ms.
|
2013-10-09 03:31:08 +00:00
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
2013-10-08 20:09:46 +00:00
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
2013-09-04 15:12:58 +00:00
|
|
|
*
|
2013-10-09 03:31:08 +00:00
|
|
|
* @method Phaser.Physics.Arcade#moveToPointer
|
2013-10-08 20:09:46 +00:00
|
|
|
* @param {any} displayObject - The display object to move.
|
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second (default is 60 pixels/sec)
|
|
|
|
* @param {Phaser.Pointer} [pointer] - The pointer to move towards. Defaults to Phaser.Input.activePointer.
|
|
|
|
* @param {number} [maxTime=0] - Time given in milliseconds (1000 = 1 sec). If set the speed is adjusted so the object will arrive at destination in the given number of ms.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new velocity.
|
2013-09-04 15:12:58 +00:00
|
|
|
*/
|
2013-10-09 03:31:08 +00:00
|
|
|
moveToPointer: function (displayObject, speed, pointer, maxTime) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-08 20:09:46 +00:00
|
|
|
speed = speed || 60;
|
|
|
|
pointer = pointer || this.game.input.activePointer;
|
|
|
|
maxTime = maxTime || 0;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._angle = this.angleToPointer(displayObject, pointer);
|
2013-10-08 20:09:46 +00:00
|
|
|
|
|
|
|
if (maxTime > 0)
|
|
|
|
{
|
|
|
|
// We know how many pixels we need to move, but how fast?
|
2013-10-09 03:31:08 +00:00
|
|
|
speed = this.distanceToPointer(displayObject, pointer) / (maxTime / 1000);
|
2013-10-08 20:09:46 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
displayObject.body.velocity.x = Math.cos(this._angle) * speed;
|
|
|
|
displayObject.body.velocity.y = Math.sin(this._angle) * speed;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-08 20:09:46 +00:00
|
|
|
return this._angle;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Move the given display object towards the x/y coordinates at a steady velocity.
|
2013-10-08 20:09:46 +00:00
|
|
|
* If you specify a maxTime then it will adjust the speed (over-writing what you set) so it arrives at the destination in that number of seconds.
|
|
|
|
* Timings are approximate due to the way browser timers work. Allow for a variance of +- 50ms.
|
2013-10-09 03:31:08 +00:00
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
2013-10-08 20:09:46 +00:00
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
|
|
|
* Note: Doesn't take into account acceleration, maxVelocity or drag (if you've set drag or acceleration too high this object may not move at all)
|
|
|
|
*
|
2013-10-09 03:31:08 +00:00
|
|
|
* @method Phaser.Physics.Arcade#moveToXY
|
2013-10-08 20:09:46 +00:00
|
|
|
* @param {any} displayObject - The display object to move.
|
2013-10-09 03:31:08 +00:00
|
|
|
* @param {number} x - The x coordinate to move towards.
|
|
|
|
* @param {number} y - The y coordinate to move towards.
|
2013-10-08 20:09:46 +00:00
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second (default is 60 pixels/sec)
|
|
|
|
* @param {number} [maxTime=0] - Time given in milliseconds (1000 = 1 sec). If set the speed is adjusted so the object will arrive at destination in the given number of ms.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new velocity.
|
|
|
|
*/
|
2013-10-09 03:31:08 +00:00
|
|
|
moveToXY: function (displayObject, x, y, speed, maxTime) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
speed = speed || 60;
|
|
|
|
maxTime = maxTime || 0;
|
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._angle = Math.atan2(y - displayObject.y, x - displayObject.x);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
if (maxTime > 0)
|
|
|
|
{
|
|
|
|
// We know how many pixels we need to move, but how fast?
|
2013-10-09 03:31:08 +00:00
|
|
|
speed = this.distanceToXY(displayObject, x, y) / (maxTime / 1000);
|
2013-09-04 15:12:58 +00:00
|
|
|
}
|
|
|
|
|
2013-10-08 20:09:46 +00:00
|
|
|
displayObject.body.velocity.x = Math.cos(this._angle) * speed;
|
|
|
|
displayObject.body.velocity.y = Math.sin(this._angle) * speed;
|
|
|
|
|
|
|
|
return this._angle;
|
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Given the angle (in degrees) and speed calculate the velocity and return it as a Point object, or set it to the given point object.
|
|
|
|
* One way to use this is: velocityFromAngle(angle, 200, sprite.velocity) which will set the values directly to the sprites velocity and not create a new Point object.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#velocityFromAngle
|
|
|
|
* @param {number} angle - The angle in degrees calculated in clockwise positive direction (down = 90 degrees positive, right = 0 degrees positive, up = 90 degrees negative)
|
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second sq.
|
|
|
|
* @param {Phaser.Point|object} [point] - The Point object in which the x and y properties will be set to the calculated velocity.
|
|
|
|
* @return {Phaser.Point} - A Point where point.x contains the velocity x value and point.y contains the velocity y value.
|
|
|
|
*/
|
|
|
|
velocityFromAngle: function (angle, speed, point) {
|
|
|
|
|
|
|
|
speed = speed || 60;
|
|
|
|
point = point || new Phaser.Point;
|
|
|
|
|
|
|
|
return point.setTo((Math.cos(this.game.math.degToRad(angle)) * speed), (Math.sin(this.game.math.degToRad(angle)) * speed));
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-10-08 20:09:46 +00:00
|
|
|
/**
|
|
|
|
* Given the rotation (in radians) and speed calculate the velocity and return it as a Point object, or set it to the given point object.
|
|
|
|
* One way to use this is: velocityFromRotation(rotation, 200, sprite.velocity) which will set the values directly to the sprites velocity and not create a new Point object.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#velocityFromRotation
|
|
|
|
* @param {number} rotation - The angle in radians.
|
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second sq.
|
|
|
|
* @param {Phaser.Point|object} [point] - The Point object in which the x and y properties will be set to the calculated velocity.
|
|
|
|
* @return {Phaser.Point} - A Point where point.x contains the velocity x value and point.y contains the velocity y value.
|
|
|
|
*/
|
|
|
|
velocityFromRotation: function (rotation, speed, point) {
|
|
|
|
|
|
|
|
speed = speed || 60;
|
|
|
|
point = point || new Phaser.Point;
|
|
|
|
|
|
|
|
return point.setTo((Math.cos(rotation) * speed), (Math.sin(rotation) * speed));
|
|
|
|
|
|
|
|
},
|
|
|
|
|
2013-09-04 15:12:58 +00:00
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Given the rotation (in radians) and speed calculate the acceleration and return it as a Point object, or set it to the given point object.
|
|
|
|
* One way to use this is: velocityFromRotation(rotation, 200, sprite.velocity) which will set the values directly to the sprites velocity and not create a new Point object.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#accelerationFromRotation
|
|
|
|
* @param {number} rotation - The angle in radians.
|
|
|
|
* @param {number} [speed=60] - The speed it will move, in pixels per second sq.
|
|
|
|
* @param {Phaser.Point|object} [point] - The Point object in which the x and y properties will be set to the calculated acceleration.
|
|
|
|
* @return {Phaser.Point} - A Point where point.x contains the acceleration x value and point.y contains the acceleration y value.
|
|
|
|
*/
|
|
|
|
accelerationFromRotation: function (rotation, speed, point) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
speed = speed || 60;
|
|
|
|
point = point || new Phaser.Point;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return point.setTo((Math.cos(rotation) * speed), (Math.sin(rotation) * speed));
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Sets the acceleration.x/y property on the display object so it will move towards the target at the given speed (in pixels per second sq.)
|
|
|
|
* You must give a maximum speed value, beyond which the display object won't go any faster.
|
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#accelerateToObject
|
|
|
|
* @param {any} displayObject - The display object to move.
|
|
|
|
* @param {any} destination - The display object to move towards. Can be any object but must have visible x/y properties.
|
|
|
|
* @param {number} [speed=60] - The speed it will accelerate in pixels per second.
|
|
|
|
* @param {number} [xSpeedMax=500] - The maximum x velocity the display object can reach.
|
|
|
|
* @param {number} [ySpeedMax=500] - The maximum y velocity the display object can reach.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new trajectory.
|
|
|
|
*/
|
|
|
|
accelerateToObject: function (displayObject, destination, speed, xSpeedMax, ySpeedMax) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
if (typeof speed === 'undefined') { speed = 60; }
|
|
|
|
if (typeof xSpeedMax === 'undefined') { xSpeedMax = 1000; }
|
|
|
|
if (typeof ySpeedMax === 'undefined') { ySpeedMax = 1000; }
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._angle = this.angleBetween(displayObject, destination);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
displayObject.body.acceleration.setTo(Math.cos(this._angle) * speed, Math.sin(this._angle) * speed);
|
|
|
|
displayObject.body.maxVelocity.setTo(xSpeedMax, ySpeedMax);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return this._angle;
|
|
|
|
|
|
|
|
},
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Sets the acceleration.x/y property on the display object so it will move towards the target at the given speed (in pixels per second sq.)
|
|
|
|
* You must give a maximum speed value, beyond which the display object won't go any faster.
|
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#accelerateToPointer
|
|
|
|
* @param {any} displayObject - The display object to move.
|
|
|
|
* @param {Phaser.Pointer} [pointer] - The pointer to move towards. Defaults to Phaser.Input.activePointer.
|
|
|
|
* @param {number} [speed=60] - The speed it will accelerate in pixels per second.
|
|
|
|
* @param {number} [xSpeedMax=500] - The maximum x velocity the display object can reach.
|
|
|
|
* @param {number} [ySpeedMax=500] - The maximum y velocity the display object can reach.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new trajectory.
|
|
|
|
*/
|
|
|
|
accelerateToPointer: function (displayObject, pointer, speed, xSpeedMax, ySpeedMax) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
if (typeof speed === 'undefined') { speed = 60; }
|
|
|
|
if (typeof pointer === 'undefined') { pointer = this.game.input.activePointer; }
|
|
|
|
if (typeof xSpeedMax === 'undefined') { xSpeedMax = 1000; }
|
|
|
|
if (typeof ySpeedMax === 'undefined') { ySpeedMax = 1000; }
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._angle = this.angleToPointer(displayObject, pointer);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
displayObject.body.acceleration.setTo(Math.cos(this._angle) * speed, Math.sin(this._angle) * speed);
|
|
|
|
displayObject.body.maxVelocity.setTo(xSpeedMax, ySpeedMax);
|
|
|
|
|
|
|
|
return this._angle;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Sets the acceleration.x/y property on the display object so it will move towards the x/y coordinates at the given speed (in pixels per second sq.)
|
|
|
|
* You must give a maximum speed value, beyond which the display object won't go any faster.
|
|
|
|
* Note: The display object does not continuously track the target. If the target changes location during transit the display object will not modify its course.
|
|
|
|
* Note: The display object doesn't stop moving once it reaches the destination coordinates.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#accelerateToXY
|
|
|
|
* @param {any} displayObject - The display object to move.
|
|
|
|
* @param {number} x - The x coordinate to accelerate towards.
|
|
|
|
* @param {number} y - The y coordinate to accelerate towards.
|
|
|
|
* @param {number} [speed=60] - The speed it will accelerate in pixels per second.
|
|
|
|
* @param {number} [xSpeedMax=500] - The maximum x velocity the display object can reach.
|
|
|
|
* @param {number} [ySpeedMax=500] - The maximum y velocity the display object can reach.
|
|
|
|
* @return {number} The angle (in radians) that the object should be visually set to in order to match its new trajectory.
|
|
|
|
*/
|
|
|
|
accelerateToXY: function (displayObject, x, y, speed, xSpeedMax, ySpeedMax) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
if (typeof speed === 'undefined') { speed = 60; }
|
|
|
|
if (typeof xSpeedMax === 'undefined') { xSpeedMax = 1000; }
|
|
|
|
if (typeof ySpeedMax === 'undefined') { ySpeedMax = 1000; }
|
|
|
|
|
|
|
|
this._angle = this.angleToXY(displayObject, x, y);
|
|
|
|
|
|
|
|
displayObject.body.acceleration.setTo(Math.cos(this._angle) * speed, Math.sin(this._angle) * speed);
|
|
|
|
displayObject.body.maxVelocity.setTo(xSpeedMax, ySpeedMax);
|
|
|
|
|
|
|
|
return this._angle;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Find the distance between two display objects (like Sprites).
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#distanceBetween
|
|
|
|
* @param {any} source - The Display Object to test from.
|
|
|
|
* @param {any} target - The Display Object to test to.
|
|
|
|
* @return {number} The distance between the source and target objects.
|
|
|
|
*/
|
|
|
|
distanceBetween: function (source, target) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._dx = source.x - target.x;
|
|
|
|
this._dy = source.y - target.y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.sqrt(this._dx * this._dx + this._dy * this._dy);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Find the distance between a display object (like a Sprite) and the given x/y coordinates.
|
|
|
|
* The calculation is made from the display objects x/y coordinate. This may be the top-left if its anchor hasn't been changed.
|
|
|
|
* If you need to calculate from the center of a display object instead use the method distanceBetweenCenters()
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#distanceToXY
|
|
|
|
* @param {any} displayObject - The Display Object to test from.
|
|
|
|
* @param {number} x - The x coordinate to move towards.
|
|
|
|
* @param {number} y - The y coordinate to move towards.
|
|
|
|
* @return {number} The distance between the object and the x/y coordinates.
|
|
|
|
*/
|
|
|
|
distanceToXY: function (displayObject, x, y) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._dx = displayObject.x - x;
|
|
|
|
this._dy = displayObject.y - y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.sqrt(this._dx * this._dx + this._dy * this._dy);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Find the distance between a display object (like a Sprite) and a Pointer. If no Pointer is given the Input.activePointer is used.
|
|
|
|
* The calculation is made from the display objects x/y coordinate. This may be the top-left if its anchor hasn't been changed.
|
|
|
|
* If you need to calculate from the center of a display object instead use the method distanceBetweenCenters()
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#distanceToPointer
|
|
|
|
* @param {any} displayObject - The Display Object to test from.
|
|
|
|
* @param {Phaser.Pointer} [pointer] - The Phaser.Pointer to test to. If none is given then Input.activePointer is used.
|
|
|
|
* @return {number} The distance between the object and the Pointer.
|
|
|
|
*/
|
|
|
|
distanceToPointer: function (displayObject, pointer) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
pointer = pointer || this.game.input.activePointer;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 04:13:38 +00:00
|
|
|
this._dx = displayObject.worldX - pointer.x;
|
|
|
|
this._dy = displayObject.worldY - pointer.y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.sqrt(this._dx * this._dx + this._dy * this._dy);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Find the angle in radians between two display objects (like Sprites).
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#angleBetween
|
|
|
|
* @param {any} source - The Display Object to test from.
|
|
|
|
* @param {any} target - The Display Object to test to.
|
|
|
|
* @return {number} The angle in radians between the source and target display objects.
|
|
|
|
*/
|
|
|
|
angleBetween: function (source, target) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._dx = target.x - source.x;
|
|
|
|
this._dy = target.y - source.y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.atan2(this._dy, this._dx);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-09 03:31:08 +00:00
|
|
|
* Find the angle in radians between a display object (like a Sprite) and the given x/y coordinate.
|
|
|
|
*
|
|
|
|
* @method Phaser.Physics.Arcade#angleToXY
|
|
|
|
* @param {any} displayObject - The Display Object to test from.
|
|
|
|
* @param {number} x - The x coordinate to get the angle to.
|
|
|
|
* @param {number} y - The y coordinate to get the angle to.
|
|
|
|
* @return {number} The angle in radians between displayObject.x/y to Pointer.x/y
|
|
|
|
*/
|
|
|
|
angleToXY: function (displayObject, x, y) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
this._dx = x - displayObject.x;
|
|
|
|
this._dy = y - displayObject.y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.atan2(this._dy, this._dx);
|
2013-09-04 15:12:58 +00:00
|
|
|
|
|
|
|
},
|
|
|
|
|
|
|
|
/**
|
2013-10-08 20:09:46 +00:00
|
|
|
* Find the angle in radians between a display object (like a Sprite) and a Pointer, taking their x/y and center into account.
|
|
|
|
*
|
2013-10-09 03:31:08 +00:00
|
|
|
* @method Phaser.Physics.Arcade#angleToPointer
|
2013-10-08 20:09:46 +00:00
|
|
|
* @param {any} displayObject - The Display Object to test from.
|
|
|
|
* @param {Phaser.Pointer} [pointer] - The Phaser.Pointer to test to. If none is given then Input.activePointer is used.
|
2013-10-09 03:31:08 +00:00
|
|
|
* @return {number} The angle in radians between displayObject.x/y to Pointer.x/y
|
2013-10-08 20:09:46 +00:00
|
|
|
*/
|
2013-10-09 03:31:08 +00:00
|
|
|
angleToPointer: function (displayObject, pointer) {
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-08 20:09:46 +00:00
|
|
|
pointer = pointer || this.game.input.activePointer;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 04:13:38 +00:00
|
|
|
this._dx = pointer.worldX - displayObject.x;
|
|
|
|
this._dy = pointer.worldY - displayObject.y;
|
2013-09-04 15:12:58 +00:00
|
|
|
|
2013-10-09 03:31:08 +00:00
|
|
|
return Math.atan2(this._dy, this._dx);
|
2013-10-08 20:09:46 +00:00
|
|
|
|
2013-09-04 15:12:58 +00:00
|
|
|
}
|
|
|
|
|
2013-09-03 14:35:40 +00:00
|
|
|
};
|