class Robot { constructor(height, width, posX, posY, color, scene) { this.height = height; this.width = width; this.x = posX; this.y = posY; this.color = color; this.range = WIDTH_MAP / 2; this.damage = DAMAGE; this.life = new HealthBar(scene, this.width * 2, this.width / 3, this.x, this.y - this.width, LIFE, 0x008000); this.shield = new HealthBar(scene, this.width * 2, this.width / 3, this.x, this.y - this.width * 1.5, SHIELD, 0x0000FF); this.canAttack = true; this.missile = new Missile(scene, 'bullet', this.width / 5, this.width / 4); scene.add.existing(this.missile); this.addScene(scene); this.lNode = []; let condition = new Condition(this, true, false, 0.5, 0); condition.addNode(new Move(false)); this.addNode(condition); this.addNode(new Attack()); this.addNode(new Move(true)); } addScene(scene) { this.scene = scene; this.circle = this.scene.add.circle(this.x, this.y, this.width / 2, this.color); } setX(x) { this.x = x; this.circle.setX(this.x); this.life.setX(this.x); this.shield.setX(this.x); } setY(y) { this.y = y; this.life.setY(this.y - this.width); this.shield.setY(this.y - this.width * 1.5); this.circle.setY(this.y); } setTarget(target) { this.target = target; this.updateTarget(); } updateTarget() { if (this.verifyTarget()) this.setTargetPos(this.target.x, this.target.y); } setTargetPos(x, y) { let diffX = this.target.x - this.x; let diffY = this.target.y - this.y; let hypot = Math.hypot(diffX, diffY); this.velocityX = diffX / hypot * WIDTH_MAP / 1000 * SPEED; this.velocityY = diffY / hypot * WIDTH_MAP / 1000 * SPEED; } advanceToTarget() { if (this.verifyTarget()) { if ((this.velocityX >= 0 && this.x >= this.target.x) || (this.velocityX <= 0 && this.x <= this.target.x)) this.setX(this.target.x); else this.setX(this.x + this.velocityX); if ((this.velocityY >= 0 && this.y >= this.target.y) || (this.velocityY <= 0 && this.y <= this.target.y)) this.setY(this.target.y); else this.setY(this.y + this.velocityY); return true; } return false; } fleeFromTarget() { if (this.verifyTarget()) { if (this.velocityX >= 0 && this.x - this.width / 2 <= 0) this.setX(this.width / 2); else if (this.velocityX <= 0 && this.x + this.width / 2 >= WIDTH_MAP) this.setX(WIDTH_MAP - this.width / 2); else this.setX(this.x - this.velocityX); if (this.velocityY >= 0 && this.y - this.width / 2 <= 0) this.setY(this.height / 2); else if (this.velocityY <= 0 && this.y + this.width / 2 >= WIDTH_MAP) this.setY(WIDTH_MAP - this.height / 2); else this.setY(this.y - this.velocityY); return true; } return false; } attackTarget() { if (this.verifyTarget() && this.target.isAlive() && this.isTargetInRange()) { if (this.canAttack) this.attack(this.target); return true; } return false; } verifyTarget() { if (this.haveTarget()) { if (!this.target.isAlive()) { this.setTarget(null); return false; } return true; } return false; } attack(target) { this.canAttack = false; this.missile.setPosition(this.x, this.y).setVisible(true); this.missile.setRotation(Math.atan2(this.y - this.target.y, this.x - this.target.x) - 3.14 / 2); this.scene.tweens.add({ targets: this.missile, x: target.x, y: target.y, ease: 'Linear', duration: 200, onComplete: () => this.finishAttack(target) }); this.scene.time.addEvent({delay: Phaser.Math.Between(1000, 3000), callback: this.reload, callbackScope: this}); } finishAttack(target) { if (target.beAttack(this.damage)) { this.setTarget(null); } this.missile.setVisible(false); } reload() { this.canAttack = true; } beAttack(damage) { let diff = this.shield.decrease(damage) if (diff > 0) { console.log("Shield Broken"); this.life.decrease(diff); } return this.die(); } isTargetInRange() { if (this.verifyTarget()) { return this.calcDistance(this.target) < this.range; } return false; } calcDistance(robot) { return Math.hypot(robot.x - this.x, robot.y - this.y); } isAlive() { return this.life.value > 0; } die() { if (this.life.value === 0) { this.circle.destroy(); this.shield.destroy(); this.life.destroy(); return true; } return false; } haveTarget() { return this.target != null; } read() { for (let i = 0; i < this.lNode.length; i++) { if (this.lNode[i].do(this)) { break; } } } addNode(node) { this.lNode.push(node); } cleanNodes() { this.lNode = []; } }