/****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
/****
* Classes
****/
var Castle = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('castle', {
anchorX: 0.5,
anchorY: 0.5
});
self.maxHealth = 100;
self.health = self.maxHealth;
self.takeDamage = function (damage) {
self.health -= damage;
LK.effects.flashObject(self, 0xFF0000, 300);
if (self.health <= 0) {
LK.showGameOver();
}
};
return self;
});
var Enemy = Container.expand(function (type) {
var self = Container.call(this);
self.type = type;
self.maxHealth = 30;
self.health = self.maxHealth;
self.speed = 1;
self.damage = 10;
self.reward = 5;
self.slowTime = 0;
self.baseSpeed = 1;
var assetName = 'basicEnemy';
if (type === 'fast') {
assetName = 'fastEnemy';
self.speed = 2;
self.baseSpeed = 2;
self.health = 20;
self.maxHealth = 20;
} else if (type === 'heavy') {
assetName = 'heavyEnemy';
self.speed = 0.5;
self.baseSpeed = 0.5;
self.health = 80;
self.maxHealth = 80;
self.damage = 25;
self.reward = 15;
} else if (type === 'boss') {
assetName = 'bossEnemy';
self.speed = 0.75;
self.baseSpeed = 0.75;
self.health = 300;
self.maxHealth = 300;
self.damage = 50;
self.reward = 100;
}
var graphics = self.attachAsset(assetName, {
anchorX: 0.5,
anchorY: 0.5
});
self.destroyed = false;
self.takeDamage = function (damage) {
self.health -= damage;
LK.effects.flashObject(self, 0xFFFFFF, 200);
if (self.health <= 0) {
resources += self.reward;
LK.getSound('death').play();
self.destroyed = true;
self.destroy();
} else {
LK.getSound('hit').play();
}
};
self.slow = function (duration) {
self.slowTime = duration;
self.speed = self.baseSpeed * 0.3;
};
self.update = function () {
if (self.slowTime > 0) {
self.slowTime--;
if (self.slowTime === 0) {
self.speed = self.baseSpeed;
}
}
// Move directly towards castle
var dx = castle.x - self.x;
var dy = castle.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < 50) {
castle.takeDamage(self.damage);
self.destroyed = true;
self.destroy();
} else {
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
}
};
return self;
});
var Lightning = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('lightning', {
anchorX: 0.5,
anchorY: 0.5
});
self.damage = 20;
self.life = 30;
self.update = function () {
self.life--;
if (self.life <= 0) {
if (self.target && !self.target.destroyed) {
self.target.takeDamage(self.damage);
}
self.destroy();
}
};
return self;
});
var Projectile = Container.expand(function (type, target) {
var self = Container.call(this);
self.type = type;
self.target = target;
self.speed = 8;
self.damage = 15;
var assetName = 'arrow';
if (type === 'cannon') {
assetName = 'cannonball';
self.damage = 40;
self.speed = 6;
}
var graphics = self.attachAsset(assetName, {
anchorX: 0.5,
anchorY: 0.5
});
self.update = function () {
if (!self.target || self.target.destroyed) {
self.destroy();
return;
}
var dx = self.target.x - self.x;
var dy = self.target.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < 20) {
self.target.takeDamage(self.damage);
self.destroy();
return;
}
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
};
return self;
});
var Soldier = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('soldier', {
anchorX: 0.5,
anchorY: 0.5
});
self.health = 50;
self.speed = 3;
self.damage = 8;
self.range = 40;
self.lastAttack = 0;
self.attackRate = 60;
self.findTarget = function () {
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance <= self.range) {
return enemy;
}
}
return null;
};
self.attack = function (target) {
if (LK.ticks - self.lastAttack >= self.attackRate) {
self.lastAttack = LK.ticks;
target.takeDamage(self.damage);
}
};
self.update = function () {
var target = self.findTarget();
if (target) {
self.attack(target);
} else if (enemies.length > 0) {
var nearest = enemies[0];
var minDistance = Infinity;
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < minDistance) {
minDistance = distance;
nearest = enemy;
}
}
if (nearest) {
var dx = nearest.x - self.x;
var dy = nearest.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
}
}
};
return self;
});
var Tower = Container.expand(function (type) {
var self = Container.call(this);
var graphics = self.attachAsset(type + 'Tower', {
anchorX: 0.5,
anchorY: 0.5
});
self.type = type;
self.range = 150;
self.damage = 10;
self.fireRate = 60; // ticks between shots
self.lastShot = 0;
self.cost = 20;
if (type === 'archer') {
self.damage = 15;
self.fireRate = 30;
self.cost = 20;
} else if (type === 'cannon') {
self.damage = 40;
self.fireRate = 90;
self.range = 120;
self.cost = 40;
} else if (type === 'wizard') {
self.damage = 20;
self.fireRate = 45;
self.range = 180;
self.cost = 60;
} else if (type === 'military') {
self.damage = 0;
self.fireRate = 600; // 10 seconds
self.range = 100;
self.cost = 80;
}
self.canShoot = function () {
return LK.ticks - self.lastShot >= self.fireRate;
};
self.findTarget = function () {
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance <= self.range) {
return enemy;
}
}
return null;
};
self.shoot = function (target) {
if (!self.canShoot()) {
return;
}
self.lastShot = LK.ticks;
if (self.type === 'military') {
// Spawn 2 soldiers every 10 seconds
for (var i = 0; i < 2; i++) {
var soldier = new Soldier();
soldier.x = self.x + (i * 40 - 20); // Spread soldiers slightly apart
soldier.y = self.y;
soldiers.push(soldier);
game.addChild(soldier);
}
} else if (self.type === 'wizard') {
target.slow(180); // 3 seconds
var lightning = new Lightning();
lightning.x = target.x;
lightning.y = target.y;
lightning.target = target;
projectiles.push(lightning);
game.addChild(lightning);
} else {
var projectile = new Projectile(self.type, target);
projectile.x = self.x;
projectile.y = self.y;
projectiles.push(projectile);
game.addChild(projectile);
}
LK.getSound('shoot').play();
};
self.update = function () {
var target = self.findTarget();
if (target) {
self.shoot(target);
}
};
return self;
});
var TowerButton = Container.expand(function (type, x, y) {
var self = Container.call(this);
var graphics = self.attachAsset('towerButton', {
anchorX: 0.5,
anchorY: 0.5
});
self.type = type;
self.x = x;
self.y = y;
var towerCosts = {
archer: 20,
cannon: 40,
wizard: 60,
military: 80
};
var label = new Text2(type.charAt(0).toUpperCase() + type.slice(1), {
size: 25,
fill: 0xFFFFFF
});
label.anchor.set(0.5, 0.3);
self.addChild(label);
var costLabel = new Text2(towerCosts[type] + ' coins', {
size: 20,
fill: 0xFFFF00
});
costLabel.anchor.set(0.5, 0.5);
costLabel.y = -50;
self.addChild(costLabel);
self.down = function (x, y, obj) {
selectedTowerType = self.type;
placingTower = true;
};
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x228B22
});
/****
* Game Code
****/
// Sounds
// UI
// Soldiers
// Enemies
// Projectiles
// Castle and towers
// Game variables
// Import tween plugin for animations
var castle;
var towers = [];
var enemies = [];
var soldiers = [];
var projectiles = [];
var resources = 100;
var currentWave = 1;
var maxWaves = 5;
var enemiesSpawned = 0;
var enemiesPerWave = 8;
var waveTimer = 0;
var selectedTowerType = null;
var placingTower = false;
var gameStarted = false;
var startButton;
var planningTime = 15; // 15 seconds for planning
var planningTimer = 0;
var planningActive = false;
var countdownText;
// Path for enemies
var path = [{
x: 100,
y: 100
}, {
x: 400,
y: 100
}, {
x: 400,
y: 400
}, {
x: 800,
y: 400
}, {
x: 800,
y: 800
}, {
x: 1200,
y: 800
}, {
x: 1200,
y: 1200
}, {
x: 1600,
y: 1200
}, {
x: 1600,
y: 1600
}, {
x: 1024,
y: 1600
}];
// Add medieval battlefield background
var background = LK.getAsset('medievalBattlefield', {
anchorX: 0,
anchorY: 0,
x: 0,
y: 0
});
game.addChild(background);
// Create castle
castle = new Castle();
castle.x = 1024;
castle.y = 1600;
game.addChild(castle);
// Create UI
var resourcesText = new Text2('Resources: ' + resources, {
size: 60,
fill: 0xFFFFFF
});
resourcesText.anchor.set(0, 0);
LK.gui.topLeft.addChild(resourcesText);
var waveText = new Text2('Wave: ' + currentWave, {
size: 60,
fill: 0xFFFFFF
});
waveText.anchor.set(1, 0);
LK.gui.topRight.addChild(waveText);
// Create countdown text
countdownText = new Text2('', {
size: 120,
fill: 0xFF0000
});
countdownText.anchor.set(0.5, 0.5);
countdownText.x = 2048 / 2;
countdownText.y = 400;
countdownText.visible = false;
game.addChild(countdownText);
// Create how to play button
var howToPlayButton = new Container();
var howToPlayBg = new Text2('How to Play?', {
size: 40,
fill: 0xFFFFFF
});
howToPlayBg.anchor.set(1, 0);
howToPlayButton.addChild(howToPlayBg);
howToPlayButton.x = -10;
howToPlayButton.y = 80;
LK.gui.topRight.addChild(howToPlayButton);
// Create start button
startButton = new Container();
var startButtonBg = LK.getAsset('start', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 2,
scaleY: 2
});
startButton.addChild(startButtonBg);
startButton.x = 2048 / 2;
startButton.y = 2732 / 2;
game.addChild(startButton);
// Create tower buttons (initially hidden)
var towerButtons = [];
var buttonTypes = ['archer', 'cannon', 'wizard', 'military'];
var towerCosts = [20, 40, 60, 80];
var buttonSpacing = 450;
var totalWidth = (buttonTypes.length - 1) * buttonSpacing;
var startX = (2048 - totalWidth) / 2;
for (var i = 0; i < buttonTypes.length; i++) {
var button = new TowerButton(buttonTypes[i], startX + i * buttonSpacing, 2600);
button.scaleX = 2.5;
button.scaleY = 2.5;
button.visible = false;
towerButtons.push(button);
game.addChild(button);
}
// Helper functions
function spawnEnemy() {
var enemyType = 'basic';
if (currentWave === maxWaves) {
enemyType = 'boss';
} else if (Math.random() < 0.3) {
enemyType = 'fast';
} else if (Math.random() < 0.2) {
enemyType = 'heavy';
}
// For Wave 5 (boss wave), spawn 2 bosses
if (currentWave === maxWaves) {
for (var j = 0; j < 2; j++) {
var enemy = new Enemy(enemyType);
// Spawn only from non-blue areas (exclude top and right edges which are blue/water areas)
var side = Math.floor(Math.random() * 2); // Only 2 sides now (bottom and left)
if (side === 0) {
// Bottom edge (land area)
enemy.x = Math.random() * 2048;
enemy.y = 2732;
} else {
// Left edge (land area)
enemy.x = 0;
enemy.y = Math.random() * 2732;
}
enemies.push(enemy);
game.addChild(enemy);
}
enemiesSpawned += 2; // Increment by 2 for boss wave
} else {
var enemy = new Enemy(enemyType);
// Spawn only from non-blue areas (exclude top and right edges which are blue/water areas)
var side = Math.floor(Math.random() * 2); // Only 2 sides now (bottom and left)
if (side === 0) {
// Bottom edge (land area)
enemy.x = Math.random() * 2048;
enemy.y = 2732;
} else {
// Left edge (land area)
enemy.x = 0;
enemy.y = Math.random() * 2732;
}
enemies.push(enemy);
game.addChild(enemy);
enemiesSpawned++;
}
}
function canPlaceTower(x, y) {
// Check if position is too close to other towers
for (var i = 0; i < towers.length; i++) {
var tower = towers[i];
var dx = tower.x - x;
var dy = tower.y - y;
if (Math.sqrt(dx * dx + dy * dy) < 120) {
return false;
}
}
// Check if position is too close to castle
var dx = castle.x - x;
var dy = castle.y - y;
if (Math.sqrt(dx * dx + dy * dy) < 150) {
return false;
}
return true;
}
function placeTower(x, y) {
if (!selectedTowerType) {
return;
}
var towerCosts = {
archer: 20,
cannon: 40,
wizard: 60,
military: 80
};
if (resources < towerCosts[selectedTowerType]) {
return;
}
if (canPlaceTower(x, y)) {
var tower = new Tower(selectedTowerType);
tower.x = x;
tower.y = y;
towers.push(tower);
game.addChild(tower);
resources -= tower.cost;
resourcesText.setText('Resources: ' + resources);
placingTower = false;
selectedTowerType = null;
}
}
// Start button click handler
startButton.down = function (x, y, obj) {
if (!gameStarted) {
gameStarted = true;
startButton.visible = false;
// Show tower buttons
for (var i = 0; i < towerButtons.length; i++) {
towerButtons[i].visible = true;
}
// Place initial towers
var archerTower = new Tower('archer');
archerTower.x = 800;
archerTower.y = 1200;
towers.push(archerTower);
game.addChild(archerTower);
var cannonTower = new Tower('cannon');
cannonTower.x = 1200;
cannonTower.y = 1000;
towers.push(cannonTower);
game.addChild(cannonTower);
// Start background music
LK.playMusic('ortacagmuzik');
// Start planning phase
planningActive = true;
planningTimer = planningTime * 60; // Convert to ticks (60 FPS)
countdownText.visible = true;
}
};
// How to play button click handler
howToPlayButton.down = function (x, y, obj) {
// Create background panel for instructions
var instructionsPanel = new Container();
var panelBg = LK.getAsset('howToPlayBackground', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 6,
scaleY: 4
});
instructionsPanel.addChild(panelBg);
instructionsPanel.x = 2048 / 2;
instructionsPanel.y = 2732 / 2;
game.addChild(instructionsPanel);
// Show instructions (you can customize this message)
var instructionsText = new Text2('Build towers to stop enemies!\n\nTower types:\n• Archer: Fast fire\n• Cannon: High damage\n• Wizard: Slows enemies\n• Military: Spawns soldiers\n\nProtect the castle!', {
size: 70,
fill: 0x000000,
align: 'center'
});
instructionsText.anchor.set(0.5, 0.5);
instructionsPanel.addChild(instructionsText);
// Remove instructions after 5 seconds
LK.setTimeout(function () {
if (instructionsPanel.parent) {
instructionsPanel.destroy();
}
}, 5000);
};
// Game events
game.down = function (x, y, obj) {
if (placingTower && gameStarted) {
placeTower(x, y);
}
};
// Main game loop
game.update = function () {
// Only run game logic if game has started
if (!gameStarted) {
return;
}
// Handle planning phase countdown
if (planningActive) {
planningTimer--;
var secondsLeft = Math.ceil(planningTimer / 60);
if (secondsLeft > 0) {
countdownText.setText('Planning Time: ' + secondsLeft);
// Add pulsing animation to countdown text
if (planningTimer % 60 === 0) {
// Every second
tween(countdownText, {
scaleX: 1.2,
scaleY: 1.2
}, {
duration: 300,
easing: tween.easeOut,
onFinish: function onFinish() {
tween(countdownText, {
scaleX: 1,
scaleY: 1
}, {
duration: 300,
easing: tween.easeIn
});
}
});
}
} else {
// Planning phase over
planningActive = false;
countdownText.visible = false;
}
}
// Update UI
resourcesText.setText('Resources: ' + resources);
waveText.setText('Wave: ' + currentWave);
// Only spawn enemies if planning phase is over
if (!planningActive) {
// Spawn enemies
if (enemiesSpawned < enemiesPerWave && waveTimer <= 0) {
spawnEnemy();
waveTimer = 60; // 1 second between spawns
}
if (waveTimer > 0) {
waveTimer--;
}
}
// Check wave completion
if (enemiesSpawned >= enemiesPerWave && enemies.length === 0) {
currentWave++;
if (currentWave > maxWaves) {
LK.showYouWin();
} else {
enemiesSpawned = 0;
enemiesPerWave += 2;
waveTimer = 180; // 3 seconds between waves
}
}
// Clean up destroyed objects
for (var i = enemies.length - 1; i >= 0; i--) {
if (enemies[i].destroyed) {
enemies.splice(i, 1);
}
}
for (var i = projectiles.length - 1; i >= 0; i--) {
if (projectiles[i].destroyed) {
projectiles.splice(i, 1);
}
}
for (var i = soldiers.length - 1; i >= 0; i--) {
if (soldiers[i].destroyed) {
soldiers.splice(i, 1);
}
}
}; /****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
/****
* Classes
****/
var Castle = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('castle', {
anchorX: 0.5,
anchorY: 0.5
});
self.maxHealth = 100;
self.health = self.maxHealth;
self.takeDamage = function (damage) {
self.health -= damage;
LK.effects.flashObject(self, 0xFF0000, 300);
if (self.health <= 0) {
LK.showGameOver();
}
};
return self;
});
var Enemy = Container.expand(function (type) {
var self = Container.call(this);
self.type = type;
self.maxHealth = 30;
self.health = self.maxHealth;
self.speed = 1;
self.damage = 10;
self.reward = 5;
self.slowTime = 0;
self.baseSpeed = 1;
var assetName = 'basicEnemy';
if (type === 'fast') {
assetName = 'fastEnemy';
self.speed = 2;
self.baseSpeed = 2;
self.health = 20;
self.maxHealth = 20;
} else if (type === 'heavy') {
assetName = 'heavyEnemy';
self.speed = 0.5;
self.baseSpeed = 0.5;
self.health = 80;
self.maxHealth = 80;
self.damage = 25;
self.reward = 15;
} else if (type === 'boss') {
assetName = 'bossEnemy';
self.speed = 0.75;
self.baseSpeed = 0.75;
self.health = 300;
self.maxHealth = 300;
self.damage = 50;
self.reward = 100;
}
var graphics = self.attachAsset(assetName, {
anchorX: 0.5,
anchorY: 0.5
});
self.destroyed = false;
self.takeDamage = function (damage) {
self.health -= damage;
LK.effects.flashObject(self, 0xFFFFFF, 200);
if (self.health <= 0) {
resources += self.reward;
LK.getSound('death').play();
self.destroyed = true;
self.destroy();
} else {
LK.getSound('hit').play();
}
};
self.slow = function (duration) {
self.slowTime = duration;
self.speed = self.baseSpeed * 0.3;
};
self.update = function () {
if (self.slowTime > 0) {
self.slowTime--;
if (self.slowTime === 0) {
self.speed = self.baseSpeed;
}
}
// Move directly towards castle
var dx = castle.x - self.x;
var dy = castle.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < 50) {
castle.takeDamage(self.damage);
self.destroyed = true;
self.destroy();
} else {
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
}
};
return self;
});
var Lightning = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('lightning', {
anchorX: 0.5,
anchorY: 0.5
});
self.damage = 20;
self.life = 30;
self.update = function () {
self.life--;
if (self.life <= 0) {
if (self.target && !self.target.destroyed) {
self.target.takeDamage(self.damage);
}
self.destroy();
}
};
return self;
});
var Projectile = Container.expand(function (type, target) {
var self = Container.call(this);
self.type = type;
self.target = target;
self.speed = 8;
self.damage = 15;
var assetName = 'arrow';
if (type === 'cannon') {
assetName = 'cannonball';
self.damage = 40;
self.speed = 6;
}
var graphics = self.attachAsset(assetName, {
anchorX: 0.5,
anchorY: 0.5
});
self.update = function () {
if (!self.target || self.target.destroyed) {
self.destroy();
return;
}
var dx = self.target.x - self.x;
var dy = self.target.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < 20) {
self.target.takeDamage(self.damage);
self.destroy();
return;
}
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
};
return self;
});
var Soldier = Container.expand(function () {
var self = Container.call(this);
var graphics = self.attachAsset('soldier', {
anchorX: 0.5,
anchorY: 0.5
});
self.health = 50;
self.speed = 3;
self.damage = 8;
self.range = 40;
self.lastAttack = 0;
self.attackRate = 60;
self.findTarget = function () {
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance <= self.range) {
return enemy;
}
}
return null;
};
self.attack = function (target) {
if (LK.ticks - self.lastAttack >= self.attackRate) {
self.lastAttack = LK.ticks;
target.takeDamage(self.damage);
}
};
self.update = function () {
var target = self.findTarget();
if (target) {
self.attack(target);
} else if (enemies.length > 0) {
var nearest = enemies[0];
var minDistance = Infinity;
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance < minDistance) {
minDistance = distance;
nearest = enemy;
}
}
if (nearest) {
var dx = nearest.x - self.x;
var dy = nearest.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
self.x += dx / distance * self.speed;
self.y += dy / distance * self.speed;
}
}
};
return self;
});
var Tower = Container.expand(function (type) {
var self = Container.call(this);
var graphics = self.attachAsset(type + 'Tower', {
anchorX: 0.5,
anchorY: 0.5
});
self.type = type;
self.range = 150;
self.damage = 10;
self.fireRate = 60; // ticks between shots
self.lastShot = 0;
self.cost = 20;
if (type === 'archer') {
self.damage = 15;
self.fireRate = 30;
self.cost = 20;
} else if (type === 'cannon') {
self.damage = 40;
self.fireRate = 90;
self.range = 120;
self.cost = 40;
} else if (type === 'wizard') {
self.damage = 20;
self.fireRate = 45;
self.range = 180;
self.cost = 60;
} else if (type === 'military') {
self.damage = 0;
self.fireRate = 600; // 10 seconds
self.range = 100;
self.cost = 80;
}
self.canShoot = function () {
return LK.ticks - self.lastShot >= self.fireRate;
};
self.findTarget = function () {
for (var i = 0; i < enemies.length; i++) {
var enemy = enemies[i];
var dx = enemy.x - self.x;
var dy = enemy.y - self.y;
var distance = Math.sqrt(dx * dx + dy * dy);
if (distance <= self.range) {
return enemy;
}
}
return null;
};
self.shoot = function (target) {
if (!self.canShoot()) {
return;
}
self.lastShot = LK.ticks;
if (self.type === 'military') {
// Spawn 2 soldiers every 10 seconds
for (var i = 0; i < 2; i++) {
var soldier = new Soldier();
soldier.x = self.x + (i * 40 - 20); // Spread soldiers slightly apart
soldier.y = self.y;
soldiers.push(soldier);
game.addChild(soldier);
}
} else if (self.type === 'wizard') {
target.slow(180); // 3 seconds
var lightning = new Lightning();
lightning.x = target.x;
lightning.y = target.y;
lightning.target = target;
projectiles.push(lightning);
game.addChild(lightning);
} else {
var projectile = new Projectile(self.type, target);
projectile.x = self.x;
projectile.y = self.y;
projectiles.push(projectile);
game.addChild(projectile);
}
LK.getSound('shoot').play();
};
self.update = function () {
var target = self.findTarget();
if (target) {
self.shoot(target);
}
};
return self;
});
var TowerButton = Container.expand(function (type, x, y) {
var self = Container.call(this);
var graphics = self.attachAsset('towerButton', {
anchorX: 0.5,
anchorY: 0.5
});
self.type = type;
self.x = x;
self.y = y;
var towerCosts = {
archer: 20,
cannon: 40,
wizard: 60,
military: 80
};
var label = new Text2(type.charAt(0).toUpperCase() + type.slice(1), {
size: 25,
fill: 0xFFFFFF
});
label.anchor.set(0.5, 0.3);
self.addChild(label);
var costLabel = new Text2(towerCosts[type] + ' coins', {
size: 20,
fill: 0xFFFF00
});
costLabel.anchor.set(0.5, 0.5);
costLabel.y = -50;
self.addChild(costLabel);
self.down = function (x, y, obj) {
selectedTowerType = self.type;
placingTower = true;
};
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x228B22
});
/****
* Game Code
****/
// Sounds
// UI
// Soldiers
// Enemies
// Projectiles
// Castle and towers
// Game variables
// Import tween plugin for animations
var castle;
var towers = [];
var enemies = [];
var soldiers = [];
var projectiles = [];
var resources = 100;
var currentWave = 1;
var maxWaves = 5;
var enemiesSpawned = 0;
var enemiesPerWave = 8;
var waveTimer = 0;
var selectedTowerType = null;
var placingTower = false;
var gameStarted = false;
var startButton;
var planningTime = 15; // 15 seconds for planning
var planningTimer = 0;
var planningActive = false;
var countdownText;
// Path for enemies
var path = [{
x: 100,
y: 100
}, {
x: 400,
y: 100
}, {
x: 400,
y: 400
}, {
x: 800,
y: 400
}, {
x: 800,
y: 800
}, {
x: 1200,
y: 800
}, {
x: 1200,
y: 1200
}, {
x: 1600,
y: 1200
}, {
x: 1600,
y: 1600
}, {
x: 1024,
y: 1600
}];
// Add medieval battlefield background
var background = LK.getAsset('medievalBattlefield', {
anchorX: 0,
anchorY: 0,
x: 0,
y: 0
});
game.addChild(background);
// Create castle
castle = new Castle();
castle.x = 1024;
castle.y = 1600;
game.addChild(castle);
// Create UI
var resourcesText = new Text2('Resources: ' + resources, {
size: 60,
fill: 0xFFFFFF
});
resourcesText.anchor.set(0, 0);
LK.gui.topLeft.addChild(resourcesText);
var waveText = new Text2('Wave: ' + currentWave, {
size: 60,
fill: 0xFFFFFF
});
waveText.anchor.set(1, 0);
LK.gui.topRight.addChild(waveText);
// Create countdown text
countdownText = new Text2('', {
size: 120,
fill: 0xFF0000
});
countdownText.anchor.set(0.5, 0.5);
countdownText.x = 2048 / 2;
countdownText.y = 400;
countdownText.visible = false;
game.addChild(countdownText);
// Create how to play button
var howToPlayButton = new Container();
var howToPlayBg = new Text2('How to Play?', {
size: 40,
fill: 0xFFFFFF
});
howToPlayBg.anchor.set(1, 0);
howToPlayButton.addChild(howToPlayBg);
howToPlayButton.x = -10;
howToPlayButton.y = 80;
LK.gui.topRight.addChild(howToPlayButton);
// Create start button
startButton = new Container();
var startButtonBg = LK.getAsset('start', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 2,
scaleY: 2
});
startButton.addChild(startButtonBg);
startButton.x = 2048 / 2;
startButton.y = 2732 / 2;
game.addChild(startButton);
// Create tower buttons (initially hidden)
var towerButtons = [];
var buttonTypes = ['archer', 'cannon', 'wizard', 'military'];
var towerCosts = [20, 40, 60, 80];
var buttonSpacing = 450;
var totalWidth = (buttonTypes.length - 1) * buttonSpacing;
var startX = (2048 - totalWidth) / 2;
for (var i = 0; i < buttonTypes.length; i++) {
var button = new TowerButton(buttonTypes[i], startX + i * buttonSpacing, 2600);
button.scaleX = 2.5;
button.scaleY = 2.5;
button.visible = false;
towerButtons.push(button);
game.addChild(button);
}
// Helper functions
function spawnEnemy() {
var enemyType = 'basic';
if (currentWave === maxWaves) {
enemyType = 'boss';
} else if (Math.random() < 0.3) {
enemyType = 'fast';
} else if (Math.random() < 0.2) {
enemyType = 'heavy';
}
// For Wave 5 (boss wave), spawn 2 bosses
if (currentWave === maxWaves) {
for (var j = 0; j < 2; j++) {
var enemy = new Enemy(enemyType);
// Spawn only from non-blue areas (exclude top and right edges which are blue/water areas)
var side = Math.floor(Math.random() * 2); // Only 2 sides now (bottom and left)
if (side === 0) {
// Bottom edge (land area)
enemy.x = Math.random() * 2048;
enemy.y = 2732;
} else {
// Left edge (land area)
enemy.x = 0;
enemy.y = Math.random() * 2732;
}
enemies.push(enemy);
game.addChild(enemy);
}
enemiesSpawned += 2; // Increment by 2 for boss wave
} else {
var enemy = new Enemy(enemyType);
// Spawn only from non-blue areas (exclude top and right edges which are blue/water areas)
var side = Math.floor(Math.random() * 2); // Only 2 sides now (bottom and left)
if (side === 0) {
// Bottom edge (land area)
enemy.x = Math.random() * 2048;
enemy.y = 2732;
} else {
// Left edge (land area)
enemy.x = 0;
enemy.y = Math.random() * 2732;
}
enemies.push(enemy);
game.addChild(enemy);
enemiesSpawned++;
}
}
function canPlaceTower(x, y) {
// Check if position is too close to other towers
for (var i = 0; i < towers.length; i++) {
var tower = towers[i];
var dx = tower.x - x;
var dy = tower.y - y;
if (Math.sqrt(dx * dx + dy * dy) < 120) {
return false;
}
}
// Check if position is too close to castle
var dx = castle.x - x;
var dy = castle.y - y;
if (Math.sqrt(dx * dx + dy * dy) < 150) {
return false;
}
return true;
}
function placeTower(x, y) {
if (!selectedTowerType) {
return;
}
var towerCosts = {
archer: 20,
cannon: 40,
wizard: 60,
military: 80
};
if (resources < towerCosts[selectedTowerType]) {
return;
}
if (canPlaceTower(x, y)) {
var tower = new Tower(selectedTowerType);
tower.x = x;
tower.y = y;
towers.push(tower);
game.addChild(tower);
resources -= tower.cost;
resourcesText.setText('Resources: ' + resources);
placingTower = false;
selectedTowerType = null;
}
}
// Start button click handler
startButton.down = function (x, y, obj) {
if (!gameStarted) {
gameStarted = true;
startButton.visible = false;
// Show tower buttons
for (var i = 0; i < towerButtons.length; i++) {
towerButtons[i].visible = true;
}
// Place initial towers
var archerTower = new Tower('archer');
archerTower.x = 800;
archerTower.y = 1200;
towers.push(archerTower);
game.addChild(archerTower);
var cannonTower = new Tower('cannon');
cannonTower.x = 1200;
cannonTower.y = 1000;
towers.push(cannonTower);
game.addChild(cannonTower);
// Start background music
LK.playMusic('ortacagmuzik');
// Start planning phase
planningActive = true;
planningTimer = planningTime * 60; // Convert to ticks (60 FPS)
countdownText.visible = true;
}
};
// How to play button click handler
howToPlayButton.down = function (x, y, obj) {
// Create background panel for instructions
var instructionsPanel = new Container();
var panelBg = LK.getAsset('howToPlayBackground', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 6,
scaleY: 4
});
instructionsPanel.addChild(panelBg);
instructionsPanel.x = 2048 / 2;
instructionsPanel.y = 2732 / 2;
game.addChild(instructionsPanel);
// Show instructions (you can customize this message)
var instructionsText = new Text2('Build towers to stop enemies!\n\nTower types:\n• Archer: Fast fire\n• Cannon: High damage\n• Wizard: Slows enemies\n• Military: Spawns soldiers\n\nProtect the castle!', {
size: 70,
fill: 0x000000,
align: 'center'
});
instructionsText.anchor.set(0.5, 0.5);
instructionsPanel.addChild(instructionsText);
// Remove instructions after 5 seconds
LK.setTimeout(function () {
if (instructionsPanel.parent) {
instructionsPanel.destroy();
}
}, 5000);
};
// Game events
game.down = function (x, y, obj) {
if (placingTower && gameStarted) {
placeTower(x, y);
}
};
// Main game loop
game.update = function () {
// Only run game logic if game has started
if (!gameStarted) {
return;
}
// Handle planning phase countdown
if (planningActive) {
planningTimer--;
var secondsLeft = Math.ceil(planningTimer / 60);
if (secondsLeft > 0) {
countdownText.setText('Planning Time: ' + secondsLeft);
// Add pulsing animation to countdown text
if (planningTimer % 60 === 0) {
// Every second
tween(countdownText, {
scaleX: 1.2,
scaleY: 1.2
}, {
duration: 300,
easing: tween.easeOut,
onFinish: function onFinish() {
tween(countdownText, {
scaleX: 1,
scaleY: 1
}, {
duration: 300,
easing: tween.easeIn
});
}
});
}
} else {
// Planning phase over
planningActive = false;
countdownText.visible = false;
}
}
// Update UI
resourcesText.setText('Resources: ' + resources);
waveText.setText('Wave: ' + currentWave);
// Only spawn enemies if planning phase is over
if (!planningActive) {
// Spawn enemies
if (enemiesSpawned < enemiesPerWave && waveTimer <= 0) {
spawnEnemy();
waveTimer = 60; // 1 second between spawns
}
if (waveTimer > 0) {
waveTimer--;
}
}
// Check wave completion
if (enemiesSpawned >= enemiesPerWave && enemies.length === 0) {
currentWave++;
if (currentWave > maxWaves) {
LK.showYouWin();
} else {
enemiesSpawned = 0;
enemiesPerWave += 2;
waveTimer = 180; // 3 seconds between waves
}
}
// Clean up destroyed objects
for (var i = enemies.length - 1; i >= 0; i--) {
if (enemies[i].destroyed) {
enemies.splice(i, 1);
}
}
for (var i = projectiles.length - 1; i >= 0; i--) {
if (projectiles[i].destroyed) {
projectiles.splice(i, 1);
}
}
for (var i = soldiers.length - 1; i >= 0; i--) {
if (soldiers[i].destroyed) {
soldiers.splice(i, 1);
}
}
};
pixel art okçu kulesi. In-Game asset. 2d. High contrast. No shadows
topçu kule pixel art. In-Game asset. 2d. High contrast. No shadows
gülle pixel art. In-Game asset. 2d. High contrast. No shadows
pixel art büyücü kulesi. In-Game asset. 2d. High contrast. No shadows
pixel art askari kule. In-Game asset. 2d. High contrast. No shadows
pixel art yıldırım. In-Game asset. 2d. High contrast. No shadows
arrow pixel art. In-Game asset. 2d. High contrast. No shadows
orta çağ pixel art asker. In-Game asset. 2d. High contrast. No shadows
orta çağ kale pixel art. In-Game asset. 2d. High contrast. No shadows
orta çağ düşman pixel art. In-Game asset. 2d. High contrast. No shadows
boss düşman altın zırh pixel art. In-Game asset. 2d. High contrast. No shadows
orta çağ hızlı düşman pixel art. In-Game asset. 2d. High contrast. No shadows
orta çağ ağır düşman pixel art. In-Game asset. 2d. High contrast. No shadows
orta çağ pixel art buton. In-Game asset. 2d. High contrast. No shadows
yazı olmadan
PİXEL ART ÇİMENLİK OVA. In-Game asset. 2d. High contrast. No shadows