diff --git a/graphics/ui/battle.svg b/graphics/ui/battle.svg index 07875fd..c8e92cf 100644 --- a/graphics/ui/battle.svg +++ b/graphics/ui/battle.svg @@ -25,6 +25,46 @@ enable-background="new"> + + + + + + + + + + + + + @@ -1236,6 +1276,292 @@ stdDeviation="0.85559144" id="feGaussianBlur5531" /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + transform="translate(0,27.637839)" + style="display:inline"> @@ -3430,147 +3757,407 @@ diff --git a/out/assets/images/battle/splash/base.png b/out/assets/images/battle/splash/base.png new file mode 100644 index 0000000..3cdaa1e Binary files /dev/null and b/out/assets/images/battle/splash/base.png differ diff --git a/out/assets/images/battle/splash/shipcard.png b/out/assets/images/battle/splash/shipcard.png new file mode 100644 index 0000000..12a403a Binary files /dev/null and b/out/assets/images/battle/splash/shipcard.png differ diff --git a/src/ui/Preload.ts b/src/ui/Preload.ts index ef85a40..169026e 100644 --- a/src/ui/Preload.ts +++ b/src/ui/Preload.ts @@ -28,6 +28,8 @@ module TS.SpaceTac.UI { this.loadSheet("options/button.png", 497, 134); this.loadSheet("options/options.png", 128, 128); this.loadSheet("options/toggle.png", 149, 149); + this.loadSheet("battle/splash/base.png", 853, 210); + this.loadSheet("battle/splash/shipcard.png", 99, 114); this.loadImage("battle/background.jpg"); this.loadImage("battle/actionbar/background.png"); this.loadSheet("battle/actionbar/icon.png", 88, 88); diff --git a/src/ui/battle/BattleSplash.ts b/src/ui/battle/BattleSplash.ts new file mode 100644 index 0000000..057aa26 --- /dev/null +++ b/src/ui/battle/BattleSplash.ts @@ -0,0 +1,96 @@ +module TS.SpaceTac.UI { + /** + * Splash screen at the start of battle + */ + export class BattleSplash { + private view: BaseView + private message: Phaser.Image + private player1: Phaser.Image + private player2: Phaser.Image + + constructor(view: BaseView, fleet1: Fleet, fleet2: Fleet) { + this.view = view; + + this.message = view.game.add.image(view.getMidWidth(), view.getMidHeight(), "battle-splash-base", 0); + this.message.anchor.set(0.5); + this.message.visible = false; + + this.player1 = view.game.add.image(0, -70, "battle-splash-base", 2); + this.player1.anchor.set(0.5); + this.player1.visible = false; + this.message.addChild(this.player1); + + let player1_name = view.game.add.text(-240, 22, fleet1.player.name, { font: `bold 22pt Arial`, fill: "#154d13" }); + player1_name.anchor.set(0.5); + player1_name.angle = -48; + this.player1.addChild(player1_name); + + fleet1.ships.forEach((ship, index) => { + let ship_card = view.game.add.image(-100 + index * 96, -26, "battle-splash-shipcard", 0); + ship_card.anchor.set(0.5); + let ship_portrait = view.game.add.image(0, 0, `ship-${ship.model.code}-portrait`); + ship_portrait.scale.set(0.3); + ship_portrait.anchor.set(0.5); + ship_card.addChild(ship_portrait); + this.player1.addChild(ship_card); + }); + + this.player2 = view.game.add.image(0, 70, "battle-splash-base", 2); + this.player2.anchor.set(0.5); + this.player2.angle = 180; + this.player2.visible = false; + this.message.addChild(this.player2); + + let player2_name = view.game.add.text(-240, 22, fleet2.player.name, { font: `bold 22pt Arial`, fill: "#651713" }); + player2_name.anchor.set(0.5); + player2_name.angle = -228; + this.player2.addChild(player2_name); + + fleet2.ships.forEach((ship, index) => { + let ship_card = view.game.add.image(-104 + index * 96, -32, "battle-splash-shipcard", 1); + ship_card.anchor.set(0.5); + let ship_portrait = view.game.add.image(0, 0, `ship-${ship.model.code}-portrait`); + ship_portrait.scale.set(0.3); + ship_portrait.anchor.set(0.5); + ship_card.angle = 180; + ship_card.addChild(ship_portrait); + this.player2.addChild(ship_card); + }); + } + + /** + * Add the splash to a view layer + */ + moveToLayer(layer: Phaser.Group): void { + layer.add(this.message); + } + + /** + * Start the animation + */ + async start(): Promise { + let anims = this.view.animations; + this.message.visible = true; + this.message.scale.set(0.8); + + await anims.addAnimation(this.message.scale, { x: 1, y: 1 }, 300, Phaser.Easing.Bounce.Out); + + this.view.timer.schedule(600, () => this.message.frame = 1); + this.view.timer.schedule(630, () => this.message.frame = 0); + this.view.timer.schedule(640, () => this.message.frame = 1); + this.view.timer.schedule(655, () => this.message.frame = 0); + this.view.timer.schedule(680, () => this.message.frame = 1); + + this.player1.x = -2000; + this.player1.visible = true; + this.player2.x = 2000; + this.player2.visible = true; + anims.addAnimation(this.player2, { x: 129 }, 600, Phaser.Easing.Bounce.Out, 400); + await anims.addAnimation(this.player1, { x: -133 }, 600, Phaser.Easing.Bounce.Out, 400); + + await anims.addAnimation(this.message, { alpha: 0 }, 500, Phaser.Easing.Linear.None, 1500); + + this.message.destroy(true); + } + } +} diff --git a/src/ui/battle/BattleView.ts b/src/ui/battle/BattleView.ts index 6e5bd52..fc7f2b9 100644 --- a/src/ui/battle/BattleView.ts +++ b/src/ui/battle/BattleView.ts @@ -107,7 +107,7 @@ module TS.SpaceTac.UI { this.targetting.moveToLayer(this.arena.layer_targetting); // "Battle" animation - this.displayFightMessage(); + this.showSplash(); // BGM this.gameui.audio.startMusic("mechanolith", 0.2); @@ -150,17 +150,13 @@ module TS.SpaceTac.UI { } } - // Display an animated "BATTLE" text in the center of the view - displayFightMessage(): void { - var text = this.game.add.text(this.getMidWidth(), this.getMidHeight(), "BATTLE !", - { align: "center", font: "bold 42px Arial", fill: "#EE2233" }); - text.anchor.set(0.5, 0.5); - this.game.tweens.create(text.scale).to({ x: 3, y: 3 }).start(); - var text_anim = this.game.tweens.create(text).to({ alpha: 0 }); - text_anim.onComplete.addOnce(() => { - text.destroy(); - }); - text_anim.start(); + /** + * Display the splash screen at the star of battle + */ + showSplash(): void { + let splash = new BattleSplash(this, this.battle.fleets[0], this.battle.fleets[1]); + splash.moveToLayer(this.layer_overlay); + splash.start(); } // Method called when cursor starts hovering over a ship (or its icon) diff --git a/src/ui/common/Animations.ts b/src/ui/common/Animations.ts index 1f17415..dfaae68 100644 --- a/src/ui/common/Animations.ts +++ b/src/ui/common/Animations.ts @@ -129,6 +129,21 @@ module TS.SpaceTac.UI { return result; } + /** + * Add an asynchronous animation to an object. + */ + addAnimation(obj: any, properties: any, duration: number, ease: Function, delay = 0): Promise { + return new Promise((resolve, reject) => { + let tween = this.tweens.create(obj); + tween.to(properties, duration, ease, false, delay); + tween.onComplete.addOnce(() => { + this.tweens.remove(tween); + resolve(); + }); + tween.start(); + }); + } + /** * Interpolate a rotation value * diff --git a/src/ui/common/Audio.ts b/src/ui/common/Audio.ts index 573ba39..458c8bd 100644 --- a/src/ui/common/Audio.ts +++ b/src/ui/common/Audio.ts @@ -26,9 +26,7 @@ module TS.SpaceTac.UI { startMusic(key: string, volume = 1): void { key = "music-" + key; if (this.isActive()) { - if (this.music && this.music.key !== key) { - this.stopMusic(); - } + this.stopMusic(); if (!this.music) { this.music_playing_volume = volume; this.music = this.game.sound.play(key, volume * this.music_volume, true);