Skip to content

Commit 483a3b6

Browse files
committed
Fix for DisplayObject/DisplayObjectContainer - getting dimensions or bounds do NOT retrieve proper values
* Documentation * TypeScript Defs * Nothing, it's a bug fix Describe the changes below: I noticed that getting dimensions or bounds changed in Phaser 2.6.1 and it was bugged - returned dimensions were doubled in the direction of the scaling for example, but the nice thing was that this time the dimensions included the rotation of the object - which I think should be the default behavior. It also bugged getLocalBounds which started returning global getBounds(); When I checked the previous version of phaser 2.5.0 - total different story. getLocalBounds returns the object without any transformations to it. Getting width and height works ok, but rotation wasn't calculated to the dimensions at all. In all cases only getBounds returned proper dimensions, which is obviously not enough and this is also a very important issue to be resolved as soon as possible since it's a major core component feature used all the time. That's why I decided to spare the time and hopefully find a good fix for all of this mess and I think I finally got there and tried to make the changes as much as possible with your Code of Conduct. This is actually the first time I am requesting a pull so I hope it will do some good. I did compare my results with how Flash handles dimensions - they match, so I do hope I didn't miss something and believe you guys would make sure everything works ok. To help you with reviewing and possibly (and hopefully) accepting this pull request I've made available online 3 demos of the issues and with demo of the fix of course: 1. http://www.nedyalkov.net/filip/demos/phaser/IncorrectDisplayObjectDimensionsDemo_v2.5.0/ 2. http://www.nedyalkov.net/filip/demos/phaser/IncorrectDisplayObjectDimensionsDemo_v2.6.1/ 3. http://www.nedyalkov.net/filip/demos/phaser/IncorrectDisplayObjectDimensionsDemoFixed_v2.6.1/ Here is a zip file of the demo projects (build with VS2015): http://www.nedyalkov.net/filip/demos/phaser/IncorrectDisplayObjectDimensionsDemos.zip I really hope to see this FIX in the next version - would help me and a lot of people I guess to get the job done properly! Thank you!
1 parent b405570 commit 483a3b6

4 files changed

Lines changed: 58 additions & 41 deletions

File tree

