Skip to content

Commit 11fdd62

Browse files
committed
World.destroy incorrectly clashed with the Group.destroy method it over-rode, renamed to World.shutdown and updated StateManager accordingly.
World.shutdown now removes all children iteratively, calling destroy on each one, ultimately performing a soft reset of the World. Objects with a scale.x or y of 0 are no longer considered valid for input (fix phaserjs#602) InputHandler will set the browser pointer back to default if destroyed while over (fix phaserjs#602) Group.destroy has a new parameter: `soft`. A soft destruction won't remove the Group from its parent or null game references. Default is `false`. InputHandler.validForInput is a new method that checks if the handler and its owner should be considered for Pointer input handling or not. Group.replace will now return the old child, the one that was replaced in the Group.
1 parent 8010d24 commit 11fdd62

7 files changed

Lines changed: 79 additions & 11 deletions

File tree

README.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,10 @@ Bug Fixes
6969
* Button.onInputUpHandler wouldn't set an upFrame for a frame ID of zero, made the check more strict.
7070
* Fixed the Loader.preloadSprite crop effect on WebGL.
7171
* Fixed Grunt script that stopped the P2 constraint classes from building properly.
72+
* World.destroy incorrectly clashed with the Group.destroy method it over-rode, renamed to World.shutdown and updated StateManager accordingly.
73+
* World.shutdown now removes all children iteratively, calling destroy on each one, ultimately performing a soft reset of the World.
74+
* Objects with a scale.x or y of 0 are no longer considered valid for input (fix #602)
75+
* InputHandler will set the browser pointer back to default if destroyed while over (fix #602)
7276

7377

7478
Updated:
@@ -81,6 +85,9 @@ Updated:
8185
* Lots of TypeScript definitions updates (thanks as always to clark for these)
8286
* Removed Device.patchAndroidClearRectBug as it's no longer used internally.
8387
* Math.wrapAngle now supports radians (thanks Cryszon, #597)
88+
* Group.replace will now return the old child, the one that was replaced in the Group.
89+
* Group.destroy has a new parameter: `soft`. A soft destruction won't remove the Group from its parent or null game references. Default is `false`.
90+
* InputHandler.validForInput is a new method that checks if the handler and its owner should be considered for Pointer input handling or not.
8491

8592

8693
New Features:

src/core/Group.js

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -561,6 +561,7 @@ Phaser.Group.prototype.getIndex = function (child) {
561561
* @method Phaser.Group#replace
562562
* @param {*} oldChild - The child in this Group that will be replaced.
563563
* @param {*} newChild - The child to be inserted into this Group.
564+
* @return {*} Returns the oldChild that was replaced within this Group.
564565
*/
565566
Phaser.Group.prototype.replace = function (oldChild, newChild) {
566567

@@ -579,9 +580,13 @@ Phaser.Group.prototype.replace = function (oldChild, newChild) {
579580
}
580581
}
581582

582-
this.removeChild(oldChild);
583+
var temp = oldChild;
584+
585+
this.remove(temp);
583586

584587
this.addAt(newChild, index);
588+
589+
return temp;
585590
}
586591

587592
}
@@ -1420,12 +1425,14 @@ Phaser.Group.prototype.removeBetween = function (startIndex, endIndex) {
14201425
*
14211426
* @method Phaser.Group#destroy
14221427
* @param {boolean} [destroyChildren=true] - Should every child of this Group have its destroy method called?
1428+
* @param {boolean} [soft=false] - A 'soft destroy' (set to true) doesn't remove this Group from its parent or null the game reference. Set to false and it does.
14231429
*/
1424-
Phaser.Group.prototype.destroy = function (destroyChildren) {
1430+
Phaser.Group.prototype.destroy = function (destroyChildren, soft) {
14251431

14261432
if (this.game === null) { return; }
14271433

14281434
if (typeof destroyChildren === 'undefined') { destroyChildren = true; }
1435+
if (typeof soft === 'undefined') { soft = false; }
14291436

14301437
if (destroyChildren)
14311438
{
@@ -1446,13 +1453,16 @@ Phaser.Group.prototype.destroy = function (destroyChildren) {
14461453
this.removeAll();
14471454
}
14481455

1449-
this.parent.removeChild(this);
1456+
this.cursor = null;
14501457

1451-
this.game = null;
1458+
if (!soft)
1459+
{
1460+
this.parent.removeChild(this);
14521461

1453-
this.exists = false;
1462+
this.game = null;
14541463

1455-
this.cursor = null;
1464+
this.exists = false;
1465+
}
14561466

14571467
}
14581468

src/core/StateManager.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,7 @@ Phaser.StateManager.prototype = {
284284
{
285285
this.game.tweens.removeAll();
286286

287-
this.game.world.destroy();
287+
this.game.world.shutdown();
288288

289289
this.game.physics.clear();
290290

src/core/World.js

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -94,15 +94,16 @@ Phaser.World.prototype.setBounds = function (x, y, width, height) {
9494

9595
/**
9696
* Destroyer of worlds.
97-
* @method Phaser.World#destroy
97+
* @method Phaser.World#shutdown
9898
*/
99-
Phaser.World.prototype.destroy = function () {
99+
Phaser.World.prototype.shutdown = function () {
100100

101101
this.camera.reset();
102102

103103
this.game.input.reset(true);
104104

105-
this.removeAll();
105+
// World is a Group, so run a soft destruction on this and all children.
106+
this.destroy(true, true);
106107

107108
}
108109

src/gameobjects/Text.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,10 @@ Phaser.Text = function (game, x, y, text, style) {
2929
{
3030
text = ' ';
3131
}
32+
else
33+
{
34+
text = text.toString();
35+
}
3236

3337
/**
3438
* @property {Phaser.Game} game - A reference to the currently running Game.

src/input/InputHandler.js

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,12 @@ Phaser.InputHandler = function (sprite) {
4040
*/
4141
this.useHandCursor = false;
4242

43+
/**
44+
* @property {boolean} _setHandCursor - Did this Sprite trigger the hand cursor?
45+
* @private
46+
*/
47+
this._setHandCursor = false;
48+
4349
/**
4450
* @property {boolean} isDragged - true if the Sprite is being currently dragged.
4551
* @default
@@ -302,6 +308,12 @@ Phaser.InputHandler.prototype = {
302308

303309
if (this.enabled)
304310
{
311+
if (this._setHandCursor)
312+
{
313+
this.game.canvas.style.cursor = "default";
314+
this._setHandCursor = false;
315+
}
316+
305317
this.enabled = false;
306318

307319
this.game.input.interactiveItems.remove(this);
@@ -314,6 +326,37 @@ Phaser.InputHandler.prototype = {
314326

315327
},
316328

329+
/**
330+
* Checks if the object this InputHandler is bound to is valid for consideration in the Pointer move event.
331+
* This is called by Phaser.Pointer and shouldn't typically be called directly.
332+
*
333+
* @method Phaser.InputHandler#validForInput
334+
* @protected
335+
* @param {number} highestID - The highest ID currently processed by the Pointer.
336+
* @param {number} highestRenderID - The highest Render Order ID currently processed by the Pointer.
337+
* @return {boolean} True if the object this InputHandler is bound to should be considered as valid for input detection.
338+
*/
339+
validForInput: function (highestID, highestRenderID) {
340+
341+
if (this.sprite.scale.x === 0 || this.sprite.scale.y === 0)
342+
{
343+
return false;
344+
}
345+
346+
if (this.pixelPerfectClick || this.pixelPerfectOver)
347+
{
348+
return true;
349+
}
350+
351+
if (this.priorityID > highestID || (this.priorityID === highestID && this.sprite._cache[3] < highestRenderID))
352+
{
353+
return true;
354+
}
355+
356+
return false;
357+
358+
},
359+
317360
/**
318361
* The x coordinate of the Input pointer, relative to the top-left of the parent Sprite.
319362
* This value is only set when the pointer is over this Sprite.
@@ -679,6 +722,7 @@ Phaser.InputHandler.prototype = {
679722
if (this.useHandCursor && this._pointerData[pointer.id].isDragged === false)
680723
{
681724
this.game.canvas.style.cursor = "pointer";
725+
this._setHandCursor = false;
682726
}
683727

684728
this.sprite.events.onInputOver.dispatch(this.sprite, pointer);
@@ -707,6 +751,7 @@ Phaser.InputHandler.prototype = {
707751
if (this.useHandCursor && this._pointerData[pointer.id].isDragged === false)
708752
{
709753
this.game.canvas.style.cursor = "default";
754+
this._setHandCursor = false;
710755
}
711756

712757
if (this.sprite && this.sprite.events)
@@ -796,6 +841,7 @@ Phaser.InputHandler.prototype = {
796841
if (this.useHandCursor)
797842
{
798843
this.game.canvas.style.cursor = "default";
844+
this._setHandCursor = false;
799845
}
800846
}
801847

src/input/Pointer.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -367,7 +367,7 @@ Phaser.Pointer.prototype = {
367367
do
368368
{
369369
// If the object is using pixelPerfect checks, or has a higher InputManager.PriorityID OR if the priority ID is the same as the current highest AND it has a higher renderOrderID, then set it to the top
370-
if (currentNode.pixelPerfectClick || currentNode.pixelPerfectOver || currentNode.priorityID > this._highestInputPriorityID || (currentNode.priorityID === this._highestInputPriorityID && currentNode.sprite._cache[3] < this._highestRenderOrderID))
370+
if (currentNode.validForInput(this._highestInputPriorityID, this._highestRenderOrderID))
371371
{
372372
if ((!fromClick && currentNode.checkPointerOver(this)) || (fromClick && currentNode.checkPointerDown(this)))
373373
{

0 commit comments

Comments
 (0)