/**** 
* Plugins
****/ 
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1");
/**** 
* Classes
****/ 
var Boss = Container.expand(function () {
	var self = Container.call(this);
	var bossGraphics = self.attachAsset('boss', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.maxHealth = 50;
	self.health = self.maxHealth;
	self.phase = 1;
	self.speed = 2;
	self.fireRate = 30;
	self.fireTimer = 60;
	self.movementTimer = 0;
	self.targetX = 2048 / 2;
	self.targetY = 300;
	self.scoreValue = 2000;
	self.active = false;
	self.attackPattern = 0;
	self.movingRight = true;
	self.takeDamage = function (damage) {
		self.health -= damage;
		// Phase changes at 66% and 33% health
		if (self.health <= self.maxHealth * 0.66 && self.phase === 1) {
			self.phase = 2;
			self.fireRate = 20;
			LK.effects.flashObject(self, 0xff0000, 500);
		} else if (self.health <= self.maxHealth * 0.33 && self.phase === 2) {
			self.phase = 3;
			self.fireRate = 15;
			LK.effects.flashObject(self, 0xff0000, 500);
		}
		if (self.health <= 0) {
			return true;
		}
		LK.effects.flashObject(self, 0xff0000, 200);
		return false;
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			if (self.phase === 1) {
				// Single bullet
				var bullet = new EnemyBullet();
				bullet.x = self.x;
				bullet.y = self.y + 100;
				game.addChild(bullet);
				enemyBullets.push(bullet);
			} else if (self.phase === 2) {
				// 3-way shot
				for (var i = -1; i <= 1; i++) {
					var bullet = new EnemyBullet();
					bullet.x = self.x + i * 50;
					bullet.y = self.y + 100;
					game.addChild(bullet);
					enemyBullets.push(bullet);
				}
			} else if (self.phase === 3) {
				// 5-way shot
				for (var i = -2; i <= 2; i++) {
					var bullet = new EnemyBullet();
					bullet.x = self.x + i * 40;
					bullet.y = self.y + 100;
					game.addChild(bullet);
					enemyBullets.push(bullet);
				}
			}
			LK.getSound('enemyShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		if (!self.active) {
			return;
		}
		// Move towards target position
		if (Math.abs(self.x - self.targetX) > 5) {
			self.x += (self.targetX - self.x) * 0.05;
		}
		if (Math.abs(self.y - self.targetY) > 5) {
			self.y += (self.targetY - self.y) * 0.05;
		}
		// Update movement pattern
		self.movementTimer++;
		if (self.movementTimer >= 120) {
			self.movementTimer = 0;
			self.attackPattern = Math.floor(Math.random() * 3);
			if (self.attackPattern === 0) {
				// Move side to side
				self.targetX = self.movingRight ? 1600 : 400;
				self.movingRight = !self.movingRight;
			} else if (self.attackPattern === 1) {
				// Move to center
				self.targetX = 2048 / 2;
			} else if (self.attackPattern === 2) {
				// Move to random position
				self.targetX = 400 + Math.random() * 1200;
			}
		}
		// Fire if ready
		self.fireTimer--;
		if (self.fireTimer <= 0) {
			self.fire();
		}
	};
	self.activate = function () {
		self.active = true;
		tween(self, {
			alpha: 1
		}, {
			duration: 1000
		});
	};
	return self;
});
var Enemy = Container.expand(function () {
	var self = Container.call(this);
	var enemyGraphics = self.attachAsset('enemy', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.health = 2;
	self.speed = 3;
	self.fireRate = 120;
	self.fireTimer = Math.floor(Math.random() * 60);
	self.scoreValue = 100;
	self.movementPattern = "straight";
	self.initialX = 0;
	self.movementAmplitude = 150;
	self.movementPhase = Math.random() * Math.PI * 2;
	self.takeDamage = function (damage) {
		self.health -= damage;
		if (self.health <= 0) {
			return true;
		}
		LK.effects.flashObject(self, 0xff0000, 200);
		return false;
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			var bullet = new EnemyBullet();
			bullet.x = self.x;
			bullet.y = self.y + 40;
			game.addChild(bullet);
			enemyBullets.push(bullet);
			LK.getSound('enemyShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		// Move the enemy based on its pattern
		if (self.movementPattern === "straight") {
			self.y += self.speed;
		} else if (self.movementPattern === "sine") {
			self.y += self.speed;
			self.x = self.initialX + Math.sin(self.movementPhase + self.y * 0.01) * self.movementAmplitude;
		}
		// Fire if ready
		self.fireTimer--;
		if (self.fireTimer <= 0 && self.y > 0 && self.y < 2732) {
			self.fire();
		}
	};
	return self;
});
var EnemyBullet = Container.expand(function () {
	var self = Container.call(this);
	var bulletGraphics = self.attachAsset('enemyBullet', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = 10;
	self.damage = 1;
	self.update = function () {
		self.y += self.speed;
	};
	return self;
});
var Explosion = Container.expand(function () {
	var self = Container.call(this);
	var explosionGraphics = self.attachAsset('explosion', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	// Set initial scale and alpha
	self.scale.set(0.2);
	self.alpha = 1;
	// Start the explosion animation
	self.animate = function () {
		tween(self.scale, {
			x: 1.5,
			y: 1.5
		}, {
			duration: 500,
			easing: tween.easeOut
		});
		tween(self, {
			alpha: 0
		}, {
			duration: 500,
			easing: tween.easeIn,
			onFinish: function onFinish() {
				self.destroy();
			}
		});
	};
	self.animate();
	return self;
});
var Player = Container.expand(function () {
	var self = Container.call(this);
	var playerGraphics = self.attachAsset('player', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.health = 3;
	self.shield = 0;
	self.fireRate = 20;
	self.fireTimer = 0;
	self.speed = 15;
	self.shieldGraphics = null;
	self.updateShield = function () {
		if (self.shield > 0 && !self.shieldGraphics) {
			self.shieldGraphics = self.attachAsset('shield', {
				anchorX: 0.5,
				anchorY: 0.5,
				alpha: 0.5
			});
		} else if (self.shield <= 0 && self.shieldGraphics) {
			self.shieldGraphics.destroy();
			self.shieldGraphics = null;
		}
	};
	self.takeDamage = function (damage) {
		if (self.shield > 0) {
			self.shield--;
			self.updateShield();
			return false;
		} else {
			self.health -= damage;
			if (self.health <= 0) {
				return true;
			}
			LK.effects.flashObject(self, 0xff0000, 300);
			return false;
		}
	};
	self.addShield = function () {
		self.shield = Math.min(self.shield + 1, 3);
		self.updateShield();
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			var bullet = new PlayerBullet();
			bullet.x = self.x;
			bullet.y = self.y - 50;
			game.addChild(bullet);
			playerBullets.push(bullet);
			LK.getSound('playerShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		if (self.fireTimer > 0) {
			self.fireTimer--;
		}
	};
	return self;
});
var PlayerBullet = Container.expand(function () {
	var self = Container.call(this);
	var bulletGraphics = self.attachAsset('playerBullet', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = -15;
	self.damage = 1;
	self.update = function () {
		self.y += self.speed;
	};
	return self;
});
var PowerUp = Container.expand(function () {
	var self = Container.call(this);
	var powerUpGraphics = self.attachAsset('powerUp', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = 5;
	self.type = "shield"; // Default type
	self.update = function () {
		self.y += self.speed;
		// Rotate the power-up
		self.rotation += 0.02;
	};
	return self;
});
/**** 
* Initialize Game
****/ 
var game = new LK.Game({
	backgroundColor: 0x000022
});
/**** 
* Game Code
****/ 
// Game variables
var player;
var boss;
var playerBullets = [];
var enemyBullets = [];
var enemies = [];
var powerUps = [];
var explosions = [];
var gameState = "playing";
var waveNumber = 1;
var enemiesDefeated = 0;
var bossDefeated = false;
var nextEnemySpawn = 60;
var nextPowerUpSpawn = 300;
var dragNode = null;
// Define GUI elements
var scoreTxt = new Text2('0', {
	size: 80,
	fill: 0xFFFFFF
});
var waveTxt = new Text2('WAVE: 1', {
	size: 80,
	fill: 0xFFFFFF
});
var healthTxt = new Text2('HEALTH: 3', {
	size: 80,
	fill: 0xFFFFFF
});
// Position GUI elements
scoreTxt.anchor.set(0.5, 0);
waveTxt.anchor.set(0, 0);
healthTxt.anchor.set(1, 0);
LK.gui.top.addChild(scoreTxt);
LK.gui.topRight.addChild(healthTxt);
LK.gui.topRight.y += 20;
LK.gui.topRight.x -= 20;
waveTxt.x = 160;
waveTxt.y = 20;
LK.gui.addChild(waveTxt);
// Initialize player
player = new Player();
player.x = 2048 / 2;
player.y = 2300;
game.addChild(player);
// Initialize boss (off-screen)
boss = new Boss();
boss.x = 2048 / 2;
boss.y = -500;
boss.alpha = 0;
game.addChild(boss);
// Start background music
LK.playMusic('bgMusic');
// Helper functions
function createExplosion(x, y) {
	var explosion = new Explosion();
	explosion.x = x;
	explosion.y = y;
	game.addChild(explosion);
	explosions.push(explosion);
	LK.getSound('explosion').play();
}
function spawnEnemy() {
	var enemy = new Enemy();
	// Position enemy at top of screen at random position
	enemy.x = 200 + Math.random() * (2048 - 400);
	enemy.y = -100;
	// Set enemy properties based on wave
	enemy.health = 1 + Math.floor(waveNumber / 2);
	enemy.speed = 3 + Math.min(waveNumber * 0.5, 5);
	// Random movement pattern
	if (Math.random() < 0.3) {
		enemy.movementPattern = "sine";
		enemy.initialX = enemy.x;
	}
	game.addChild(enemy);
	enemies.push(enemy);
}
function spawnPowerUp() {
	var powerUp = new PowerUp();
	// Position power-up at top of screen at random position
	powerUp.x = 200 + Math.random() * (2048 - 400);
	powerUp.y = -100;
	game.addChild(powerUp);
	powerUps.push(powerUp);
	// Set next power-up spawn time
	nextPowerUpSpawn = 500 + Math.random() * 500;
}
function startBossFight() {
	// Clear all enemies and bullets
	for (var i = enemies.length - 1; i >= 0; i--) {
		enemies[i].destroy();
		enemies.splice(i, 1);
	}
	for (var i = enemyBullets.length - 1; i >= 0; i--) {
		enemyBullets[i].destroy();
		enemyBullets.splice(i, 1);
	}
	// Prepare the boss
	boss.health = boss.maxHealth + waveNumber * 10;
	boss.y = -300;
	boss.targetY = 300;
	boss.phase = 1;
	boss.active = false;
	// Boss entry animation
	tween(boss, {
		y: -300
	}, {
		duration: 0,
		onFinish: function onFinish() {
			boss.alpha = 1;
			tween(boss, {
				y: 300
			}, {
				duration: 2000,
				easing: tween.elasticOut,
				onFinish: function onFinish() {
					boss.activate();
					LK.getSound('bossAppear').play();
				}
			});
		}
	});
	waveTxt.setText("WAVE " + waveNumber + ": BOSS");
}
function advanceToNextWave() {
	waveNumber++;
	enemiesDefeated = 0;
	bossDefeated = false;
	if (waveNumber % 3 === 0) {
		// Every 3rd wave is a boss wave
		startBossFight();
	} else {
		waveTxt.setText("WAVE: " + waveNumber);
	}
}
// Event handlers
function handleMove(x, y, obj) {
	if (dragNode && gameState === "playing") {
		// Move player, but keep it within screen bounds
		player.x = Math.max(100, Math.min(x, 2048 - 100));
		player.y = Math.max(100, Math.min(y, 2732 - 100));
	}
}
game.move = handleMove;
game.down = function (x, y, obj) {
	if (gameState === "playing") {
		dragNode = player;
		handleMove(x, y, obj);
	}
};
game.up = function (x, y, obj) {
	dragNode = null;
};
// Main game loop
game.update = function () {
	if (gameState !== "playing") {
		return;
	}
	// Update player
	player.update();
	// Auto-fire
	player.fire();
	// Update boss
	boss.update();
	// Check if we need to spawn enemies
	if (waveNumber % 3 !== 0) {
		// Only spawn regular enemies on non-boss waves
		nextEnemySpawn--;
		if (nextEnemySpawn <= 0) {
			spawnEnemy();
			nextEnemySpawn = 60 - Math.min(waveNumber * 5, 40);
		}
	}
	// Check if we need to spawn power-ups
	nextPowerUpSpawn--;
	if (nextPowerUpSpawn <= 0) {
		spawnPowerUp();
	}
	// Update player bullets
	for (var i = playerBullets.length - 1; i >= 0; i--) {
		var bullet = playerBullets[i];
		bullet.update();
		// Check if bullet is off-screen
		if (bullet.y < -50) {
			bullet.destroy();
			playerBullets.splice(i, 1);
			continue;
		}
		// Check collision with enemies
		for (var j = enemies.length - 1; j >= 0; j--) {
			var enemy = enemies[j];
			if (bullet.intersects(enemy)) {
				// Damage enemy
				if (enemy.takeDamage(bullet.damage)) {
					// Enemy destroyed
					createExplosion(enemy.x, enemy.y);
					enemy.destroy();
					enemies.splice(j, 1);
					enemiesDefeated++;
					LK.setScore(LK.getScore() + enemy.scoreValue);
					scoreTxt.setText(LK.getScore());
					// Check if we need to advance to next wave
					if (enemiesDefeated >= 10 + waveNumber * 5) {
						advanceToNextWave();
					}
				}
				// Remove bullet
				bullet.destroy();
				playerBullets.splice(i, 1);
				break;
			}
		}
		// Check collision with boss
		if (bullet && boss.active && bullet.intersects(boss)) {
			// Damage boss
			if (boss.takeDamage(bullet.damage)) {
				// Boss destroyed
				createExplosion(boss.x, boss.y);
				bossDefeated = true;
				boss.active = false;
				boss.alpha = 0;
				LK.setScore(LK.getScore() + boss.scoreValue);
				scoreTxt.setText(LK.getScore());
				// Advance to next wave after a delay
				LK.setTimeout(function () {
					advanceToNextWave();
				}, 2000);
			}
			// Remove bullet
			bullet.destroy();
			playerBullets.splice(i, 1);
		}
	}
	// Update enemy bullets
	for (var i = enemyBullets.length - 1; i >= 0; i--) {
		var bullet = enemyBullets[i];
		bullet.update();
		// Check if bullet is off-screen
		if (bullet.y > 2732 + 50) {
			bullet.destroy();
			enemyBullets.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (bullet.intersects(player)) {
			// Damage player
			if (player.takeDamage(bullet.damage)) {
				// Player destroyed - game over
				createExplosion(player.x, player.y);
				player.alpha = 0;
				gameState = "gameover";
				LK.getSound('gameOver').play();
				LK.setTimeout(function () {
					LK.showGameOver();
				}, 1500);
			}
			// Update health display
			healthTxt.setText("HEALTH: " + player.health);
			// Remove bullet
			bullet.destroy();
			enemyBullets.splice(i, 1);
		}
	}
	// Update enemies
	for (var i = enemies.length - 1; i >= 0; i--) {
		var enemy = enemies[i];
		enemy.update();
		// Check if enemy is off-screen
		if (enemy.y > 2732 + 100) {
			enemy.destroy();
			enemies.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (enemy.intersects(player)) {
			// Damage player
			if (player.takeDamage(1)) {
				// Player destroyed - game over
				createExplosion(player.x, player.y);
				player.alpha = 0;
				gameState = "gameover";
				LK.getSound('gameOver').play();
				LK.setTimeout(function () {
					LK.showGameOver();
				}, 1500);
			}
			// Update health display
			healthTxt.setText("HEALTH: " + player.health);
			// Destroy enemy
			createExplosion(enemy.x, enemy.y);
			enemy.destroy();
			enemies.splice(i, 1);
		}
	}
	// Update power-ups
	for (var i = powerUps.length - 1; i >= 0; i--) {
		var powerUp = powerUps[i];
		powerUp.update();
		// Check if power-up is off-screen
		if (powerUp.y > 2732 + 50) {
			powerUp.destroy();
			powerUps.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (powerUp.intersects(player)) {
			// Apply power-up effect
			player.addShield();
			LK.getSound('powerUp').play();
			// Remove power-up
			powerUp.destroy();
			powerUps.splice(i, 1);
		}
	}
	// Update health display
	healthTxt.setText("HEALTH: " + player.health);
}; /**** 
* Plugins
****/ 
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1");
/**** 
* Classes
****/ 
var Boss = Container.expand(function () {
	var self = Container.call(this);
	var bossGraphics = self.attachAsset('boss', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.maxHealth = 50;
	self.health = self.maxHealth;
	self.phase = 1;
	self.speed = 2;
	self.fireRate = 30;
	self.fireTimer = 60;
	self.movementTimer = 0;
	self.targetX = 2048 / 2;
	self.targetY = 300;
	self.scoreValue = 2000;
	self.active = false;
	self.attackPattern = 0;
	self.movingRight = true;
	self.takeDamage = function (damage) {
		self.health -= damage;
		// Phase changes at 66% and 33% health
		if (self.health <= self.maxHealth * 0.66 && self.phase === 1) {
			self.phase = 2;
			self.fireRate = 20;
			LK.effects.flashObject(self, 0xff0000, 500);
		} else if (self.health <= self.maxHealth * 0.33 && self.phase === 2) {
			self.phase = 3;
			self.fireRate = 15;
			LK.effects.flashObject(self, 0xff0000, 500);
		}
		if (self.health <= 0) {
			return true;
		}
		LK.effects.flashObject(self, 0xff0000, 200);
		return false;
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			if (self.phase === 1) {
				// Single bullet
				var bullet = new EnemyBullet();
				bullet.x = self.x;
				bullet.y = self.y + 100;
				game.addChild(bullet);
				enemyBullets.push(bullet);
			} else if (self.phase === 2) {
				// 3-way shot
				for (var i = -1; i <= 1; i++) {
					var bullet = new EnemyBullet();
					bullet.x = self.x + i * 50;
					bullet.y = self.y + 100;
					game.addChild(bullet);
					enemyBullets.push(bullet);
				}
			} else if (self.phase === 3) {
				// 5-way shot
				for (var i = -2; i <= 2; i++) {
					var bullet = new EnemyBullet();
					bullet.x = self.x + i * 40;
					bullet.y = self.y + 100;
					game.addChild(bullet);
					enemyBullets.push(bullet);
				}
			}
			LK.getSound('enemyShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		if (!self.active) {
			return;
		}
		// Move towards target position
		if (Math.abs(self.x - self.targetX) > 5) {
			self.x += (self.targetX - self.x) * 0.05;
		}
		if (Math.abs(self.y - self.targetY) > 5) {
			self.y += (self.targetY - self.y) * 0.05;
		}
		// Update movement pattern
		self.movementTimer++;
		if (self.movementTimer >= 120) {
			self.movementTimer = 0;
			self.attackPattern = Math.floor(Math.random() * 3);
			if (self.attackPattern === 0) {
				// Move side to side
				self.targetX = self.movingRight ? 1600 : 400;
				self.movingRight = !self.movingRight;
			} else if (self.attackPattern === 1) {
				// Move to center
				self.targetX = 2048 / 2;
			} else if (self.attackPattern === 2) {
				// Move to random position
				self.targetX = 400 + Math.random() * 1200;
			}
		}
		// Fire if ready
		self.fireTimer--;
		if (self.fireTimer <= 0) {
			self.fire();
		}
	};
	self.activate = function () {
		self.active = true;
		tween(self, {
			alpha: 1
		}, {
			duration: 1000
		});
	};
	return self;
});
var Enemy = Container.expand(function () {
	var self = Container.call(this);
	var enemyGraphics = self.attachAsset('enemy', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.health = 2;
	self.speed = 3;
	self.fireRate = 120;
	self.fireTimer = Math.floor(Math.random() * 60);
	self.scoreValue = 100;
	self.movementPattern = "straight";
	self.initialX = 0;
	self.movementAmplitude = 150;
	self.movementPhase = Math.random() * Math.PI * 2;
	self.takeDamage = function (damage) {
		self.health -= damage;
		if (self.health <= 0) {
			return true;
		}
		LK.effects.flashObject(self, 0xff0000, 200);
		return false;
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			var bullet = new EnemyBullet();
			bullet.x = self.x;
			bullet.y = self.y + 40;
			game.addChild(bullet);
			enemyBullets.push(bullet);
			LK.getSound('enemyShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		// Move the enemy based on its pattern
		if (self.movementPattern === "straight") {
			self.y += self.speed;
		} else if (self.movementPattern === "sine") {
			self.y += self.speed;
			self.x = self.initialX + Math.sin(self.movementPhase + self.y * 0.01) * self.movementAmplitude;
		}
		// Fire if ready
		self.fireTimer--;
		if (self.fireTimer <= 0 && self.y > 0 && self.y < 2732) {
			self.fire();
		}
	};
	return self;
});
var EnemyBullet = Container.expand(function () {
	var self = Container.call(this);
	var bulletGraphics = self.attachAsset('enemyBullet', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = 10;
	self.damage = 1;
	self.update = function () {
		self.y += self.speed;
	};
	return self;
});
var Explosion = Container.expand(function () {
	var self = Container.call(this);
	var explosionGraphics = self.attachAsset('explosion', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	// Set initial scale and alpha
	self.scale.set(0.2);
	self.alpha = 1;
	// Start the explosion animation
	self.animate = function () {
		tween(self.scale, {
			x: 1.5,
			y: 1.5
		}, {
			duration: 500,
			easing: tween.easeOut
		});
		tween(self, {
			alpha: 0
		}, {
			duration: 500,
			easing: tween.easeIn,
			onFinish: function onFinish() {
				self.destroy();
			}
		});
	};
	self.animate();
	return self;
});
var Player = Container.expand(function () {
	var self = Container.call(this);
	var playerGraphics = self.attachAsset('player', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.health = 3;
	self.shield = 0;
	self.fireRate = 20;
	self.fireTimer = 0;
	self.speed = 15;
	self.shieldGraphics = null;
	self.updateShield = function () {
		if (self.shield > 0 && !self.shieldGraphics) {
			self.shieldGraphics = self.attachAsset('shield', {
				anchorX: 0.5,
				anchorY: 0.5,
				alpha: 0.5
			});
		} else if (self.shield <= 0 && self.shieldGraphics) {
			self.shieldGraphics.destroy();
			self.shieldGraphics = null;
		}
	};
	self.takeDamage = function (damage) {
		if (self.shield > 0) {
			self.shield--;
			self.updateShield();
			return false;
		} else {
			self.health -= damage;
			if (self.health <= 0) {
				return true;
			}
			LK.effects.flashObject(self, 0xff0000, 300);
			return false;
		}
	};
	self.addShield = function () {
		self.shield = Math.min(self.shield + 1, 3);
		self.updateShield();
	};
	self.fire = function () {
		if (self.fireTimer <= 0) {
			var bullet = new PlayerBullet();
			bullet.x = self.x;
			bullet.y = self.y - 50;
			game.addChild(bullet);
			playerBullets.push(bullet);
			LK.getSound('playerShoot').play();
			self.fireTimer = self.fireRate;
		}
	};
	self.update = function () {
		if (self.fireTimer > 0) {
			self.fireTimer--;
		}
	};
	return self;
});
var PlayerBullet = Container.expand(function () {
	var self = Container.call(this);
	var bulletGraphics = self.attachAsset('playerBullet', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = -15;
	self.damage = 1;
	self.update = function () {
		self.y += self.speed;
	};
	return self;
});
var PowerUp = Container.expand(function () {
	var self = Container.call(this);
	var powerUpGraphics = self.attachAsset('powerUp', {
		anchorX: 0.5,
		anchorY: 0.5
	});
	self.speed = 5;
	self.type = "shield"; // Default type
	self.update = function () {
		self.y += self.speed;
		// Rotate the power-up
		self.rotation += 0.02;
	};
	return self;
});
/**** 
* Initialize Game
****/ 
var game = new LK.Game({
	backgroundColor: 0x000022
});
/**** 
* Game Code
****/ 
// Game variables
var player;
var boss;
var playerBullets = [];
var enemyBullets = [];
var enemies = [];
var powerUps = [];
var explosions = [];
var gameState = "playing";
var waveNumber = 1;
var enemiesDefeated = 0;
var bossDefeated = false;
var nextEnemySpawn = 60;
var nextPowerUpSpawn = 300;
var dragNode = null;
// Define GUI elements
var scoreTxt = new Text2('0', {
	size: 80,
	fill: 0xFFFFFF
});
var waveTxt = new Text2('WAVE: 1', {
	size: 80,
	fill: 0xFFFFFF
});
var healthTxt = new Text2('HEALTH: 3', {
	size: 80,
	fill: 0xFFFFFF
});
// Position GUI elements
scoreTxt.anchor.set(0.5, 0);
waveTxt.anchor.set(0, 0);
healthTxt.anchor.set(1, 0);
LK.gui.top.addChild(scoreTxt);
LK.gui.topRight.addChild(healthTxt);
LK.gui.topRight.y += 20;
LK.gui.topRight.x -= 20;
waveTxt.x = 160;
waveTxt.y = 20;
LK.gui.addChild(waveTxt);
// Initialize player
player = new Player();
player.x = 2048 / 2;
player.y = 2300;
game.addChild(player);
// Initialize boss (off-screen)
boss = new Boss();
boss.x = 2048 / 2;
boss.y = -500;
boss.alpha = 0;
game.addChild(boss);
// Start background music
LK.playMusic('bgMusic');
// Helper functions
function createExplosion(x, y) {
	var explosion = new Explosion();
	explosion.x = x;
	explosion.y = y;
	game.addChild(explosion);
	explosions.push(explosion);
	LK.getSound('explosion').play();
}
function spawnEnemy() {
	var enemy = new Enemy();
	// Position enemy at top of screen at random position
	enemy.x = 200 + Math.random() * (2048 - 400);
	enemy.y = -100;
	// Set enemy properties based on wave
	enemy.health = 1 + Math.floor(waveNumber / 2);
	enemy.speed = 3 + Math.min(waveNumber * 0.5, 5);
	// Random movement pattern
	if (Math.random() < 0.3) {
		enemy.movementPattern = "sine";
		enemy.initialX = enemy.x;
	}
	game.addChild(enemy);
	enemies.push(enemy);
}
function spawnPowerUp() {
	var powerUp = new PowerUp();
	// Position power-up at top of screen at random position
	powerUp.x = 200 + Math.random() * (2048 - 400);
	powerUp.y = -100;
	game.addChild(powerUp);
	powerUps.push(powerUp);
	// Set next power-up spawn time
	nextPowerUpSpawn = 500 + Math.random() * 500;
}
function startBossFight() {
	// Clear all enemies and bullets
	for (var i = enemies.length - 1; i >= 0; i--) {
		enemies[i].destroy();
		enemies.splice(i, 1);
	}
	for (var i = enemyBullets.length - 1; i >= 0; i--) {
		enemyBullets[i].destroy();
		enemyBullets.splice(i, 1);
	}
	// Prepare the boss
	boss.health = boss.maxHealth + waveNumber * 10;
	boss.y = -300;
	boss.targetY = 300;
	boss.phase = 1;
	boss.active = false;
	// Boss entry animation
	tween(boss, {
		y: -300
	}, {
		duration: 0,
		onFinish: function onFinish() {
			boss.alpha = 1;
			tween(boss, {
				y: 300
			}, {
				duration: 2000,
				easing: tween.elasticOut,
				onFinish: function onFinish() {
					boss.activate();
					LK.getSound('bossAppear').play();
				}
			});
		}
	});
	waveTxt.setText("WAVE " + waveNumber + ": BOSS");
}
function advanceToNextWave() {
	waveNumber++;
	enemiesDefeated = 0;
	bossDefeated = false;
	if (waveNumber % 3 === 0) {
		// Every 3rd wave is a boss wave
		startBossFight();
	} else {
		waveTxt.setText("WAVE: " + waveNumber);
	}
}
// Event handlers
function handleMove(x, y, obj) {
	if (dragNode && gameState === "playing") {
		// Move player, but keep it within screen bounds
		player.x = Math.max(100, Math.min(x, 2048 - 100));
		player.y = Math.max(100, Math.min(y, 2732 - 100));
	}
}
game.move = handleMove;
game.down = function (x, y, obj) {
	if (gameState === "playing") {
		dragNode = player;
		handleMove(x, y, obj);
	}
};
game.up = function (x, y, obj) {
	dragNode = null;
};
// Main game loop
game.update = function () {
	if (gameState !== "playing") {
		return;
	}
	// Update player
	player.update();
	// Auto-fire
	player.fire();
	// Update boss
	boss.update();
	// Check if we need to spawn enemies
	if (waveNumber % 3 !== 0) {
		// Only spawn regular enemies on non-boss waves
		nextEnemySpawn--;
		if (nextEnemySpawn <= 0) {
			spawnEnemy();
			nextEnemySpawn = 60 - Math.min(waveNumber * 5, 40);
		}
	}
	// Check if we need to spawn power-ups
	nextPowerUpSpawn--;
	if (nextPowerUpSpawn <= 0) {
		spawnPowerUp();
	}
	// Update player bullets
	for (var i = playerBullets.length - 1; i >= 0; i--) {
		var bullet = playerBullets[i];
		bullet.update();
		// Check if bullet is off-screen
		if (bullet.y < -50) {
			bullet.destroy();
			playerBullets.splice(i, 1);
			continue;
		}
		// Check collision with enemies
		for (var j = enemies.length - 1; j >= 0; j--) {
			var enemy = enemies[j];
			if (bullet.intersects(enemy)) {
				// Damage enemy
				if (enemy.takeDamage(bullet.damage)) {
					// Enemy destroyed
					createExplosion(enemy.x, enemy.y);
					enemy.destroy();
					enemies.splice(j, 1);
					enemiesDefeated++;
					LK.setScore(LK.getScore() + enemy.scoreValue);
					scoreTxt.setText(LK.getScore());
					// Check if we need to advance to next wave
					if (enemiesDefeated >= 10 + waveNumber * 5) {
						advanceToNextWave();
					}
				}
				// Remove bullet
				bullet.destroy();
				playerBullets.splice(i, 1);
				break;
			}
		}
		// Check collision with boss
		if (bullet && boss.active && bullet.intersects(boss)) {
			// Damage boss
			if (boss.takeDamage(bullet.damage)) {
				// Boss destroyed
				createExplosion(boss.x, boss.y);
				bossDefeated = true;
				boss.active = false;
				boss.alpha = 0;
				LK.setScore(LK.getScore() + boss.scoreValue);
				scoreTxt.setText(LK.getScore());
				// Advance to next wave after a delay
				LK.setTimeout(function () {
					advanceToNextWave();
				}, 2000);
			}
			// Remove bullet
			bullet.destroy();
			playerBullets.splice(i, 1);
		}
	}
	// Update enemy bullets
	for (var i = enemyBullets.length - 1; i >= 0; i--) {
		var bullet = enemyBullets[i];
		bullet.update();
		// Check if bullet is off-screen
		if (bullet.y > 2732 + 50) {
			bullet.destroy();
			enemyBullets.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (bullet.intersects(player)) {
			// Damage player
			if (player.takeDamage(bullet.damage)) {
				// Player destroyed - game over
				createExplosion(player.x, player.y);
				player.alpha = 0;
				gameState = "gameover";
				LK.getSound('gameOver').play();
				LK.setTimeout(function () {
					LK.showGameOver();
				}, 1500);
			}
			// Update health display
			healthTxt.setText("HEALTH: " + player.health);
			// Remove bullet
			bullet.destroy();
			enemyBullets.splice(i, 1);
		}
	}
	// Update enemies
	for (var i = enemies.length - 1; i >= 0; i--) {
		var enemy = enemies[i];
		enemy.update();
		// Check if enemy is off-screen
		if (enemy.y > 2732 + 100) {
			enemy.destroy();
			enemies.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (enemy.intersects(player)) {
			// Damage player
			if (player.takeDamage(1)) {
				// Player destroyed - game over
				createExplosion(player.x, player.y);
				player.alpha = 0;
				gameState = "gameover";
				LK.getSound('gameOver').play();
				LK.setTimeout(function () {
					LK.showGameOver();
				}, 1500);
			}
			// Update health display
			healthTxt.setText("HEALTH: " + player.health);
			// Destroy enemy
			createExplosion(enemy.x, enemy.y);
			enemy.destroy();
			enemies.splice(i, 1);
		}
	}
	// Update power-ups
	for (var i = powerUps.length - 1; i >= 0; i--) {
		var powerUp = powerUps[i];
		powerUp.update();
		// Check if power-up is off-screen
		if (powerUp.y > 2732 + 50) {
			powerUp.destroy();
			powerUps.splice(i, 1);
			continue;
		}
		// Check collision with player
		if (powerUp.intersects(player)) {
			// Apply power-up effect
			player.addShield();
			LK.getSound('powerUp').play();
			// Remove power-up
			powerUp.destroy();
			powerUps.splice(i, 1);
		}
	}
	// Update health display
	healthTxt.setText("HEALTH: " + player.health);
};