src/pixi/display/DisplayObject.js

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -313,21 +313,21 @@ PIXI.DisplayObject.prototype = {
313313
* the new, updated, worldTransform property, along with the parent transform used.
314314
*
315315
* @method PIXI.DisplayObject#updateTransform
316-
* @param {PIXI.DisplayObject} [parent] - Optional parent to calculate this DisplayObjects transform from.
317-
* @return {PIXI.DisplayObject} - A reference to this DisplayObject.
316+
* @param {PIXI.DisplayObject} [targetCoordinateSpace] Optional targetCoordinateSpace to calculate this DisplayObjects transform from.
317+
* @return {PIXI.DisplayObject} A reference to this DisplayObject.
318318
*/
319-
updateTransform: function (parent) {
319+
updateTransform: function (targetCoordinateSpace) {
320320

321-
if (!parent && !this.parent && !this.game)
321+
if (!targetCoordinateSpace && !this.parent && !this.game)
322322
{
323323
return this;
324324
}
325325

326326
var p = this.parent;
327327

328-
if (parent)
328+
if (targetCoordinateSpace)
329329
{
330-
p = parent;
330+
p = targetCoordinateSpace;
331331
}
332332
else if (!this.parent)
333333
{

src/pixi/display/DisplayObjectContainer.js

Lines changed: 46 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ PIXI.DisplayObjectContainer.prototype.constructor = PIXI.DisplayObjectContainer;
4949
Object.defineProperty(PIXI.DisplayObjectContainer.prototype, 'width', {
5050

5151
get: function() {
52-
return this.scale.x * this.getLocalBounds().width;
52+
return this.getLocalBounds().width;
5353
},
5454

5555
set: function(value) {
@@ -78,7 +78,7 @@ Object.defineProperty(PIXI.DisplayObjectContainer.prototype, 'width', {
7878
Object.defineProperty(PIXI.DisplayObjectContainer.prototype, 'height', {
7979

8080
get: function() {
81-
return this.scale.y * this.getLocalBounds().height;
81+
return this.getLocalBounds().height;
8282
},
8383

8484
set: function(value) {
@@ -290,16 +290,17 @@ PIXI.DisplayObjectContainer.prototype.removeChildren = function(beginIndex, endI
290290
* Updates the transform on all children of this container for rendering
291291
*
292292
* @method updateTransform
293+
* @param {PIXI.DisplayObject} [targetCoordinateSpace] Optional targetCoordinateSpace to calculate this DisplayObjects transform from.
293294
* @private
294295
*/
295-
PIXI.DisplayObjectContainer.prototype.updateTransform = function()
296+
PIXI.DisplayObjectContainer.prototype.updateTransform = function (targetCoordinateSpace)
296297
{
297298
if (!this.visible)
298299
{
299300
return;
300301
}
301302

302-
this.displayObjectUpdateTransform();
303+
this.displayObjectUpdateTransform(targetCoordinateSpace);
303304

304305
if (this._cacheAsBitmap)
305306
{
@@ -319,16 +320,43 @@ PIXI.DisplayObjectContainer.prototype.displayObjectContainerUpdateTransform = PI
319320
* Retrieves the bounds of the displayObjectContainer as a rectangle. The bounds calculation takes all visible children into consideration.
320321
*
321322
* @method getBounds
323+
* @param {PIXI.DisplayObject | PIXI.Matrix} [targetCoordinateSpace]
322324
* @return {Rectangle} The rectangular bounding area
323325
*/
324-
PIXI.DisplayObjectContainer.prototype.getBounds = function()
326+
PIXI.DisplayObjectContainer.prototype.getBounds = function (targetCoordinateSpace)
325327
{
326328
if (this.children.length === 0)
327329
{
328330
return PIXI.EmptyRectangle;
329331
}
330332

331-
this.updateTransform();
333+
var isTargetCoordinateSpaceDisplayObject = targetCoordinateSpace && targetCoordinateSpace instanceof PIXI.DisplayObject;
334+
var i;
335+
336+
if (isTargetCoordinateSpaceDisplayObject)
337+
{
338+
var matrixCache = this.worldTransform;
339+
340+
this.worldTransform = new PIXI.Matrix();
341+
342+
for (i = 0; i < this.children.length; i++)
343+
{
344+
this.children[i].updateTransform();
345+
}
346+
347+
var targetCoordinateSpaceMatrixCache = targetCoordinateSpace.worldTransform;
348+
targetCoordinateSpace.worldTransform = PIXI.identityMatrix;
349+
}
350+
351+
if (!isTargetCoordinateSpaceDisplayObject || isTargetCoordinateSpaceDisplayObject && targetCoordinateSpace !== this)
352+
{
353+
this.updateTransform(targetCoordinateSpace);
354+
}
355+
356+
if (isTargetCoordinateSpaceDisplayObject)
357+
{
358+
targetCoordinateSpace.worldTransform = targetCoordinateSpaceMatrixCache;
359+
}
332360

333361
var minX = Infinity;
334362
var minY = Infinity;
@@ -342,7 +370,7 @@ PIXI.DisplayObjectContainer.prototype.getBounds = function()
342370

343371
var childVisible = false;
344372

345-
for (var i = 0; i < this.children.length; i++)
373+
for (i = 0; i < this.children.length; i++)
346374
{
347375
var child = this.children[i];
348376

@@ -365,6 +393,16 @@ PIXI.DisplayObjectContainer.prototype.getBounds = function()
365393
maxY = maxY > childMaxY ? maxY : childMaxY;
366394
}
367395

396+
if (isTargetCoordinateSpaceDisplayObject)
397+
{
398+
this.worldTransform = matrixCache;
399+
400+
for (i = 0; i < this.children.length; i++)
401+
{
402+
this.children[i].updateTransform();
403+
}
404+
}
405+
368406
if (!childVisible)
369407
{
370408
return PIXI.EmptyRectangle;
@@ -388,25 +426,7 @@ PIXI.DisplayObjectContainer.prototype.getBounds = function()
388426
*/
389427
PIXI.DisplayObjectContainer.prototype.getLocalBounds = function()
390428
{
391-
var matrixCache = this.worldTransform;
392-
393-
this.worldTransform = PIXI.identityMatrix;
394-
395-
for (var i = 0; i < this.children.length; i++)
396-
{
397-
this.children[i].updateTransform();
398-
}
399-
400-
var bounds = this.getBounds();
401-
402-
this.worldTransform = matrixCache;
403-
404-
for (i = 0; i < this.children.length; i++)
405-
{
406-
this.children[i].updateTransform();
407-
}
408-
409-
return bounds;
429+
return this.getBounds(this.parent);
410430
};
411431

412432
/**

typescript/pixi.comments.d.ts

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -796,9 +796,7 @@ declare module PIXI {
796796
y: number;
797797

798798
click(e: InteractionData): void;
799-
displayObjectUpdateTransform(): void;
800-
getBounds(matrix?: Matrix): Rectangle;
801-
getLocalBounds(): Rectangle;
799+
displayObjectUpdateTransform(targetCoordinateSpace?: PIXI.DisplayObject): void;
802800
generateTexture(resolution?: number, scaleMode?: number, renderer?: PixiRenderer | number): RenderTexture;
803801
mousedown(e: InteractionData): void;
804802
mouseout(e: InteractionData): void;
@@ -818,7 +816,7 @@ declare module PIXI {
818816
touchendoutside(e: InteractionData): void;
819817
touchstart(e: InteractionData): void;
820818
touchmove(e: InteractionData): void;
821-
updateTransform(parent?: PIXI.DisplayObjectContainer): void;
819+
updateTransform(targetCoordinateSpace?: PIXI.DisplayObject): void;
822820

823821
}
824822

@@ -881,9 +879,10 @@ declare module PIXI {
881879

882880
/**
883881
* Retrieves the bounds of the displayObjectContainer as a rectangle. The bounds calculation takes all visible children into consideration.
882+
* @param targetCoordinateSpace The targetCoordinateSpace to calculate the bounds from.
884883
* @return The rectangular bounding area
885884
*/
886-
getBounds(): Rectangle;
885+
getBounds(targetCoordinateSpace?: PIXI.DisplayObject | Matrix): Rectangle;
887886

888887
/**
889888
* Returns the child at the specified index

typescript/pixi.d.ts

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -484,9 +484,7 @@ declare module PIXI {
484484
y: number;
485485

486486
click(e: InteractionData): void;
487-
displayObjectUpdateTransform(): void;
488-
getBounds(matrix?: Matrix): Rectangle;
489-
getLocalBounds(): Rectangle;
487+
displayObjectUpdateTransform(targetCoordinateSpace?: PIXI.DisplayObject): void
490488
generateTexture(resolution?: number, scaleMode?: number, renderer?: PixiRenderer | number): RenderTexture;
491489
mousedown(e: InteractionData): void;
492490
mouseout(e: InteractionData): void;
@@ -521,7 +519,7 @@ declare module PIXI {
521519

522520
addChild(child: DisplayObject): DisplayObject;
523521
addChildAt(child: DisplayObject, index: number): DisplayObject;
524-
getBounds(): Rectangle;
522+
getBounds(targetCoordinateSpace?: PIXI.DisplayObject | Matrix): Rectangle;
525523
getChildAt(index: number): DisplayObject;
526524
getChildIndex(child: DisplayObject): number;
527525
getLocalBounds(): Rectangle;

0 commit comments

Comments
 (0)