Skip to content

Commit dfb22f1

Browse files
committed
Tracked down an evil bug in Group.swap that caused the linked list to get corrupted in an upward (B to A) neighbour swap.
1 parent 8b793cd commit dfb22f1

8 files changed

Lines changed: 494 additions & 129 deletions

File tree

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ Version 1.1.3 - in build
4646
* New: StageScaleMode.forceOrientation allows you to lock your game to one orientation and display a Sprite (i.e. a "please rotate" screen) when incorrect.
4747
* New: World.visible boolean added, toggles rendering of the world on/off entirely.
4848
* New: Polygon class & drawPolygon method added to Graphics (thanks rjimenezda)
49+
* New: Added Group.iterate, a powerful way to count or return child that match a certain criteria. Refactored Group to use iterate, lots of repeated code cut.
4950
* Fixed: Mouse.stop now uses the true useCapture, which means the event listeners stop listening correctly (thanks beeglebug)
5051
* Fixed: Input Keyboard example fix (thanks Atrodilla)
5152
* Updated: ArcadePhysics.updateMotion applies the dt to the velocity calculations as well as position now (thanks jcs)

examples/wip/sort.js

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
var game = new Phaser.Game(800, 600, Phaser.CANVAS, 'phaser-example', { preload: preload, create: create, update: update, render: render });
2+
3+
function preload() {
4+
5+
game.load.image('phaser', 'assets/sprites/phaser-dude.png');
6+
game.load.spritesheet('veggies', 'assets/sprites/fruitnveg32wh37.png', 32, 32);
7+
8+
}
9+
10+
var sprite;
11+
var group;
12+
var oldY = 0;
13+
14+
function create() {
15+
16+
game.stage.backgroundColor = '#2d2d2d';
17+
18+
// sprite = game.add.sprite(32, 200, 'phaser');
19+
// sprite.name = 'phaser-dude';
20+
21+
group = game.add.group();
22+
23+
sprite = group.create(300, 200, 'phaser');
24+
sprite.name = 'phaser-dude';
25+
26+
for (var i = 0; i < 10; i++)
27+
{
28+
var c = group.create(100 + Math.random() * 700, game.world.randomY, 'veggies', game.rnd.integerInRange(0, 36));
29+
c.name = 'veg' + i;
30+
}
31+
32+
game.input.onUp.add(sortGroup, this);
33+
game.input.keyboard.addKeyCapture([ Phaser.Keyboard.LEFT, Phaser.Keyboard.RIGHT, Phaser.Keyboard.UP, Phaser.Keyboard.DOWN ]);
34+
35+
}
36+
37+
function sortGroup () {
38+
39+
console.log('%c ', 'background: #efefef');
40+
group.sort();
41+
group.dump(false);
42+
43+
}
44+
45+
function update() {
46+
47+
sprite.body.velocity.x = 0;
48+
sprite.body.velocity.y = 0;
49+
50+
if (game.input.keyboard.isDown(Phaser.Keyboard.LEFT))
51+
{
52+
sprite.body.velocity.x = -200;
53+
}
54+
else if (game.input.keyboard.isDown(Phaser.Keyboard.RIGHT))
55+
{
56+
sprite.body.velocity.x = 200;
57+
}
58+
59+
if (game.input.keyboard.isDown(Phaser.Keyboard.UP))
60+
{
61+
sprite.body.velocity.y = -200;
62+
}
63+
else if (game.input.keyboard.isDown(Phaser.Keyboard.DOWN))
64+
{
65+
sprite.body.velocity.y = 200;
66+
}
67+
68+
if (sprite.y !== oldY)
69+
{
70+
// console.log('sorted');
71+
// group.sort();
72+
// oldY = sprite.y;
73+
}
74+
75+
}
76+
77+
function render() {
78+
79+
// game.debug.renderText(group.cursor.name, 32, 32);
80+
// game.debug.renderInputInfo(32, 32);
81+
82+
}

