/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); var storage = LK.import("@upit/storage.v1", { bestScore: 0 }); var facekit = LK.import("@upit/facekit.v1"); /**** * Classes ****/ var Base = Container.expand(function () { var self = Container.call(this); self.graphics = self.attachAsset('base', { anchorX: 0.5, anchorY: 0.5 }); self.health = 100; self.isPlayerBase = true; // Health bar background self.healthBarBg = self.attachAsset('unit', { width: 300, height: 20, color: 0x000000, anchorX: 0.5, anchorY: 0.5, y: -180 }); // Health bar foreground self.healthBar = self.attachAsset('unit', { width: 300, height: 20, color: 0x00ff00, anchorX: 0, anchorY: 0.5, y: -180, x: -150 }); self.takeDamage = function (amount) { self.health -= amount; if (self.health < 0) { self.health = 0; } // Update health bar width self.healthBar.width = self.health / 100 * 300; if (self.health <= 0 && self.isPlayerBase) { LK.showGameOver(); } else if (self.health <= 0 && !self.isPlayerBase) { // Player wins LK.setScore(LK.getScore() + 1000); LK.showYouWin(); } }; return self; }); var EnemyBase = Base.expand(function () { var self = Base.call(this); // Override base graphics with enemy base self.graphics.destroy(); self.graphics = self.attachAsset('enemyBase', { anchorX: 0.5, anchorY: 0.5 }); self.healthBar.tint = 0xff0000; self.isPlayerBase = false; return self; }); var Enemy = Container.expand(function () { var self = Container.call(this); self.graphics = self.attachAsset('enemy', { anchorX: 0.5, anchorY: 0.5 }); self.speed = 3; self.alive = true; self.targetUnit = null; self.lastPosition = { x: 0, y: 0 }; self.update = function () { if (!self.alive) { return; } self.lastPosition.x = self.x; self.lastPosition.y = self.y; // If we have a target unit, move toward it if (self.targetUnit && self.targetUnit.alive) { var dx = self.targetUnit.x - self.x; var dy = self.targetUnit.y - self.y; var distance = Math.sqrt(dx * dx + dy * dy); if (distance > self.speed) { self.x += dx / distance * self.speed; self.y += dy / distance * self.speed; } } else { // No target or target is dead, find new target self.findNewTarget(); } }; self.findNewTarget = function () { var closestUnit = null; var closestDistance = Infinity; // Find the closest military unit for (var i = 0; i < units.length; i++) { var unit = units[i]; if (!unit.alive) { continue; } var dx = unit.x - self.x; var dy = unit.y - self.y; var distance = Math.sqrt(dx * dx + dy * dy); // If target is in stealth mode and not super close, can't detect it if (unit.state === "stealth" && distance > 100) { continue; } if (distance < closestDistance) { closestDistance = distance; closestUnit = unit; } } self.targetUnit = closestUnit; }; self.kill = function () { if (!self.alive) { return; } self.alive = false; tween(self, { alpha: 0 }, { duration: 500, onFinish: function onFinish() { self.destroy(); } }); }; return self; }); var MilitaryUnit = Container.expand(function () { var self = Container.call(this); // Default state is normal self.state = "normal"; self.targetPosition = null; self.speed = 5; self.alive = true; self.score = 0; // Normal unit representation self.normalGraphics = self.attachAsset('unit', { anchorX: 0.5, anchorY: 0.5 }); // Stealth unit representation (initially hidden) self.stealthGraphics = self.attachAsset('stealth', { anchorX: 0.5, anchorY: 0.5, alpha: 0 }); // Attack unit representation (initially hidden) self.attackGraphics = self.attachAsset('attack', { anchorX: 0.5, anchorY: 0.5, alpha: 0 }); // Set initial state self.setState = function (newState) { if (newState === self.state) { return; } // Hide all graphics first self.normalGraphics.alpha = 0; self.stealthGraphics.alpha = 0; self.attackGraphics.alpha = 0; // Show the appropriate graphics if (newState === "normal") { self.normalGraphics.alpha = 1; self.speed = 5; } else if (newState === "stealth") { self.stealthGraphics.alpha = 1; self.speed = 3; // Slower in stealth mode } else if (newState === "attack") { self.attackGraphics.alpha = 1; self.speed = 7; // Faster in attack mode } self.state = newState; }; // Move toward target if one is set self.update = function () { if (!self.alive) { return; } if (self.targetPosition) { var dx = self.targetPosition.x - self.x; var dy = self.targetPosition.y - self.y; var distance = Math.sqrt(dx * dx + dy * dy); if (distance > self.speed) { self.x += dx / distance * self.speed; self.y += dy / distance * self.speed; } else { self.x = self.targetPosition.x; self.y = self.targetPosition.y; self.targetPosition = null; } } }; // Destroy unit self.kill = function () { if (!self.alive) { return; } self.alive = false; tween(self, { alpha: 0 }, { duration: 500, onFinish: function onFinish() { self.destroy(); } }); }; return self; }); var Target = Container.expand(function () { var self = Container.call(this); self.graphics = self.attachAsset('target', { anchorX: 0.5, anchorY: 0.5, alpha: 0.5 }); // Pulse animation self.pulse = function () { tween(self.graphics, { alpha: 0.8, scaleX: 1.2, scaleY: 1.2 }, { duration: 500, easing: tween.easeOut, onFinish: function onFinish() { tween(self.graphics, { alpha: 0.5, scaleX: 1, scaleY: 1 }, { duration: 500, easing: tween.easeIn }); } }); }; self.pulse(); return self; }); var VoiceIndicator = Container.expand(function () { var self = Container.call(this); // Background self.bg = self.attachAsset('unit', { width: 400, height: 100, color: 0x000000, anchorX: 0.5, anchorY: 0.5, alpha: 0.5 }); // Voice level indicator self.level = self.attachAsset('unit', { width: 0, height: 80, color: 0x00ff00, anchorX: 0, anchorY: 0.5, x: -190 }); // Text labels self.whisperText = new Text2("Whisper", { size: 40, fill: 0xFFFFFF }); self.whisperText.anchor.set(0.5); self.whisperText.x = -135; self.whisperText.y = 50; self.addChild(self.whisperText); self.normalText = new Text2("Normal", { size: 40, fill: 0xFFFFFF }); self.normalText.anchor.set(0.5); self.normalText.x = 0; self.normalText.y = 50; self.addChild(self.normalText); self.shoutText = new Text2("Shout", { size: 40, fill: 0xFFFFFF }); self.shoutText.anchor.set(0.5); self.shoutText.x = 135; self.shoutText.y = 50; self.addChild(self.shoutText); // Update the indicator based on volume self.update = function () { var volume = facekit.volume; // Calculate width based on volume (0-1) var width = volume * 380; self.level.width = width; // Change color based on volume if (volume < 0.3) { self.level.tint = 0x33cc33; // Green for whisper } else if (volume > 0.7) { self.level.tint = 0xcc3333; // Red for shout } else { self.level.tint = 0x3366cc; // Blue for normal } }; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ backgroundColor: 0x222222 }); /**** * Game Code ****/ // Game state variables var units = []; var enemies = []; var target = null; var playerBase = null; var enemyBase = null; var voiceIndicator = null; var voiceMode = "normal"; var lastVoiceMode = "normal"; var lastSpawnTime = 0; var currentWave = 1; var gameStarted = false; // Setup GUI var scoreTxt = new Text2("Score: 0", { size: 60, fill: 0xFFFFFF }); scoreTxt.anchor.set(0.5, 0); LK.gui.top.addChild(scoreTxt); var waveTxt = new Text2("Wave: 1", { size: 60, fill: 0xFFFFFF }); waveTxt.anchor.set(1, 0); waveTxt.x = -50; LK.gui.topRight.addChild(waveTxt); var instructionsTxt = new Text2("Use your voice to command units:\nWhisper - Stealth Mode\nNormal Voice - Normal Mode\nShout - Attack Mode\n\nTap to place target location", { size: 50, fill: 0xFFFFFF }); instructionsTxt.anchor.set(0.5, 0.5); LK.gui.center.addChild(instructionsTxt); var startButton = LK.getAsset('unit', { width: 300, height: 100, color: 0x3366cc, anchorX: 0.5, anchorY: 0.5 }); LK.gui.center.addChild(startButton); startButton.y = 200; var startText = new Text2("START", { size: 60, fill: 0xFFFFFF }); startText.anchor.set(0.5, 0.5); startButton.addChild(startText); // Start game when button is pressed startButton.down = function () { startGame(); }; function startGame() { gameStarted = true; LK.gui.center.removeChild(instructionsTxt); LK.gui.center.removeChild(startButton); // Create bases playerBase = new Base(); playerBase.x = 1024; playerBase.y = 2300; game.addChild(playerBase); enemyBase = new EnemyBase(); enemyBase.x = 1024; enemyBase.y = 400; game.addChild(enemyBase); // Create voice indicator voiceIndicator = new VoiceIndicator(); voiceIndicator.x = 1024; voiceIndicator.y = 2600; game.addChild(voiceIndicator); // Create initial units createUnit(900, 2000); createUnit(1150, 2000); // Start background music LK.playMusic('bgmusic'); } function createUnit(x, y) { var unit = new MilitaryUnit(); unit.x = x; unit.y = y; game.addChild(unit); units.push(unit); return unit; } function createEnemy(x, y) { var enemy = new Enemy(); enemy.x = x; enemy.y = y; game.addChild(enemy); enemies.push(enemy); return enemy; } function spawnEnemies() { var now = Date.now(); if (now - lastSpawnTime > 5000) { // Spawn every 5 seconds lastSpawnTime = now; // Spawn enemies based on wave var count = Math.min(2 + currentWave, 8); for (var i = 0; i < count; i++) { var x = 400 + Math.random() * 1248; var y = 400 + Math.random() * 200; createEnemy(x, y); } // Increase wave currentWave++; waveTxt.setText("Wave: " + currentWave); } } function createTarget(x, y) { // Remove existing target if there is one if (target) { target.destroy(); } // Create new target target = new Target(); target.x = x; target.y = y; game.addChild(target); // Command all units to move to target for (var i = 0; i < units.length; i++) { if (units[i].alive) { units[i].targetPosition = { x: x, y: y }; } } // Play sound based on voice mode if (voiceMode === "stealth") { LK.getSound('stealth').play(); } else if (voiceMode === "attack") { LK.getSound('attack').play(); } else { LK.getSound('order').play(); } } function checkCollisions() { // Check for enemy-unit collisions for (var i = enemies.length - 1; i >= 0; i--) { var enemy = enemies[i]; if (!enemy.alive) { continue; } // Check collision with player base if (playerBase && enemy.intersects(playerBase)) { playerBase.takeDamage(1); enemy.kill(); enemies.splice(i, 1); continue; } // Check collision with units for (var j = units.length - 1; j >= 0; j--) { var unit = units[j]; if (!unit.alive) { continue; } if (unit.intersects(enemy)) { // Combat outcome depends on unit state if (unit.state === "attack") { // Unit is in attack mode, more likely to win enemy.kill(); enemies.splice(i, 1); LK.setScore(LK.getScore() + 100); break; } else if (unit.state === "stealth") { // Stealth units can sometimes evade if (Math.random() > 0.7) { // Unit escapes unit.x += Math.random() * 100 - 50; unit.y += Math.random() * 100 - 50; } else { unit.kill(); units.splice(j, 1); } } else { // Normal combat, 50/50 chance if (Math.random() > 0.5) { enemy.kill(); enemies.splice(i, 1); LK.setScore(LK.getScore() + 50); } else { unit.kill(); units.splice(j, 1); } break; } } } } // Check for units reaching enemy base for (var k = units.length - 1; k >= 0; k--) { var unit = units[k]; if (!unit.alive) { continue; } if (enemyBase && unit.intersects(enemyBase)) { // Unit is attacking enemy base var damage = unit.state === "attack" ? 20 : 10; enemyBase.takeDamage(damage); unit.kill(); units.splice(k, 1); LK.setScore(LK.getScore() + 200); } } } function determineVoiceMode() { var volume = facekit.volume; if (volume < 0.1) { // No sound, keep previous mode return voiceMode; } else if (volume < 0.3) { return "stealth"; } else if (volume > 0.7) { return "attack"; } else { return "normal"; } } function spawnNewUnits() { // Spawn new units every 10 seconds if we have fewer than 5 if (LK.ticks % 600 === 0 && units.length < 5) { createUnit(900 + Math.random() * 250, 2000 + Math.random() * 200); } } function updateScore() { scoreTxt.setText("Score: " + LK.getScore()); // Store best score if current score is higher if (LK.getScore() > storage.bestScore) { storage.bestScore = LK.getScore(); } } // Game down event - place target game.down = function (x, y) { if (!gameStarted) { return; } // Don't place target too close to enemy base or on bases var distToEnemyBase = Math.sqrt(Math.pow(x - enemyBase.x, 2) + Math.pow(y - enemyBase.y, 2)); var distToPlayerBase = Math.sqrt(Math.pow(x - playerBase.x, 2) + Math.pow(y - playerBase.y, 2)); if (distToEnemyBase > 350 && distToPlayerBase > 350) { createTarget(x, y); } }; // Game tick event game.update = function () { if (!gameStarted) { return; } // Update voice mode based on audio input voiceMode = determineVoiceMode(); // Update voice indicator if (voiceIndicator) { voiceIndicator.update(); } // Update all units with current voice mode if (voiceMode !== lastVoiceMode) { for (var i = 0; i < units.length; i++) { if (units[i].alive) { units[i].setState(voiceMode); } } lastVoiceMode = voiceMode; } // Check for collisions checkCollisions(); // Spawn enemies spawnEnemies(); // Spawn new units if needed spawnNewUnits(); // Update score display updateScore(); };
===================================================================
--- original.js
+++ change.js
@@ -1,6 +1,599 @@
-/****
+/****
+* Plugins
+****/
+var tween = LK.import("@upit/tween.v1");
+var storage = LK.import("@upit/storage.v1", {
+ bestScore: 0
+});
+var facekit = LK.import("@upit/facekit.v1");
+
+/****
+* Classes
+****/
+var Base = Container.expand(function () {
+ var self = Container.call(this);
+ self.graphics = self.attachAsset('base', {
+ anchorX: 0.5,
+ anchorY: 0.5
+ });
+ self.health = 100;
+ self.isPlayerBase = true;
+ // Health bar background
+ self.healthBarBg = self.attachAsset('unit', {
+ width: 300,
+ height: 20,
+ color: 0x000000,
+ anchorX: 0.5,
+ anchorY: 0.5,
+ y: -180
+ });
+ // Health bar foreground
+ self.healthBar = self.attachAsset('unit', {
+ width: 300,
+ height: 20,
+ color: 0x00ff00,
+ anchorX: 0,
+ anchorY: 0.5,
+ y: -180,
+ x: -150
+ });
+ self.takeDamage = function (amount) {
+ self.health -= amount;
+ if (self.health < 0) {
+ self.health = 0;
+ }
+ // Update health bar width
+ self.healthBar.width = self.health / 100 * 300;
+ if (self.health <= 0 && self.isPlayerBase) {
+ LK.showGameOver();
+ } else if (self.health <= 0 && !self.isPlayerBase) {
+ // Player wins
+ LK.setScore(LK.getScore() + 1000);
+ LK.showYouWin();
+ }
+ };
+ return self;
+});
+var EnemyBase = Base.expand(function () {
+ var self = Base.call(this);
+ // Override base graphics with enemy base
+ self.graphics.destroy();
+ self.graphics = self.attachAsset('enemyBase', {
+ anchorX: 0.5,
+ anchorY: 0.5
+ });
+ self.healthBar.tint = 0xff0000;
+ self.isPlayerBase = false;
+ return self;
+});
+var Enemy = Container.expand(function () {
+ var self = Container.call(this);
+ self.graphics = self.attachAsset('enemy', {
+ anchorX: 0.5,
+ anchorY: 0.5
+ });
+ self.speed = 3;
+ self.alive = true;
+ self.targetUnit = null;
+ self.lastPosition = {
+ x: 0,
+ y: 0
+ };
+ self.update = function () {
+ if (!self.alive) {
+ return;
+ }
+ self.lastPosition.x = self.x;
+ self.lastPosition.y = self.y;
+ // If we have a target unit, move toward it
+ if (self.targetUnit && self.targetUnit.alive) {
+ var dx = self.targetUnit.x - self.x;
+ var dy = self.targetUnit.y - self.y;
+ var distance = Math.sqrt(dx * dx + dy * dy);
+ if (distance > self.speed) {
+ self.x += dx / distance * self.speed;
+ self.y += dy / distance * self.speed;
+ }
+ } else {
+ // No target or target is dead, find new target
+ self.findNewTarget();
+ }
+ };
+ self.findNewTarget = function () {
+ var closestUnit = null;
+ var closestDistance = Infinity;
+ // Find the closest military unit
+ for (var i = 0; i < units.length; i++) {
+ var unit = units[i];
+ if (!unit.alive) {
+ continue;
+ }
+ var dx = unit.x - self.x;
+ var dy = unit.y - self.y;
+ var distance = Math.sqrt(dx * dx + dy * dy);
+ // If target is in stealth mode and not super close, can't detect it
+ if (unit.state === "stealth" && distance > 100) {
+ continue;
+ }
+ if (distance < closestDistance) {
+ closestDistance = distance;
+ closestUnit = unit;
+ }
+ }
+ self.targetUnit = closestUnit;
+ };
+ self.kill = function () {
+ if (!self.alive) {
+ return;
+ }
+ self.alive = false;
+ tween(self, {
+ alpha: 0
+ }, {
+ duration: 500,
+ onFinish: function onFinish() {
+ self.destroy();
+ }
+ });
+ };
+ return self;
+});
+var MilitaryUnit = Container.expand(function () {
+ var self = Container.call(this);
+ // Default state is normal
+ self.state = "normal";
+ self.targetPosition = null;
+ self.speed = 5;
+ self.alive = true;
+ self.score = 0;
+ // Normal unit representation
+ self.normalGraphics = self.attachAsset('unit', {
+ anchorX: 0.5,
+ anchorY: 0.5
+ });
+ // Stealth unit representation (initially hidden)
+ self.stealthGraphics = self.attachAsset('stealth', {
+ anchorX: 0.5,
+ anchorY: 0.5,
+ alpha: 0
+ });
+ // Attack unit representation (initially hidden)
+ self.attackGraphics = self.attachAsset('attack', {
+ anchorX: 0.5,
+ anchorY: 0.5,
+ alpha: 0
+ });
+ // Set initial state
+ self.setState = function (newState) {
+ if (newState === self.state) {
+ return;
+ }
+ // Hide all graphics first
+ self.normalGraphics.alpha = 0;
+ self.stealthGraphics.alpha = 0;
+ self.attackGraphics.alpha = 0;
+ // Show the appropriate graphics
+ if (newState === "normal") {
+ self.normalGraphics.alpha = 1;
+ self.speed = 5;
+ } else if (newState === "stealth") {
+ self.stealthGraphics.alpha = 1;
+ self.speed = 3; // Slower in stealth mode
+ } else if (newState === "attack") {
+ self.attackGraphics.alpha = 1;
+ self.speed = 7; // Faster in attack mode
+ }
+ self.state = newState;
+ };
+ // Move toward target if one is set
+ self.update = function () {
+ if (!self.alive) {
+ return;
+ }
+ if (self.targetPosition) {
+ var dx = self.targetPosition.x - self.x;
+ var dy = self.targetPosition.y - self.y;
+ var distance = Math.sqrt(dx * dx + dy * dy);
+ if (distance > self.speed) {
+ self.x += dx / distance * self.speed;
+ self.y += dy / distance * self.speed;
+ } else {
+ self.x = self.targetPosition.x;
+ self.y = self.targetPosition.y;
+ self.targetPosition = null;
+ }
+ }
+ };
+ // Destroy unit
+ self.kill = function () {
+ if (!self.alive) {
+ return;
+ }
+ self.alive = false;
+ tween(self, {
+ alpha: 0
+ }, {
+ duration: 500,
+ onFinish: function onFinish() {
+ self.destroy();
+ }
+ });
+ };
+ return self;
+});
+var Target = Container.expand(function () {
+ var self = Container.call(this);
+ self.graphics = self.attachAsset('target', {
+ anchorX: 0.5,
+ anchorY: 0.5,
+ alpha: 0.5
+ });
+ // Pulse animation
+ self.pulse = function () {
+ tween(self.graphics, {
+ alpha: 0.8,
+ scaleX: 1.2,
+ scaleY: 1.2
+ }, {
+ duration: 500,
+ easing: tween.easeOut,
+ onFinish: function onFinish() {
+ tween(self.graphics, {
+ alpha: 0.5,
+ scaleX: 1,
+ scaleY: 1
+ }, {
+ duration: 500,
+ easing: tween.easeIn
+ });
+ }
+ });
+ };
+ self.pulse();
+ return self;
+});
+var VoiceIndicator = Container.expand(function () {
+ var self = Container.call(this);
+ // Background
+ self.bg = self.attachAsset('unit', {
+ width: 400,
+ height: 100,
+ color: 0x000000,
+ anchorX: 0.5,
+ anchorY: 0.5,
+ alpha: 0.5
+ });
+ // Voice level indicator
+ self.level = self.attachAsset('unit', {
+ width: 0,
+ height: 80,
+ color: 0x00ff00,
+ anchorX: 0,
+ anchorY: 0.5,
+ x: -190
+ });
+ // Text labels
+ self.whisperText = new Text2("Whisper", {
+ size: 40,
+ fill: 0xFFFFFF
+ });
+ self.whisperText.anchor.set(0.5);
+ self.whisperText.x = -135;
+ self.whisperText.y = 50;
+ self.addChild(self.whisperText);
+ self.normalText = new Text2("Normal", {
+ size: 40,
+ fill: 0xFFFFFF
+ });
+ self.normalText.anchor.set(0.5);
+ self.normalText.x = 0;
+ self.normalText.y = 50;
+ self.addChild(self.normalText);
+ self.shoutText = new Text2("Shout", {
+ size: 40,
+ fill: 0xFFFFFF
+ });
+ self.shoutText.anchor.set(0.5);
+ self.shoutText.x = 135;
+ self.shoutText.y = 50;
+ self.addChild(self.shoutText);
+ // Update the indicator based on volume
+ self.update = function () {
+ var volume = facekit.volume;
+ // Calculate width based on volume (0-1)
+ var width = volume * 380;
+ self.level.width = width;
+ // Change color based on volume
+ if (volume < 0.3) {
+ self.level.tint = 0x33cc33; // Green for whisper
+ } else if (volume > 0.7) {
+ self.level.tint = 0xcc3333; // Red for shout
+ } else {
+ self.level.tint = 0x3366cc; // Blue for normal
+ }
+ };
+ return self;
+});
+
+/****
* Initialize Game
-****/
+****/
var game = new LK.Game({
- backgroundColor: 0x000000
-});
\ No newline at end of file
+ backgroundColor: 0x222222
+});
+
+/****
+* Game Code
+****/
+// Game state variables
+var units = [];
+var enemies = [];
+var target = null;
+var playerBase = null;
+var enemyBase = null;
+var voiceIndicator = null;
+var voiceMode = "normal";
+var lastVoiceMode = "normal";
+var lastSpawnTime = 0;
+var currentWave = 1;
+var gameStarted = false;
+// Setup GUI
+var scoreTxt = new Text2("Score: 0", {
+ size: 60,
+ fill: 0xFFFFFF
+});
+scoreTxt.anchor.set(0.5, 0);
+LK.gui.top.addChild(scoreTxt);
+var waveTxt = new Text2("Wave: 1", {
+ size: 60,
+ fill: 0xFFFFFF
+});
+waveTxt.anchor.set(1, 0);
+waveTxt.x = -50;
+LK.gui.topRight.addChild(waveTxt);
+var instructionsTxt = new Text2("Use your voice to command units:\nWhisper - Stealth Mode\nNormal Voice - Normal Mode\nShout - Attack Mode\n\nTap to place target location", {
+ size: 50,
+ fill: 0xFFFFFF
+});
+instructionsTxt.anchor.set(0.5, 0.5);
+LK.gui.center.addChild(instructionsTxt);
+var startButton = LK.getAsset('unit', {
+ width: 300,
+ height: 100,
+ color: 0x3366cc,
+ anchorX: 0.5,
+ anchorY: 0.5
+});
+LK.gui.center.addChild(startButton);
+startButton.y = 200;
+var startText = new Text2("START", {
+ size: 60,
+ fill: 0xFFFFFF
+});
+startText.anchor.set(0.5, 0.5);
+startButton.addChild(startText);
+// Start game when button is pressed
+startButton.down = function () {
+ startGame();
+};
+function startGame() {
+ gameStarted = true;
+ LK.gui.center.removeChild(instructionsTxt);
+ LK.gui.center.removeChild(startButton);
+ // Create bases
+ playerBase = new Base();
+ playerBase.x = 1024;
+ playerBase.y = 2300;
+ game.addChild(playerBase);
+ enemyBase = new EnemyBase();
+ enemyBase.x = 1024;
+ enemyBase.y = 400;
+ game.addChild(enemyBase);
+ // Create voice indicator
+ voiceIndicator = new VoiceIndicator();
+ voiceIndicator.x = 1024;
+ voiceIndicator.y = 2600;
+ game.addChild(voiceIndicator);
+ // Create initial units
+ createUnit(900, 2000);
+ createUnit(1150, 2000);
+ // Start background music
+ LK.playMusic('bgmusic');
+}
+function createUnit(x, y) {
+ var unit = new MilitaryUnit();
+ unit.x = x;
+ unit.y = y;
+ game.addChild(unit);
+ units.push(unit);
+ return unit;
+}
+function createEnemy(x, y) {
+ var enemy = new Enemy();
+ enemy.x = x;
+ enemy.y = y;
+ game.addChild(enemy);
+ enemies.push(enemy);
+ return enemy;
+}
+function spawnEnemies() {
+ var now = Date.now();
+ if (now - lastSpawnTime > 5000) {
+ // Spawn every 5 seconds
+ lastSpawnTime = now;
+ // Spawn enemies based on wave
+ var count = Math.min(2 + currentWave, 8);
+ for (var i = 0; i < count; i++) {
+ var x = 400 + Math.random() * 1248;
+ var y = 400 + Math.random() * 200;
+ createEnemy(x, y);
+ }
+ // Increase wave
+ currentWave++;
+ waveTxt.setText("Wave: " + currentWave);
+ }
+}
+function createTarget(x, y) {
+ // Remove existing target if there is one
+ if (target) {
+ target.destroy();
+ }
+ // Create new target
+ target = new Target();
+ target.x = x;
+ target.y = y;
+ game.addChild(target);
+ // Command all units to move to target
+ for (var i = 0; i < units.length; i++) {
+ if (units[i].alive) {
+ units[i].targetPosition = {
+ x: x,
+ y: y
+ };
+ }
+ }
+ // Play sound based on voice mode
+ if (voiceMode === "stealth") {
+ LK.getSound('stealth').play();
+ } else if (voiceMode === "attack") {
+ LK.getSound('attack').play();
+ } else {
+ LK.getSound('order').play();
+ }
+}
+function checkCollisions() {
+ // Check for enemy-unit collisions
+ for (var i = enemies.length - 1; i >= 0; i--) {
+ var enemy = enemies[i];
+ if (!enemy.alive) {
+ continue;
+ }
+ // Check collision with player base
+ if (playerBase && enemy.intersects(playerBase)) {
+ playerBase.takeDamage(1);
+ enemy.kill();
+ enemies.splice(i, 1);
+ continue;
+ }
+ // Check collision with units
+ for (var j = units.length - 1; j >= 0; j--) {
+ var unit = units[j];
+ if (!unit.alive) {
+ continue;
+ }
+ if (unit.intersects(enemy)) {
+ // Combat outcome depends on unit state
+ if (unit.state === "attack") {
+ // Unit is in attack mode, more likely to win
+ enemy.kill();
+ enemies.splice(i, 1);
+ LK.setScore(LK.getScore() + 100);
+ break;
+ } else if (unit.state === "stealth") {
+ // Stealth units can sometimes evade
+ if (Math.random() > 0.7) {
+ // Unit escapes
+ unit.x += Math.random() * 100 - 50;
+ unit.y += Math.random() * 100 - 50;
+ } else {
+ unit.kill();
+ units.splice(j, 1);
+ }
+ } else {
+ // Normal combat, 50/50 chance
+ if (Math.random() > 0.5) {
+ enemy.kill();
+ enemies.splice(i, 1);
+ LK.setScore(LK.getScore() + 50);
+ } else {
+ unit.kill();
+ units.splice(j, 1);
+ }
+ break;
+ }
+ }
+ }
+ }
+ // Check for units reaching enemy base
+ for (var k = units.length - 1; k >= 0; k--) {
+ var unit = units[k];
+ if (!unit.alive) {
+ continue;
+ }
+ if (enemyBase && unit.intersects(enemyBase)) {
+ // Unit is attacking enemy base
+ var damage = unit.state === "attack" ? 20 : 10;
+ enemyBase.takeDamage(damage);
+ unit.kill();
+ units.splice(k, 1);
+ LK.setScore(LK.getScore() + 200);
+ }
+ }
+}
+function determineVoiceMode() {
+ var volume = facekit.volume;
+ if (volume < 0.1) {
+ // No sound, keep previous mode
+ return voiceMode;
+ } else if (volume < 0.3) {
+ return "stealth";
+ } else if (volume > 0.7) {
+ return "attack";
+ } else {
+ return "normal";
+ }
+}
+function spawnNewUnits() {
+ // Spawn new units every 10 seconds if we have fewer than 5
+ if (LK.ticks % 600 === 0 && units.length < 5) {
+ createUnit(900 + Math.random() * 250, 2000 + Math.random() * 200);
+ }
+}
+function updateScore() {
+ scoreTxt.setText("Score: " + LK.getScore());
+ // Store best score if current score is higher
+ if (LK.getScore() > storage.bestScore) {
+ storage.bestScore = LK.getScore();
+ }
+}
+// Game down event - place target
+game.down = function (x, y) {
+ if (!gameStarted) {
+ return;
+ }
+ // Don't place target too close to enemy base or on bases
+ var distToEnemyBase = Math.sqrt(Math.pow(x - enemyBase.x, 2) + Math.pow(y - enemyBase.y, 2));
+ var distToPlayerBase = Math.sqrt(Math.pow(x - playerBase.x, 2) + Math.pow(y - playerBase.y, 2));
+ if (distToEnemyBase > 350 && distToPlayerBase > 350) {
+ createTarget(x, y);
+ }
+};
+// Game tick event
+game.update = function () {
+ if (!gameStarted) {
+ return;
+ }
+ // Update voice mode based on audio input
+ voiceMode = determineVoiceMode();
+ // Update voice indicator
+ if (voiceIndicator) {
+ voiceIndicator.update();
+ }
+ // Update all units with current voice mode
+ if (voiceMode !== lastVoiceMode) {
+ for (var i = 0; i < units.length; i++) {
+ if (units[i].alive) {
+ units[i].setState(voiceMode);
+ }
+ }
+ lastVoiceMode = voiceMode;
+ }
+ // Check for collisions
+ checkCollisions();
+ // Spawn enemies
+ spawnEnemies();
+ // Spawn new units if needed
+ spawnNewUnits();
+ // Update score display
+ updateScore();
+};
\ No newline at end of file