Browse code

update shmuprpg

devnewton authored on 12/10/2016 13:09:26
Showing 23 changed files
... ...
@@ -150,73 +150,61 @@ var __makeRelativeRequire = function(require, mappings, pref) {
150 150
 };
151 151
 require.register("ShmuprpgApp.ts", function(exports, require, module) {
152 152
 "use strict";
153
-var ShmuprpgGame_ts_1 = require("./ShmuprpgGame.ts");
153
+const ShmuprpgGame_ts_1 = require("./ShmuprpgGame.ts");
154 154
 new ShmuprpgGame_ts_1.ShmuprpgGame();
155
-//# sourceMappingURL=ShmuprpgApp.js.map
155
+
156
+
156 157
 });
157 158
 
158 159
 require.register("ShmuprpgGame.ts", function(exports, require, module) {
159 160
 "use strict";
160
-var __extends = (this && this.__extends) || function (d, b) {
161
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
162
-    function __() { this.constructor = d; }
163
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
164
-};
165
-var Intro_ts_1 = require("./states/Intro.ts");
166
-var Title_ts_1 = require("./states/Title.ts");
167
-var Level_ts_1 = require("./states/Level.ts");
168
-var GameOver_ts_1 = require("./states/GameOver.ts");
169
-var Controls_ts_1 = require("./utils/Controls.ts");
170
-var ShmuprpgGame = (function (_super) {
171
-    __extends(ShmuprpgGame, _super);
172
-    function ShmuprpgGame() {
173
-        var _this = this;
174
-        _super.call(this, 1920, 1080, Phaser.CANVAS, 'game', {
175
-            preload: function () { return _this.preloadGame(); },
176
-            create: function () { return _this.createGame(); }
161
+const Intro_ts_1 = require("./states/Intro.ts");
162
+const Title_ts_1 = require("./states/Title.ts");
163
+const Level_ts_1 = require("./states/Level.ts");
164
+const GameOver_ts_1 = require("./states/GameOver.ts");
165
+const Controls_ts_1 = require("./utils/Controls.ts");
166
+class ShmuprpgGame extends Phaser.Game {
167
+    constructor() {
168
+        super(1920, 1080, Phaser.CANVAS, 'game', {
169
+            preload: () => this.preloadGame(),
170
+            create: () => this.createGame()
177 171
         });
178 172
         this.state.add('Intro', Intro_ts_1.Intro);
179 173
         this.state.add('Title', Title_ts_1.Title);
180 174
         this.state.add('Level', Level_ts_1.Level);
181 175
         this.state.add('GameOver', GameOver_ts_1.GameOver);
182 176
     }
183
-    ShmuprpgGame.prototype.preloadGame = function () {
177
+    preloadGame() {
184 178
         this.scale.scaleMode = Phaser.ScaleManager.SHOW_ALL;
185 179
         this.scale.fullScreenScaleMode = Phaser.ScaleManager.SHOW_ALL;
186 180
         this.scale.pageAlignHorizontally = true;
187 181
         this.scale.pageAlignVertically = true;
188
-    };
189
-    ShmuprpgGame.prototype.createGame = function () {
182
+    }
183
+    createGame() {
190 184
         this.controls = new Controls_ts_1.Controls(this);
191 185
         this.state.start('Level');
192
-    };
193
-    ShmuprpgGame.prototype.addSpriteAnimation = function (sprite, animationName, frameCount) {
186
+    }
187
+    addSpriteAnimation(sprite, animationName, frameCount) {
194 188
         return sprite.animations.add(animationName, this.genAnimArray(animationName, frameCount));
195
-    };
196
-    ShmuprpgGame.prototype.genAnimArray = function (name, n) {
197
-        var result = new Array();
198
-        for (var i = 0; i < n; ++i) {
189
+    }
190
+    genAnimArray(name, n) {
191
+        let result = new Array();
192
+        for (let i = 0; i < n; ++i) {
199 193
             result.push(name + i);
200 194
         }
201 195
         return result;
202
-    };
203
-    return ShmuprpgGame;
204
-}(Phaser.Game));
196
+    }
197
+}
205 198
 exports.ShmuprpgGame = ShmuprpgGame;
206
-//# sourceMappingURL=ShmuprpgGame.js.map
199
+
200
+
207 201
 });
208 202
 
209
-;require.register("entities/Bird.ts", function(exports, require, module) {
203
+require.register("entities/Bird.ts", function(exports, require, module) {
210 204
 "use strict";
211
-var __extends = (this && this.__extends) || function (d, b) {
212
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
213
-    function __() { this.constructor = d; }
214
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
215
-};
216
-var Bird = (function (_super) {
217
-    __extends(Bird, _super);
218
-    function Bird(game) {
219
-        _super.call(this, game, 0, 0, 'bird');
205
+class Bird extends Phaser.Sprite {
206
+    constructor(game) {
207
+        super(game, 0, 0, 'bird');
220 208
         this.animations.add('fly');
221 209
         this.game.physics.enable(this, Phaser.Physics.ARCADE);
222 210
         this.anchor.setTo(0.5, 0.5);
... ...
@@ -226,128 +214,109 @@ var Bird = (function (_super) {
226 214
         this.birdExplosion = this.game.add.sprite(this.x, this.y, 'bird-explosion');
227 215
         this.birdExplosion.anchor.setTo(0.5, 0.5);
228 216
         this.birdExplosion.exists = false;
229
-        var explodeAnimation = this.birdExplosion.animations.add('explode');
217
+        const explodeAnimation = this.birdExplosion.animations.add('explode');
230 218
         explodeAnimation.killOnComplete = true;
231 219
     }
232
-    Bird.prototype.fly = function (fromX, fromY, angle) {
233
-        var _this = this;
234
-        var beforeBird = this.game.add.sprite(fromX, fromY, 'before-bird');
220
+    fly(fromX, fromY, angle) {
221
+        const beforeBird = this.game.add.sprite(fromX, fromY, 'before-bird');
235 222
         beforeBird.anchor.setTo(0.5, 0.5);
236
-        var beforeBirdAnimation = beforeBird.animations.add('appears');
237
-        beforeBirdAnimation.onComplete.add(function () {
223
+        const beforeBirdAnimation = beforeBird.animations.add('appears');
224
+        beforeBirdAnimation.onComplete.add(() => {
238 225
             beforeBird.destroy();
239
-            _this.reset(fromX, fromY);
240
-            _this.play('fly', 8, true);
241
-            _this.game.physics.arcade.velocityFromRotation(angle, 300, _this.body.velocity);
242
-            _this.scale.set(_this.body.velocity.x < 0 ? -1 : 1, 1);
226
+            this.reset(fromX, fromY, 1);
227
+            this.play('fly', 8, true);
228
+            this.game.physics.arcade.velocityFromRotation(angle, 300, this.body.velocity);
229
+            this.scale.set(this.body.velocity.x < 0 ? -1 : 1, 1);
243 230
         });
244 231
         beforeBirdAnimation.play(4, false);
245
-    };
246
-    Bird.prototype.kill = function () {
247
-        _super.prototype.kill.call(this);
232
+    }
233
+    kill() {
234
+        super.kill();
248 235
         this.birdExplosion.reset(this.x, this.y);
249 236
         this.birdExplosion.play('explode', 8, false);
250 237
         return this;
251
-    };
252
-    return Bird;
253
-}(Phaser.Sprite));
238
+    }
239
+}
254 240
 exports.Bird = Bird;
255
-//# sourceMappingURL=Bird.js.map
241
+
242
+
256 243
 });
257 244
 
258
-;require.register("entities/BirdFlock.ts", function(exports, require, module) {
245
+require.register("entities/BirdFlock.ts", function(exports, require, module) {
259 246
 "use strict";
260
-var __extends = (this && this.__extends) || function (d, b) {
261
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
262
-    function __() { this.constructor = d; }
263
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
264
-};
265
-var Bird_ts_1 = require("./Bird.ts");
266
-var BirdFlock = (function (_super) {
267
-    __extends(BirdFlock, _super);
268
-    function BirdFlock(target, maxBirds) {
269
-        if (maxBirds === void 0) { maxBirds = 8; }
270
-        _super.call(this, target.game);
247
+const Bird_ts_1 = require("./Bird.ts");
248
+class BirdFlock extends Phaser.Group {
249
+    constructor(target, maxBirds = 10) {
250
+        super(target.game);
271 251
         this.flyRate = 1000;
272 252
         this.nextFlyTime = 0;
273 253
         this.target = target;
274
-        for (var i = 0; i < maxBirds; ++i) {
254
+        for (let i = 0; i < maxBirds; ++i) {
275 255
             this.add(this.createBird());
276 256
         }
277 257
     }
278
-    BirdFlock.preload = function (game) {
258
+    static preload(game) {
279 259
         game.load.spritesheet('bird', 'sprites/oga/tower-defense-prototyping-assets-4-monsters-some-tiles-a-background-image/bird.png', 48, 48, 5);
280 260
         game.load.spritesheet('before-bird', 'sprites/oga/rpg-special-move-effects/VioletSlash.png', 64, 64, 4);
281 261
         game.load.spritesheet('bird-explosion', 'sprites/oga/space_shooter_pack/explosion.png', 16, 16, 5);
282
-    };
283
-    BirdFlock.prototype.update = function () {
284
-        _super.prototype.update.call(this);
285
-        var x = this.game.world.randomX;
286
-        var y = this.game.world.randomY;
287
-        var angle = Phaser.Math.angleBetween(x, y, this.target.x, this.target.y);
262
+    }
263
+    update() {
264
+        super.update();
265
+        const x = this.game.world.randomX;
266
+        const y = this.game.world.randomY;
267
+        const angle = Phaser.Math.angleBetween(x, y, this.target.x, this.target.y);
288 268
         this.fly(x, y, angle);
289
-    };
290
-    BirdFlock.prototype.createBird = function () {
269
+    }
270
+    createBird() {
291 271
         return new Bird_ts_1.Bird(this.game);
292
-    };
293
-    BirdFlock.prototype.fly = function (fromX, fromY, angle) {
272
+    }
273
+    fly(fromX, fromY, angle) {
294 274
         if (this.game.time.time >= this.nextFlyTime) {
295
-            var bird = this.getFirstExists(false);
275
+            const bird = this.getFirstExists(false);
296 276
             if (bird) {
297 277
                 bird.fly(fromX, fromY, angle);
298 278
                 this.nextFlyTime = this.game.time.time + this.flyRate;
299 279
             }
300 280
         }
301
-    };
302
-    return BirdFlock;
303
-}(Phaser.Group));
281
+    }
282
+}
304 283
 exports.BirdFlock = BirdFlock;
305
-//# sourceMappingURL=BirdFlock.js.map
284
+
285
+
306 286
 });
307 287
 
308
-;require.register("entities/Bullet.ts", function(exports, require, module) {
288
+require.register("entities/Bullet.ts", function(exports, require, module) {
309 289
 "use strict";
310
-var __extends = (this && this.__extends) || function (d, b) {
311
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
312
-    function __() { this.constructor = d; }
313
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
314
-};
315
-var Bullet = (function (_super) {
316
-    __extends(Bullet, _super);
317
-    function Bullet(game) {
318
-        _super.call(this, game, 0, 0, 'bullet');
290
+class Bullet extends Phaser.Sprite {
291
+    constructor(game) {
292
+        super(game, 0, 0, 'bullets');
293
+        game.addSpriteAnimation(this, 'bullet.red', 4);
319 294
         this.game.physics.enable(this, Phaser.Physics.ARCADE);
320 295
         this.anchor.setTo(0.5, 0.5);
321 296
         this.checkWorldBounds = true;
322 297
         this.outOfBoundsKill = true;
323 298
         this.exists = false;
324 299
     }
325
-    Bullet.prototype.fire = function (fromX, fromY, angle, speed, gravityX, gravityY) {
326
-        this.reset(fromX, fromY);
300
+    fire(fromX, fromY, angle, speed, gravityX, gravityY) {
301
+        this.reset(fromX, fromY, 1);
327 302
         this.scale.set(1);
328 303
         this.game.physics.arcade.velocityFromRotation(angle, speed, this.body.velocity);
329 304
         this.angle = angle;
330 305
         this.body.gravity.set(gravityX, gravityY);
331
-    };
332
-    return Bullet;
333
-}(Phaser.Sprite));
306
+        this.play('bullet.red', 4, true);
307
+    }
308
+}
334 309
 exports.Bullet = Bullet;
335
-//# sourceMappingURL=Bullet.js.map
310
+
311
+
336 312
 });
337 313
 
338
-;require.register("entities/Grobelin.ts", function(exports, require, module) {
314
+require.register("entities/Grobelin.ts", function(exports, require, module) {
339 315
 "use strict";
340
-var __extends = (this && this.__extends) || function (d, b) {
341
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
342
-    function __() { this.constructor = d; }
343
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
344
-};
345
-var Grobelin = (function (_super) {
346
-    __extends(Grobelin, _super);
347
-    function Grobelin(game, pathfinder) {
348
-        _super.call(this, game, 0, 0, 'grobelin');
349
-        this.path = new Array();
350
-        this.thinking = false;
316
+const b3 = require("../ia/decisions/b3.ts");
317
+class Grobelin extends Phaser.Sprite {
318
+    constructor(game, pathfinder) {
319
+        super(game, 0, 0, 'grobelin');
351 320
         this.exists = false;
352 321
         this.pathfinder = pathfinder;
353 322
         this.game.physics.enable(this, Phaser.Physics.ARCADE);
... ...
@@ -358,88 +327,74 @@ var Grobelin = (function (_super) {
358 327
         this.grobelinDeath.anchor.setTo(0.5, 0.5);
359 328
         this.grobelinDeath.exists = false;
360 329
     }
361
-    Grobelin.prototype.getVulnerableRectangles = function () {
330
+    getVulnerableRectangles() {
362 331
         return [new Phaser.Rectangle(this.x, this.y, this.width, this.height)];
363
-    };
364
-    Grobelin.prototype.appears = function (fromX, fromY, target) {
365
-        var _this = this;
366
-        var beforeGrobelin = this.game.add.sprite(fromX, fromY, 'before-bird');
332
+    }
333
+    appears(fromX, fromY, target) {
334
+        const beforeGrobelin = this.game.add.sprite(fromX, fromY, 'before-bird');
367 335
         beforeGrobelin.anchor.setTo(0.5, 0.5);
368
-        var beforeGrobelinAnimation = beforeGrobelin.animations.add('appears');
369
-        beforeGrobelinAnimation.onComplete.add(function () {
336
+        const beforeGrobelinAnimation = beforeGrobelin.animations.add('appears');
337
+        beforeGrobelinAnimation.onComplete.add(() => {
370 338
             beforeGrobelin.destroy();
371
-            _this.reset(fromX, fromY, 50);
372
-            _this.body.setSize(16, 16, 24, 48);
373
-            _this.body.collideWorldBounds = true;
374
-            _this.path = [];
375
-            _this.currentPathPointTarget = null;
376
-            _this.thinking = false;
377
-            _this.enemy = target;
339
+            this.reset(fromX, fromY, 50);
340
+            this.body.setSize(16, 16, 24, 48);
341
+            this.body.collideWorldBounds = true;
342
+            this.blackboard = new GrobelinBlackboard();
343
+            this.enemy = target;
378 344
         });
379 345
         beforeGrobelinAnimation.play(4, false);
380
-    };
381
-    Grobelin.prototype.kill = function () {
382
-        _super.prototype.kill.call(this);
346
+    }
347
+    kill() {
348
+        super.kill();
383 349
         this.damageTween.stop(true);
384 350
         this.tint = 0xFFFFFF;
385 351
         this.grobelinDeath.reset(this.x, this.y);
386 352
         this.grobelinDeath.animations.play("lpc.hurt", 6, false).killOnComplete = true;
387 353
         return this;
388
-    };
389
-    Grobelin.prototype.update = function () {
390
-        _super.prototype.update.call(this);
354
+    }
355
+    update() {
356
+        super.update();
391 357
         if (this.exists) {
392 358
             this.executeBehaviorTree();
393 359
         }
394
-    };
395
-    Grobelin.prototype.damage = function (amount) {
396
-        var _this = this;
360
+    }
361
+    damage(amount) {
397 362
         if (!this.damageTween) {
398 363
             this.damageTween = this.game.add.tween(this).from({ tint: 0xFF0000 }).to({ tint: 0xFFFFFF }, 500, Phaser.Easing.Linear.None, true, 0, 4, false);
399
-            this.damageTween.onComplete.add(function () { return _this.damageTween = null; });
364
+            this.damageTween.onComplete.add(() => this.damageTween = null);
400 365
         }
401
-        _super.prototype.damage.call(this, amount);
366
+        super.damage(amount);
402 367
         return this;
403
-    };
404
-    Grobelin.prototype.executeBehaviorTree = function () {
405
-        this.priority_Root();
406
-    };
407
-    Grobelin.prototype.priority_Root = function () {
408
-        this.sequence_Attack() || this.action_FollowPath() || this.action_SearchAPathToEnemy();
409
-    };
410
-    Grobelin.prototype.sequence_Attack = function () {
411
-        return this.condition_IsNearEnemy() && this.action_AttackEnemy();
412
-    };
413
-    Grobelin.prototype.condition_IsNearEnemy = function () {
414
-        return this.enemy && Phaser.Math.distance(this.body.center.x, this.body.center.y, this.enemy.body.center.x, this.enemy.body.center.y) < this.body.width * 2;
415
-    };
416
-    Grobelin.prototype.action_AttackEnemy = function () {
368
+    }
369
+    executeBehaviorTree() {
370
+        GrobelinB3.get().tick(this, this.blackboard);
371
+    }
372
+    attackEnemy() {
417 373
         this.body.velocity.x = 0;
418 374
         this.body.velocity.y = 0;
419 375
         if (!this.attackAnimation) {
420
-            _a = this.action_AttackEnemy_PlayAnimation(), this.attackAnimation = _a[0], this.attackDangerousOffset = _a[1];
376
+            [this.attackAnimation, this.attackDangerousOffset] = this.playAttackEnemyAnimation();
421 377
         }
422 378
         else if (this.attackAnimation.isFinished) {
423 379
             this.attackAnimation = null;
424
-            var enemyRectangle = new Phaser.Rectangle(this.enemy.left, this.enemy.top, this.enemy.width, this.enemy.height);
380
+            const enemyRectangle = new Phaser.Rectangle(this.enemy.left, this.enemy.top, this.enemy.width, this.enemy.height);
425 381
             if (Phaser.Rectangle.containsPoint(enemyRectangle, this.getAttackPoint())) {
426 382
                 this.enemy.damage(1);
427 383
             }
428 384
         }
429 385
         return true;
430
-        var _a;
431
-    };
432
-    Grobelin.prototype.getAttackPoint = function () {
386
+    }
387
+    getAttackPoint() {
433 388
         if (this.attackDangerousOffset) {
434 389
             return new Phaser.Point(this.body.center.x + this.attackDangerousOffset.x, this.body.center.y + this.attackDangerousOffset.y);
435 390
         }
436 391
         else {
437 392
             return null;
438 393
         }
439
-    };
440
-    Grobelin.prototype.action_AttackEnemy_PlayAnimation = function () {
441
-        var dx = this.enemy.body.center.x - this.body.center.x;
442
-        var dy = this.enemy.body.center.y - this.body.center.y;
394
+    }
395
+    playAttackEnemyAnimation() {
396
+        const dx = this.enemy.body.center.x - this.body.center.x;
397
+        const dy = this.enemy.body.center.y - this.body.center.y;
443 398
         if (Math.abs(dx) > Math.abs(dy)) {
444 399
             if (dx < 0) {
445 400
                 return [this.play("lpc.thrust.left", 8, false), new Phaser.Point(-24, -16)];
... ...
@@ -474,115 +429,147 @@ var Grobelin = (function (_super) {
474 429
                 return [this.play("lpc.thrust.back", 8, false), new Phaser.Point(8, -48)];
475 430
             }
476 431
         }
477
-    };
478
-    Grobelin.prototype.action_FollowPath = function () {
479
-        if (this.currentPathPointTarget) {
480
-            this.action_FollowPath_MoveToXY(this.currentPathPointTarget.x, this.currentPathPointTarget.y, 300);
481
-            if (Phaser.Math.distance(this.body.center.x, this.body.center.y, this.currentPathPointTarget.x, this.currentPathPointTarget.y) < this.body.halfWidth) {
482
-                this.currentPathPointTarget = null;
432
+    }
433
+}
434
+exports.Grobelin = Grobelin;
435
+class GrobelinBlackboard extends b3.Blackboard {
436
+}
437
+class GrobelinB3 extends b3.Tree {
438
+    constructor() {
439
+        super();
440
+        this.root = this.selector(this.sequence(new ConditionIsNearEnemy(), new ActionAttackEnemy()), new ActionFollowPath(), new ActionSearchAPathToEnemy());
441
+    }
442
+    static get() {
443
+        return this.singleton || (this.singleton = new GrobelinB3());
444
+    }
445
+}
446
+class ActionFollowPath extends b3.Action {
447
+    tick(t) {
448
+        let me = t.me;
449
+        let currentPathPointTarget = t.blackboard.currentPathPointTarget;
450
+        if (currentPathPointTarget) {
451
+            this.moveToXY(me, currentPathPointTarget.x, currentPathPointTarget.y, 300);
452
+            if (Phaser.Math.distance(me.body.center.x, me.body.center.y, currentPathPointTarget.x, currentPathPointTarget.y) < me.body.halfWidth) {
453
+                t.blackboard.currentPathPointTarget = null;
483 454
             }
484 455
         }
485 456
         else {
486
-            this.currentPathPointTarget = this.path.shift();
487
-            if (this.path.length == 0) {
488
-                this.body.velocity.x = 0;
489
-                this.body.velocity.y = 0;
490
-                return false;
457
+            let path = t.blackboard.path || [];
458
+            t.blackboard.currentPathPointTarget = path.shift();
459
+            if (path.length == 0) {
460
+                me.body.velocity.x = 0;
461
+                me.body.velocity.y = 0;
462
+                return b3.NodeState.FAILURE;
491 463
             }
492 464
         }
493
-        this.action_FollowPath_Animate();
494
-        return true;
495
-    };
496
-    Grobelin.prototype.action_FollowPath_Animate = function () {
497
-        if (Math.abs(this.body.velocity.x) > Math.abs(this.body.velocity.y)) {
498
-            if (this.body.velocity.x < 0) {
499
-                this.play("lpc.walk.left", 8, false);
465
+        this.animate(me);
466
+        return b3.NodeState.RUNNING;
467
+    }
468
+    animate(me) {
469
+        if (Math.abs(me.body.velocity.x) > Math.abs(me.body.velocity.y)) {
470
+            if (me.body.velocity.x < 0) {
471
+                me.play("lpc.walk.left", 8, false);
500 472
             }
501
-            else if (this.body.velocity.x > 0) {
502
-                this.play("lpc.walk.right", 8, false);
473
+            else if (me.body.velocity.x > 0) {
474
+                me.play("lpc.walk.right", 8, false);
503 475
             }
504
-            else if (this.body.velocity.y < 0) {
505
-                this.play("lpc.walk.back", 8, false);
476
+            else if (me.body.velocity.y < 0) {
477
+                me.play("lpc.walk.back", 8, false);
506 478
             }
507
-            else if (this.body.velocity.y > 0) {
508
-                this.play("lpc.walk.front", 8, false);
479
+            else if (me.body.velocity.y > 0) {
480
+                me.play("lpc.walk.front", 8, false);
509 481
             }
510 482
             else {
511
-                this.play("lpc.hurt", 0, false);
483
+                me.play("lpc.hurt", 0, false);
512 484
             }
513 485
         }
514 486
         else {
515
-            if (this.body.velocity.y < 0) {
516
-                this.play("lpc.walk.back", 8, false);
487
+            if (me.body.velocity.y < 0) {
488
+                me.play("lpc.walk.back", 8, false);
517 489
             }
518
-            else if (this.body.velocity.y > 0) {
519
-                this.play("lpc.walk.front", 8, false);
490
+            else if (me.body.velocity.y > 0) {
491
+                me.play("lpc.walk.front", 8, false);
520 492
             }
521
-            else if (this.body.velocity.x < 0) {
522
-                this.play("lpc.walk.left", 8, false);
493
+            else if (me.body.velocity.x < 0) {
494
+                me.play("lpc.walk.left", 8, false);
523 495
             }
524
-            else if (this.body.velocity.x > 0) {
525
-                this.play("lpc.walk.right", 8, false);
496
+            else if (me.body.velocity.x > 0) {
497
+                me.play("lpc.walk.right", 8, false);
526 498
             }
527 499
             else {
528
-                this.play("lpc.hurt", 0, false);
500
+                me.play("lpc.hurt", 0, false);
529 501
             }
530 502
         }
531
-    };
532
-    Grobelin.prototype.action_FollowPath_MoveToXY = function (x, y, speed) {
533
-        if (speed === void 0) { speed = 60; }
534
-        var angle = Math.atan2(y - this.body.center.y, x - this.body.center.x);
535
-        this.body.velocity.x = Math.cos(angle) * speed;
536
-        this.body.velocity.y = Math.sin(angle) * speed;
537
-    };
538
-    Grobelin.prototype.action_SearchAPathToEnemy = function () {
539
-        var _this = this;
540
-        if (!this.thinking) {
541
-            this.thinking = true;
542
-            this.pathfinder.findPath(this.body.center.x, this.body.center.y, this.enemy.body.center.x, this.enemy.body.center.y, function (path) {
543
-                _this.path = path || new Array();
544
-                _this.thinking = false;
503
+    }
504
+    moveToXY(me, x, y, speed = 60) {
505
+        var angle = Math.atan2(y - me.body.center.y, x - me.body.center.x);
506
+        me.body.velocity.x = Math.cos(angle) * speed;
507
+        me.body.velocity.y = Math.sin(angle) * speed;
508
+    }
509
+}
510
+class ActionSearchAPathToEnemy extends b3.Action {
511
+    constructor(...args) {
512
+        super(...args);
513
+        this.thinking = new b3.BlackboardKey();
514
+    }
515
+    tick(t) {
516
+        let thinking = t.blackboard.get(this.thinking) || false;
517
+        let me = t.me;
518
+        if (!thinking) {
519
+            t.blackboard.set(this.thinking, true);
520
+            me.pathfinder.findPath(me.body.center.x, me.body.center.y, me.enemy.body.center.x, me.enemy.body.center.y, (path) => {
521
+                t.blackboard.path = path || [];
522
+                t.blackboard.set(this.thinking, false);
545 523
             });
546 524
         }
547
-        return this.path.length == 0;
548
-    };
549
-    return Grobelin;
550
-}(Phaser.Sprite));
551
-exports.Grobelin = Grobelin;
552
-//# sourceMappingURL=Grobelin.js.map
525
+        let path = t.blackboard.path || [];
526
+        return path.length > 0 ? b3.NodeState.SUCCESS : b3.NodeState.RUNNING;
527
+    }
528
+}
529
+class ConditionIsNearEnemy extends b3.Condition {
530
+    check(t) {
531
+        let me = t.me;
532
+        return me.enemy && Phaser.Math.distance(me.body.center.x, me.body.center.y, me.enemy.body.center.x, me.enemy.body.center.y) < me.body.width * 2;
533
+    }
534
+}
535
+class ActionAttackEnemy extends b3.Action {
536
+    tick(t) {
537
+        if (t.me.attackEnemy()) {
538
+            return b3.NodeState.SUCCESS;
539
+        }
540
+        else {
541
+            return b3.NodeState.RUNNING;
542
+        }
543
+    }
544
+}
545
+
546
+
553 547
 });
554 548
 
555 549
 ;require.register("entities/GrobelinHorde.ts", function(exports, require, module) {
556 550
 "use strict";
557
-var __extends = (this && this.__extends) || function (d, b) {
558
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
559
-    function __() { this.constructor = d; }
560
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
561
-};
562
-var Grobelin_ts_1 = require("./Grobelin.ts");
563
-var GrobelinHorde = (function (_super) {
564
-    __extends(GrobelinHorde, _super);
565
-    function GrobelinHorde(target, pathFinder, maxGrobelins) {
566
-        if (maxGrobelins === void 0) { maxGrobelins = 4; }
567
-        _super.call(this, target.game);
551
+const Grobelin_ts_1 = require("./Grobelin.ts");
552
+class GrobelinHorde extends Phaser.Group {
553
+    constructor(target, pathFinder, maxGrobelins = 4) {
554
+        super(target.game);
568 555
         this.appearsRate = 10000;
569 556
         this.nextAppearsTime = 0;
570 557
         this.pathfinder = pathFinder;
571 558
         this.target = target;
572
-        for (var i = 0; i < maxGrobelins; ++i) {
559
+        for (let i = 0; i < maxGrobelins; ++i) {
573 560
             this.add(this.createGrobelin());
574 561
         }
575 562
     }
576
-    GrobelinHorde.preload = function (game) {
563
+    static preload(game) {
577 564
         game.load.atlasXML('grobelin', 'sprites/lpc/characters/grobelin.png', 'sprites/lpc/characters/lpc.xml');
578
-    };
579
-    GrobelinHorde.prototype.update = function () {
580
-        _super.prototype.update.call(this);
565
+    }
566
+    update() {
567
+        super.update();
581 568
         this.appears();
582
-    };
583
-    GrobelinHorde.prototype.createGrobelin = function () {
584
-        var grobelin = new Grobelin_ts_1.Grobelin(this.game, this.pathfinder);
585
-        var game = this.game;
569
+    }
570
+    createGrobelin() {
571
+        const grobelin = new Grobelin_ts_1.Grobelin(this.game, this.pathfinder);
572
+        const game = this.game;
586 573
         game.addSpriteAnimation(grobelin.grobelinDeath, 'lpc.hurt', 6);
587 574
         game.addSpriteAnimation(grobelin, 'lpc.hurt', 6);
588 575
         game.addSpriteAnimation(grobelin, 'lpc.walk.back', 9);
... ...
@@ -594,35 +581,29 @@ var GrobelinHorde = (function (_super) {
594 581
         game.addSpriteAnimation(grobelin, 'lpc.thrust.left', 9);
595 582
         game.addSpriteAnimation(grobelin, 'lpc.thrust.right', 9);
596 583
         return grobelin;
597
-    };
598
-    GrobelinHorde.prototype.appears = function () {
584
+    }
585
+    appears() {
599 586
         if (this.game.time.time >= this.nextAppearsTime) {
600
-            var grobelin = this.getFirstExists(false);
587
+            const grobelin = this.getFirstExists(false);
601 588
             if (grobelin) {
602
-                var pos = this.pathfinder.randomWalkablePos();
589
+                const pos = this.pathfinder.randomWalkablePos();
603 590
                 grobelin.appears(pos.x, pos.y, this.target);
604 591
                 this.nextAppearsTime = this.game.time.time + this.appearsRate;
605 592
             }
606 593
         }
607
-    };
608
-    return GrobelinHorde;
609
-}(Phaser.Group));
594
+    }
595
+}
610 596
 exports.GrobelinHorde = GrobelinHorde;
611
-//# sourceMappingURL=GrobelinHorde.js.map
597
+
598
+
612 599
 });
613 600
 
614
-;require.register("entities/Hero.ts", function(exports, require, module) {
601
+require.register("entities/Hero.ts", function(exports, require, module) {
615 602
 "use strict";
616
-var __extends = (this && this.__extends) || function (d, b) {
617
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
618
-    function __() { this.constructor = d; }
619
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
620
-};
621
-var MachineGun_ts_1 = require("./MachineGun.ts");
622
-var Hero = (function (_super) {
623
-    __extends(Hero, _super);
624
-    function Hero(game) {
625
-        _super.call(this, game, game.world.centerX, game.world.centerY, 'tobira');
603
+const MachineGun_ts_1 = require("./MachineGun.ts");
604
+class Hero extends Phaser.Sprite {
605
+    constructor(game) {
606
+        super(game, game.world.centerX, game.world.centerY, 'tobira');
626 607
         this.invincible = false;
627 608
         this.health = 3;
628 609
         this.controls = game.controls;
... ...
@@ -639,12 +620,12 @@ var Hero = (function (_super) {
639 620
         this.weapon = new MachineGun_ts_1.MachineGun(this.game);
640 621
         this.game.add.existing(this.weapon);
641 622
     }
642
-    Hero.preload = function (game) {
623
+    static preload(game) {
643 624
         game.load.atlasXML('tobira', 'sprites/lpc/characters/tobira.png', 'sprites/lpc/characters/lpc.xml');
644
-        game.load.spritesheet('bullet', 'sprites/lpc/shootemup/effects01.png', 16, 16, 4);
645
-    };
646
-    Hero.prototype.update = function () {
647
-        _super.prototype.update.call(this);
625
+        game.load.atlasXML('bullets', 'sprites/lpc/shootemup/effects01.png', 'sprites/lpc/shootemup/bullets.xml');
626
+    }
627
+    update() {
628
+        super.update();
648 629
         this.body.velocity.x = 0;
649 630
         this.body.velocity.y = 0;
650 631
         if (this.controls.isGoingLeft()) {
... ...
@@ -674,179 +655,757 @@ var Hero = (function (_super) {
674 655
         else {
675 656
             this.play("lpc.hurt", 0, false);
676 657
         }
677
-        var shootingAngle = this.controls.shootingAngle(this.x, this.y);
658
+        const shootingAngle = this.controls.shootingAngle(this.x, this.y);
678 659
         if (shootingAngle != null) {
679 660
             this.weapon.fire(this.x, this.y, shootingAngle);
680 661
         }
681
-    };
682
-    Hero.prototype.damage = function (amount) {
683
-        var _this = this;
662
+    }
663
+    damage(amount) {
684 664
         if (!this.invincible) {
685 665
             this.invincible = true;
686
-            this.game.add.tween(this).from({ tint: 0xFF0000 }).to({ tint: 0xFFFFFF }, 1000, Phaser.Easing.Linear.None, true, 0, 4, false).onComplete.add(function () { return _this.invincible = false; });
687
-            _super.prototype.damage.call(this, amount);
666
+            this.game.add.tween(this).from({ tint: 0xFF0000 }).to({ tint: 0xFFFFFF }, 1000, Phaser.Easing.Linear.None, true, 0, 4, false).onComplete.add(() => this.invincible = false);
667
+            super.damage(amount);
688 668
             if (!this.alive) {
689 669
                 this.game.state.start('GameOver');
690 670
             }
691 671
         }
692 672
         return this;
693
-    };
694
-    return Hero;
695
-}(Phaser.Sprite));
673
+    }
674
+}
696 675
 exports.Hero = Hero;
697
-//# sourceMappingURL=Hero.js.map
676
+
677
+
698 678
 });
699 679
 
700
-;require.register("entities/MachineGun.ts", function(exports, require, module) {
680
+require.register("entities/MachineGun.ts", function(exports, require, module) {
701 681
 "use strict";
702
-var __extends = (this && this.__extends) || function (d, b) {
703
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
704
-    function __() { this.constructor = d; }
705
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
706
-};
707
-var Bullet_ts_1 = require("./Bullet.ts");
708
-var MachineGun = (function (_super) {
709
-    __extends(MachineGun, _super);
710
-    function MachineGun(game, maxBullets) {
711
-        if (maxBullets === void 0) { maxBullets = 64; }
712
-        _super.call(this, game);
682
+const Bullet_ts_1 = require("./Bullet.ts");
683
+class MachineGun extends Phaser.Group {
684
+    constructor(game, maxBullets = 64) {
685
+        super(game);
713 686
         this.bulletSpeed = 600;
714 687
         this.fireRate = 200;
715 688
         this.nextFireTime = 0;
716
-        for (var i = 0; i < maxBullets; ++i) {
689
+        for (let i = 0; i < maxBullets; ++i) {
717 690
             this.add(this.createBullet());
718 691
         }
719 692
     }
720
-    MachineGun.prototype.createBullet = function () {
721
-        var bullet = new Bullet_ts_1.Bullet(this.game);
722
-        return bullet;
723
-    };
724
-    MachineGun.prototype.fire = function (fromX, fromY, angle) {
693
+    createBullet() {
694
+        return new Bullet_ts_1.Bullet(this.game);
695
+    }
696
+    fire(fromX, fromY, angle) {
725 697
         if (this.game.time.time >= this.nextFireTime) {
726
-            var bullet = this.getFirstExists(false);
698
+            const bullet = this.getFirstExists(false);
727 699
             if (bullet) {
728 700
                 bullet.fire(fromX, fromY, angle, this.bulletSpeed, 0, 0);
729 701
                 this.nextFireTime = this.game.time.time + this.fireRate;
730 702
             }
731 703
         }
732
-    };
733
-    return MachineGun;
734
-}(Phaser.Group));
704
+    }
705
+}
735 706
 exports.MachineGun = MachineGun;
736
-//# sourceMappingURL=MachineGun.js.map
707
+
708
+
709
+});
710
+
711
+require.register("entities/Spider.ts", function(exports, require, module) {
712
+"use strict";
713
+const b3 = require("../ia/decisions/b3.ts");
714
+const MachineGun_ts_1 = require("./MachineGun.ts");
715
+class Spider extends Phaser.Sprite {
716
+    constructor(game, pathfinder) {
717
+        super(game, 0, 0, 'spider');
718
+        this.exists = false;
719
+        this.pathfinder = pathfinder;
720
+        this.game.physics.enable(this, Phaser.Physics.ARCADE);
721
+        this.anchor.setTo(0.5, 0.5);
722
+        this.checkWorldBounds = true;
723
+        this.outOfBoundsKill = true;
724
+        this.spiderDeath = this.game.add.sprite(this.x, this.y, 'spider');
725
+        this.spiderDeath.anchor.setTo(0.5, 0.5);
726
+        this.spiderDeath.exists = false;
727
+        this.machineGun = new MachineGun_ts_1.MachineGun(this.game, 1);
728
+    }
729
+    getVulnerableRectangles() {
730
+        return [new Phaser.Rectangle(this.x, this.y, this.width, this.height)];
731
+    }
732
+    appears(fromX, fromY, target) {
733
+        const beforeSpider = this.game.add.sprite(fromX, fromY, 'before-bird');
734
+        beforeSpider.anchor.setTo(0.5, 0.5);
735
+        const beforeSpiderAnimation = beforeSpider.animations.add('appears');
736
+        beforeSpiderAnimation.onComplete.add(() => {
737
+            beforeSpider.destroy();
738
+            this.reset(fromX, fromY, 10);
739
+            this.body.setSize(16, 16, 24, 48);
740
+            this.body.collideWorldBounds = true;
741
+            this.blackboard = new SpiderBlackboard();
742
+            this.enemy = target;
743
+        });
744
+        beforeSpiderAnimation.play(4, false);
745
+    }
746
+    kill() {
747
+        super.kill();
748
+        this.damageTween.stop(true);
749
+        this.tint = 0xFFFFFF;
750
+        this.spiderDeath.reset(this.x, this.y);
751
+        this.spiderDeath.animations.play("spider.hurt", 6, false).killOnComplete = true;
752
+        return this;
753
+    }
754
+    update() {
755
+        super.update();
756
+        if (this.exists) {
757
+            this.executeBehaviorTree();
758
+        }
759
+    }
760
+    damage(amount) {
761
+        if (!this.damageTween) {
762
+            this.damageTween = this.game.add.tween(this).from({ tint: 0xFF0000 }).to({ tint: 0xFFFFFF }, 500, Phaser.Easing.Linear.None, true, 0, 4, false);
763
+            this.damageTween.onComplete.add(() => this.damageTween = null);
764
+        }
765
+        super.damage(amount);
766
+        return this;
767
+    }
768
+    executeBehaviorTree() {
769
+        SpiderB3.get().tick(this, this.blackboard);
770
+    }
771
+    attackEnemy() {
772
+        this.body.velocity.x = 0;
773
+        this.body.velocity.y = 0;
774
+        if (!this.attackAnimation) {
775
+            [this.attackAnimation, this.attackDangerousOffset] = this.playAttackEnemyAnimation();
776
+        }
777
+        else if (this.attackAnimation.isFinished) {
778
+            this.attackAnimation = null;
779
+            const enemyRectangle = new Phaser.Rectangle(this.enemy.left, this.enemy.top, this.enemy.width, this.enemy.height);
780
+            if (Phaser.Rectangle.containsPoint(enemyRectangle, this.getAttackPoint())) {
781
+                this.enemy.damage(1);
782
+            }
783
+        }
784
+        return true;
785
+    }
786
+    fire() {
787
+        this.body.velocity.x = 0;
788
+        this.body.velocity.y = 0;
789
+        let [_, fireOffset] = this.playFireAnimation();
790
+        let angle = Phaser.Math.angleBetween(this.body.center.x, this.body.center.y, this.enemy.body.center.x, this.enemy.body.center.y);
791
+        this.machineGun.fire(this.body.center.x + fireOffset.x, this.body.center.y + fireOffset.y, angle);
792
+        return true;
793
+    }
794
+    playFireAnimation() {
795
+        const dx = this.enemy.body.center.x - this.body.center.x;
796
+        const dy = this.enemy.body.center.y - this.body.center.y;
797
+        if (Math.abs(dx) > Math.abs(dy)) {
798
+            if (dx < 0) {
799
+                return [this.play("spider.stand.left", 6, false), new Phaser.Point(-24, -16)];
800
+            }
801
+            else if (dx > 0) {
802
+                return [this.play("spider.stand.right", 6, false), new Phaser.Point(24, -16)];
803
+            }
804
+            else if (dy < 0) {
805
+                return [this.play("spider.stand.back", 6, false), new Phaser.Point(8, -48)];
806
+            }
807
+            else if (dy > 0) {
808
+                return [this.play("spider.stand.front", 6, false), new Phaser.Point(-8, 8)];
809
+            }
810
+            else {
811
+                return [this.play("spider.stand.right", 6, false), new Phaser.Point(24, -16)];
812
+            }
813
+        }
814
+        else {
815
+            if (dy < 0) {
816
+                return [this.play("spider.stand.back", 8, false), new Phaser.Point(8, -48)];
817
+            }
818
+            else if (dy > 0) {
819
+                return [this.play("spider.stand.front", 8, false), new Phaser.Point(-8, 8)];
820
+            }
821
+            else if (dx < 0) {
822
+                return [this.play("spider.stand.left", 8, false), new Phaser.Point(-24, -16)];
823
+            }
824
+            else if (dx > 0) {
825
+                return [this.play("spider.stand.right", 8, false), new Phaser.Point(24, -16)];
826
+            }
827
+            else {
828
+                return [this.play("spider.stand.back", 8, false), new Phaser.Point(8, -48)];
829
+            }
830
+        }
831
+    }
832
+    getAttackPoint() {
833
+        if (this.attackDangerousOffset) {
834
+            return new Phaser.Point(this.body.center.x + this.attackDangerousOffset.x, this.body.center.y + this.attackDangerousOffset.y);
835
+        }
836
+        else {
837
+            return null;
838
+        }
839
+    }
840
+    playAttackEnemyAnimation() {
841
+        const dx = this.enemy.body.center.x - this.body.center.x;
842
+        const dy = this.enemy.body.center.y - this.body.center.y;
843
+        if (Math.abs(dx) > Math.abs(dy)) {
844
+            if (dx < 0) {
845
+                return [this.play("spider.attack.left", 8, false), new Phaser.Point(-24, -16)];
846
+            }
847
+            else if (dx > 0) {
848
+                return [this.play("spider.attack.right", 8, false), new Phaser.Point(24, -16)];
849
+            }
850
+            else if (dy < 0) {
851
+                return [this.play("spider.attack.back", 8, false), new Phaser.Point(8, -48)];
852
+            }
853
+            else if (dy > 0) {
854
+                return [this.play("spider.attack.front", 8, false), new Phaser.Point(-8, 8)];
855
+            }
856
+            else {
857
+                return [this.play("spider.attack.right", 8, false), new Phaser.Point(24, -16)];
858
+            }
859
+        }
860
+        else {
861
+            if (dy < 0) {
862
+                return [this.play("spider.attack.back", 8, false), new Phaser.Point(8, -48)];
863
+            }
864
+            else if (dy > 0) {
865
+                return [this.play("spider.attack.front", 8, false), new Phaser.Point(-8, 8)];
866
+            }
867
+            else if (dx < 0) {
868
+                return [this.play("spider.attack.left", 8, false), new Phaser.Point(-24, -16)];
869
+            }
870
+            else if (dx > 0) {
871
+                return [this.play("spider.attack.right", 8, false), new Phaser.Point(24, -16)];
872
+            }
873
+            else {
874
+                return [this.play("spider.attack.back", 8, false), new Phaser.Point(8, -48)];
875
+            }
876
+        }
877
+    }
878
+}
879
+exports.Spider = Spider;
880
+class SpiderBlackboard extends b3.Blackboard {
881
+}
882
+class SpiderB3 extends b3.Tree {
883
+    constructor() {
884
+        super();
885
+        this.root = this.selector(this.sequence(new ConditionIsNearEnemy(), new ActionAttackEnemy()), this.sequence(new ConditionIsEnemyInLineOfFire(), new ActionFire()), new ActionFollowPath(), new ActionSearchAPathToEnemy());
886
+    }
887
+    static get() {
888
+        return this.singleton || (this.singleton = new SpiderB3());
889
+    }
890
+}
891
+class ActionFollowPath extends b3.Action {
892
+    tick(t) {
893
+        let me = t.me;
894
+        let currentPathPointTarget = t.blackboard.currentPathPointTarget;
895
+        if (currentPathPointTarget) {
896
+            this.moveToXY(me, currentPathPointTarget.x, currentPathPointTarget.y, 300);
897
+            if (Phaser.Math.distance(me.body.center.x, me.body.center.y, currentPathPointTarget.x, currentPathPointTarget.y) < me.body.halfWidth) {
898
+                t.blackboard.currentPathPointTarget = null;
899
+            }
900
+        }
901
+        else {
902
+            let path = t.blackboard.path || [];
903
+            t.blackboard.currentPathPointTarget = path.shift();
904
+            if (path.length == 0) {
905
+                me.body.velocity.x = 0;
906
+                me.body.velocity.y = 0;
907
+                return b3.NodeState.FAILURE;
908
+            }
909
+        }
910
+        this.animate(me);
911
+        return b3.NodeState.RUNNING;
912
+    }
913
+    animate(me) {
914
+        if (Math.abs(me.body.velocity.x) > Math.abs(me.body.velocity.y)) {
915
+            if (me.body.velocity.x < 0) {
916
+                me.play("spider.walk.left", 8, false);
917
+            }
918
+            else if (me.body.velocity.x > 0) {
919
+                me.play("spider.walk.right", 8, false);
920
+            }
921
+            else if (me.body.velocity.y < 0) {
922
+                me.play("spider.walk.back", 8, false);
923
+            }
924
+            else if (me.body.velocity.y > 0) {
925
+                me.play("spider.walk.front", 8, false);
926
+            }
927
+            else {
928
+                me.play("spider.hurt", 0, false);
929
+            }
930
+        }
931
+        else {
932
+            if (me.body.velocity.y < 0) {
933
+                me.play("spider.walk.back", 8, false);
934
+            }
935
+            else if (me.body.velocity.y > 0) {
936
+                me.play("spider.walk.front", 8, false);
937
+            }
938
+            else if (me.body.velocity.x < 0) {
939
+                me.play("spider.walk.left", 8, false);
940
+            }
941
+            else if (me.body.velocity.x > 0) {
942
+                me.play("spider.walk.right", 8, false);
943
+            }
944
+            else {
945
+                me.play("lpc.hurt", 0, false);
946
+            }
947
+        }
948
+    }
949
+    moveToXY(me, x, y, speed = 60) {
950
+        var angle = Math.atan2(y - me.body.center.y, x - me.body.center.x);
951
+        me.body.velocity.x = Math.cos(angle) * speed;
952
+        me.body.velocity.y = Math.sin(angle) * speed;
953
+    }
954
+}
955
+class ActionSearchAPathToEnemy extends b3.Action {
956
+    constructor(...args) {
957
+        super(...args);
958
+        this.thinking = new b3.BlackboardKey();
959
+    }
960
+    tick(t) {
961
+        let thinking = t.blackboard.get(this.thinking) || false;
962
+        let me = t.me;
963
+        if (!thinking) {
964
+            t.blackboard.set(this.thinking, true);
965
+            me.pathfinder.findPath(me.body.center.x, me.body.center.y, me.enemy.body.center.x, me.enemy.body.center.y, (path) => {
966
+                t.blackboard.path = path || [];
967
+                t.blackboard.set(this.thinking, false);
968
+            });
969
+        }
970
+        let path = t.blackboard.path || [];
971
+        return path.length > 0 ? b3.NodeState.SUCCESS : b3.NodeState.RUNNING;
972
+    }
973
+}
974
+class ConditionIsEnemyInLineOfFire extends b3.Condition {
975
+    check(t) {
976
+        let me = t.me;
977
+        if (me.enemy) {
978
+            const epsilon = 10 * Phaser.Math.PI2 / 360;
979
+            let angle = Phaser.Math.angleBetween(me.body.center.x, me.body.center.y, me.enemy.body.center.x, me.enemy.body.center.y);
980
+            angle = Phaser.Math.normalizeAngle(angle);
981
+            if (Phaser.Math.fuzzyEqual(angle, Phaser.Math.PI2, epsilon)) {
982
+                return true;
983
+            }
984
+            if (Phaser.Math.fuzzyEqual(angle, Math.PI / 2, epsilon)) {
985
+                return true;
986
+            }
987
+            if (Phaser.Math.fuzzyEqual(angle, Math.PI, epsilon)) {
988
+                return true;
989
+            }
990
+            if (Phaser.Math.fuzzyEqual(angle, 3 * Math.PI / 2, epsilon)) {
991
+                return true;
992
+            }
993
+        }
994
+        return false;
995
+    }
996
+}
997
+class ActionFire extends b3.Action {
998
+    tick(t) {
999
+        t.me.fire();
1000
+        return b3.NodeState.RUNNING;
1001
+    }
1002
+}
1003
+class ConditionIsNearEnemy extends b3.Condition {
1004
+    check(t) {
1005
+        let me = t.me;
1006
+        return me.enemy && Phaser.Math.distance(me.body.center.x, me.body.center.y, me.enemy.body.center.x, me.enemy.body.center.y) < me.body.width * 2;
1007
+    }
1008
+}
1009
+class ActionAttackEnemy extends b3.Action {
1010
+    tick(t) {
1011
+        if (t.me.attackEnemy()) {
1012
+            return b3.NodeState.SUCCESS;
1013
+        }
1014
+        else {
1015
+            return b3.NodeState.RUNNING;
1016
+        }
1017
+    }
1018
+}
1019
+
1020
+
737 1021
 });
738 1022
 
739
-;require.register("entities/features/Vulnerable.ts", function(exports, require, module) {
1023
+;require.register("entities/SpiderHorde.ts", function(exports, require, module) {
740 1024
 "use strict";
741
-//# sourceMappingURL=Vulnerable.js.map
1025
+const Spider_ts_1 = require("./Spider.ts");
1026
+class SpiderHorde extends Phaser.Group {
1027
+    constructor(target, pathFinder, maxSpiders = 4) {
1028
+        super(target.game);
1029
+        this.appearsRate = 10000;
1030
+        this.nextAppearsTime = 0;
1031
+        this.pathfinder = pathFinder;
1032
+        this.target = target;
1033
+        for (let i = 0; i < maxSpiders; ++i) {
1034
+            this.add(this.createSpider());
1035
+        }
1036
+    }
1037
+    static preload(game) {
1038
+        game.load.atlasXML('spider', 'sprites/lpc/spiders/spider01.png', 'sprites/lpc/spiders/spider.xml');
1039
+    }
1040
+    update() {
1041
+        super.update();
1042
+        this.appears();
1043
+    }
1044
+    createSpider() {
1045
+        const spider = new Spider_ts_1.Spider(this.game, this.pathfinder);
1046
+        const game = this.game;
1047
+        game.addSpriteAnimation(spider.spiderDeath, 'spider.hurt', 6);
1048
+        game.addSpriteAnimation(spider, 'spider.stand.back', 6);
1049
+        game.addSpriteAnimation(spider, 'spider.stand.front', 6);
1050
+        game.addSpriteAnimation(spider, 'spider.stand.left', 6);
1051
+        game.addSpriteAnimation(spider, 'spider.stand.right', 6);
1052
+        game.addSpriteAnimation(spider, 'spider.walk.back', 9);
1053
+        game.addSpriteAnimation(spider, 'spider.walk.front', 9);
1054
+        game.addSpriteAnimation(spider, 'spider.walk.left', 9);
1055
+        game.addSpriteAnimation(spider, 'spider.walk.right', 9);
1056
+        game.addSpriteAnimation(spider, 'spider.attack.back', 9);
1057
+        game.addSpriteAnimation(spider, 'spider.attack.front', 9);
1058
+        game.addSpriteAnimation(spider, 'spider.attack.left', 9);
1059
+        game.addSpriteAnimation(spider, 'spider.attack.right', 9);
1060
+        return spider;
1061
+    }
1062
+    appears() {
1063
+        if (this.game.time.time >= this.nextAppearsTime) {
1064
+            const spider = this.getFirstExists(false);
1065
+            if (spider) {
1066
+                const pos = this.pathfinder.randomWalkablePos();
1067
+                spider.appears(pos.x, pos.y, this.target);
1068
+                this.nextAppearsTime = this.game.time.time + this.appearsRate;
1069
+            }
1070
+        }
1071
+    }
1072
+}
1073
+exports.SpiderHorde = SpiderHorde;
1074
+
1075
+
742 1076
 });
743 1077
 
744
-;require.register("states/AbstractState.ts", function(exports, require, module) {
1078
+require.register("entities/features/Vulnerable.ts", function(exports, require, module) {
745 1079
 "use strict";
746
-var __extends = (this && this.__extends) || function (d, b) {
747
-    for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
748
-    function __() { this.constructor = d; }
749
-    d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
750
-};
751
-var AbstractState = (function (_super) {
752
-    __extends(AbstractState, _super);
753
-    function AbstractState() {
754
-        _super.call(this);
755
-    }
756
-    AbstractState.prototype.create = function () {
757
-        var _this = this;
758
-        this.game.input.keyboard.addKey(Phaser.Keyboard.F).onDown.add(function () { return _this.toggleFullscreen(); });
759
-    };
760
-    AbstractState.prototype.toggleFullscreen = function () {
1080
+
1081
+
1082
+});
1083
+
1084
+require.register("ia/decisions/b3.ts", function(exports, require, module) {
1085
+"use strict";
1086
+class Tree {
1087
+    tick(me, blackboard) {
1088
+        const t = new Tick(me, blackboard);
1089
+        this.root.tick(t);
1090
+    }
1091
+    sequence(...children) {
1092
+        return new Sequence(...children);
1093
+    }
1094
+    selector(...children) {
1095
+        return new Selector(...children);
1096
+    }
1097
+    parallel(...children) {
1098
+        return new Parallel(...children);
1099
+    }
1100
+}
1101
+exports.Tree = Tree;
1102
+class BlackboardKey {
1103
+    constructor() {
1104
+        this.id = Symbol();
1105
+    }
1106
+}
1107
+exports.BlackboardKey = BlackboardKey;
1108
+class Blackboard {
1109
+    constructor() {
1110
+        this.data = {};
1111
+    }
1112
+    get(k) {
1113
+        return this.data[k.id];
1114
+    }
1115
+    set(k, value) {
1116
+        this.data[k.id] = value;
1117
+    }
1118
+    reset() {
1119
+        this.data = {};
1120
+    }
1121
+}
1122
+exports.Blackboard = Blackboard;
1123
+class Tick {
1124
+    constructor(me, b) {
1125
+        this.blackboard = b;
1126
+        this.me = me;
1127
+    }
1128
+}
1129
+exports.Tick = Tick;
1130
+(function (NodeState) {
1131
+    NodeState[NodeState["SUCCESS"] = 0] = "SUCCESS";
1132
+    NodeState[NodeState["FAILURE"] = 1] = "FAILURE";
1133
+    NodeState[NodeState["RUNNING"] = 2] = "RUNNING";
1134
+})(exports.NodeState || (exports.NodeState = {}));
1135
+var NodeState = exports.NodeState;
1136
+class Node {
1137
+}
1138
+exports.Node = Node;
1139
+class Branch extends Node {
1140
+    constructor(...children) {
1141
+        super();
1142
+        this.children = children;
1143
+    }
1144
+}
1145
+exports.Branch = Branch;
1146
+class Leaf extends Node {
1147
+}
1148
+exports.Leaf = Leaf;
1149
+class Selector extends Branch {
1150
+    constructor(...children) {
1151
+        super(...children);
1152
+    }
1153
+    tick(t) {
1154
+        for (let c of this.children) {
1155
+            switch (c.tick(t)) {
1156
+                case NodeState.SUCCESS:
1157
+                    return NodeState.SUCCESS;
1158
+                case NodeState.RUNNING:
1159
+                    return NodeState.RUNNING;
1160
+            }
1161
+        }
1162
+        return NodeState.FAILURE;
1163
+    }
1164
+}
1165
+exports.Selector = Selector;
1166
+class Sequence extends Branch {
1167
+    constructor(...children) {
1168
+        super(...children);
1169
+    }
1170
+    tick(t) {
1171
+        for (let c of this.children) {
1172
+            switch (c.tick(t)) {
1173
+                case NodeState.FAILURE:
1174
+                    return NodeState.FAILURE;
1175
+                case NodeState.RUNNING:
1176
+                    return NodeState.RUNNING;
1177
+            }
1178
+        }
1179
+        return NodeState.SUCCESS;
1180
+    }
1181
+}
1182
+exports.Sequence = Sequence;
1183
+class Parallel extends Branch {
1184
+    constructor(...children) {
1185
+        super(...children);
1186
+    }
1187
+    tick(t) {
1188
+        let failures = 0, successes = 0;
1189
+        for (let c of this.children) {
1190
+            switch (c.tick(t)) {
1191
+                case NodeState.FAILURE:
1192
+                    return ++failures;
1193
+                case NodeState.SUCCESS:
1194
+                    return ++successes;
1195
+            }
1196
+        }
1197
+        if (successes >= this.successThreshold) {
1198
+            return NodeState.SUCCESS;
1199
+        }
1200
+        else if (failures >= this.failureThreshold) {
1201
+            return NodeState.FAILURE;
1202
+        }
1203
+        else {
1204
+            return NodeState.RUNNING;
1205
+        }
1206
+    }
1207
+}
1208
+exports.Parallel = Parallel;
1209
+class Decorator extends Node {
1210
+    constructor(child) {
1211
+        super();
1212
+        this.child = child;
1213
+    }
1214
+}
1215
+exports.Decorator = Decorator;
1216
+class Action extends Leaf {
1217
+}
1218
+exports.Action = Action;
1219
+class Condition extends Leaf {
1220
+    tick(t) {
1221
+        if (this.check(t)) {
1222
+            return NodeState.SUCCESS;
1223
+        }
1224
+        else {
1225
+            return NodeState.FAILURE;
1226
+        }
1227
+    }
1228
+}
1229
+exports.Condition = Condition;
1230
+
1231
+
1232
+});
1233
+
1234
+require.register("ia/services/Pathfinder.ts", function(exports, require, module) {
1235
+"use strict";
1236
+const EasyStar = require('easystarjs');
1237
+class Pathfinder {
1238
+    constructor(map) {
1239
+        this.map = map;
1240
+        const pathfindLayer = map.getLayerIndex('pathfind');
1241
+        const grid = new Array();
1242
+        for (let row = 0; row < map.height; ++row) {
1243
+            var gridRow = new Array(map.width);
1244
+            for (let column = 0; column < map.width; ++column) {
1245
+                const tile = map.getTile(column, row, pathfindLayer);
1246
+                gridRow[column] = this.isTileWalkable(tile) ? 1 : 0;
1247
+            }
1248
+            grid[row] = gridRow;
1249
+        }
1250
+        this.easystar = new EasyStar.js();
1251
+        this.easystar.setGrid(grid);
1252
+        this.easystar.enableDiagonals();
1253
+        this.easystar.setAcceptableTiles([1]);
1254
+    }
1255
+    randomWalkablePos() {
1256
+        const pathfindLayer = this.map.getLayerIndex('pathfind');
1257
+        const rnd = this.map.game.rnd;
1258
+        const maxChances = this.map.width * this.map.height;
1259
+        for (let i = 0; i < maxChances; ++i) {
1260
+            const x = rnd.integerInRange(0, this.map.width - 1);
1261
+            const y = rnd.integerInRange(0, this.map.height - 1);
1262
+            const tile = this.map.getTile(x, y, pathfindLayer);
1263
+            if (this.isTileWalkable(tile)) {
1264
+                return new Phaser.Point(tile.worldX, tile.worldY);
1265
+            }
1266
+        }
1267
+        return null;
1268
+    }
1269
+    isTileWalkable(tile) {
1270
+        return tile && tile.properties['walkable'] == 1;
1271
+    }
1272
+    findPath(startX, startY, endX, endY, callback) {
1273
+        const tileStart = this.map.getTileWorldXY(startX, startY);
1274
+        const tileEnd = this.findNearestWalkableTile(endX, endY);
1275
+        if (tileEnd) {
1276
+            this.easystar.findPath(tileStart.x, tileStart.y, tileEnd.x, tileEnd.y, (path) => {
1277
+                let worldPath;
1278
+                if (path && path.length > 1) {
1279
+                    worldPath = new Array(path.length - 1);
1280
+                    for (let i = 1; i < path.length; ++i) {
1281
+                        const tile = this.map.getTile(path[i].x, path[i].y);
1282
+                        worldPath[i - 1] = new Phaser.Point(tile.worldX + tile.width / 2, tile.worldY + tile.height / 2);
1283
+                    }
1284
+                }
1285
+                else {
1286
+                    worldPath = new Array();
1287
+                }
1288
+                callback(worldPath);
1289
+            });
1290
+        }
1291
+        else {
1292
+            callback(new Array());
1293
+        }
1294
+    }