examples/wip/swap.js

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,89 @@
1+
var game = new Phaser.Game(800, 600, Phaser.CANVAS, 'phaser-example', { preload: preload, create: create, update: update, render: render });
2+
3+
function preload() {
4+
5+
game.load.image('phaser', 'assets/sprites/phaser-dude.png');
6+
game.load.spritesheet('veggies', 'assets/sprites/fruitnveg32wh37.png', 32, 32);
7+
8+
}
9+
10+
var group;
11+
var start = false;
12+
var swapCount = 0;
13+
var time = 0;
14+
var test = 0;
15+
16+
function create() {
17+
18+
game.stage.backgroundColor = '#2d2d2d';
19+
20+
group = game.add.group();
21+
22+
for (var i = 0; i < 10; i++)
23+
{
24+
var c = group.create(100 + Math.random() * 700, game.world.randomY, 'veggies', game.rnd.integerInRange(0, 36));
25+
c.name = 'veg' + i;
26+
}
27+
28+
test = group.length;
29+
30+
game.input.onUp.add(toggleSwap, this);
31+
32+
}
33+
34+
function toggleSwap () {
35+
36+
if (start)
37+
{
38+
start = false;
39+
}
40+
else
41+
{
42+
start = true;
43+
}
44+
45+
}
46+
47+
function update() {
48+
49+
if (start && game.time.now > time)
50+
{
51+
var a = group.getRandom();
52+
var b = group.getRandom();
53+
54+
if (a.name !== b.name)
55+
{
56+
console.log('************************ NEW ROUND *********************');
57+
group.dump(true);
58+
console.log('Group Size: ' + group.length);
59+
group.swap(a, b);
60+
swapCount++;
61+
62+
if (group.length !== test)
63+
{
64+
start = false;
65+
console.log('************************ SHIT *********************');
66+
group.dump(true);
67+
console.log('************************ SHIT *********************');
68+
}
69+
70+
if (group.validate() == false)
71+
{
72+
start = false;
73+
console.log('************************ VALIDATE FAIL *********************');
74+
group.dump(true);
75+
console.log('************************ VALIDATE FAIL *********************');
76+
}
77+
78+
}
79+
80+
time = game.time.now + 100;
81+
}
82+
83+
}
84+
85+
function render() {
86+
87+
game.debug.renderText('Swap: ' + swapCount, 32, 32);
88+
89+
}

resources/Project Templates/Basic/MainMenu.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ BasicGame.MainMenu.prototype = {
1010

1111
create: function () {
1212

13-
// We've already preloaded our assets, so let's kick right into the Main Menu itself
13+
// We've already preloaded our assets, so let's kick right into the Main Menu itself.
1414
// Here all we're doing is playing some music and adding a picture and button
1515
// Naturally I expect you to do something significantly better :)
1616

resources/Project Templates/Basic/Preloader.js

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,13 @@ BasicGame.Preloader.prototype = {
1717
this.background = this.add.sprite(0, 0, 'preloaderBackground');
1818
this.preloadBar = this.add.sprite(300, 400, 'preloaderBar');
1919

20-
// This sets the preloadBar sprite as a loader sprite, basically
21-
// what that does is automatically crop the sprite from 0 to full-width
20+
// This sets the preloadBar sprite as a loader sprite.
21+
// What that does is automatically crop the sprite from 0 to full-width
2222
// as the files below are loaded in.
2323
this.load.setPreloadSprite(this.preloadBar);
2424

25-
// Here we load most of the assets our game needs
25+
// Here we load the rest of the assets our game needs.
26+
// As this is just a Project Template I've not provided these assets, swap them for your own.
2627
this.load.image('titlepage', 'images/title.jpg');
2728
this.load.atlas('playButton', 'images/play_button.png', 'images/play_button.json');
2829
this.load.audio('titleMusic', ['audio/main_menu.mp3']);
@@ -33,7 +34,7 @@ BasicGame.Preloader.prototype = {
3334

3435
create: function () {
3536

36-
// Once the load has finished we disable the crop because we're going to sit in the update loop for a short while
37+
// Once the load has finished we disable the crop because we're going to sit in the update loop for a short while as the music decodes
3738
this.preloadBar.cropEnabled = false;
3839

3940
},
@@ -51,7 +52,7 @@ BasicGame.Preloader.prototype = {
5152

5253
if (this.cache.isSoundDecoded('titleMusic') && this.ready == false)
5354
{
54-
this.ready = false;
55+
this.ready = true;
5556
this.game.state.start('MainMenu');
5657
}
5758

resources/Project Templates/Basic/index.html

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
<head>
44
<meta charset="UTF-8" />
55
<title>Phaser Basic Project Template</title>
6+
<script src="phaser.min.js"></script>
67
<script src="Boot.js"></script>
78
<script src="Preloader.js"></script>
89
<script src="MainMenu.js"></script>
@@ -17,7 +18,7 @@
1718
window.onload = function() {
1819

1920
// Create your Phaser game and inject it into the gameContainer div.
20-
// We did it in a window.onload event, but you can do it anywhere (requireJS load, anonymous function, jQuery dom ready, etc - whatever floats your boat)
21+
// We did it in a window.onload event, but you can do it anywhere (requireJS load, anonymous function, jQuery dom ready, - whatever floats your boat)
2122
var game = new Phaser.Game(1024, 768, Phaser.AUTO, 'gameContainer');
2223

2324
// Add the States your game has.

src/core/Game.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -425,6 +425,8 @@ Phaser.Game.prototype = {
425425
if (this._paused)
426426
{
427427
this.renderer.render(this.stage._stage);
428+
this.plugins.render();
429+
this.state.render();
428430
}
429431
else
430432
{

0 commit comments

Comments
 (0)