User prompt
When I have explosive arrows and poison arrows and other combos not all of them seem to elactually afflict the monsters
User prompt
Make it so you can see the lightning and explosions and extra effects that affect other monsters come out of the arrows ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
Make the letters for tye upgrade cards fit in the space of the card
User prompt
Make it so every time the monsters get better the color of them changes
User prompt
Make it so you can not get the same orbital object or special arrow affect twice and increase the varaity of arrow affects and orbital objects
User prompt
The special arrow affects are not working
User prompt
Make the special arrow effects a separate card from the orbital objects
User prompt
Make the orbital objects an extra upgrade card and do damage to monsters
User prompt
Make it so you can have one of the upgrade cards a shield or swords and other things circling around you ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
Make it so you one of the three cards every round is a special power up like poison arrows explosive arrows etc
User prompt
Move the cards a bit more to the left
User prompt
Center the upgrade cards because I can't see the third one
User prompt
Make it three cards
User prompt
Can you make it so you get 1 random special abilities card every round
User prompt
Make it so the upgrade cards are more centered because I can't see all of the third one ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
I've killed 100 monsters but i am still on waves 1
User prompt
Make the waves shorter
User prompt
Make they waves start short but progressively get longer
User prompt
Make it so the monsters are easier to defeat
Code edit (1 edits merged)
Please save this source code
User prompt
Arcane Archer: Wave Defense
Initial prompt
Create a game where you are an archer and you have to defend against waves of monsters and every round you get to pick one out of a randomly selected 3 abilities from a pool of 100
/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); var storage = LK.import("@upit/storage.v1", { highscore: 0, totalGamesPlayed: 0 }); /**** * Classes ****/ var Arrow = Container.expand(function () { var self = Container.call(this); self.arrowBody = self.attachAsset('arrow', { anchorX: 0, anchorY: 0.5 }); self.arrowHead = self.attachAsset('arrowHead', { anchorX: 0.5, anchorY: 0.5, x: 50 }); self.speed = 15; self.damage = 10; self.pierce = 0; self.pierceCount = 0; self.hitEnemies = []; self.specialType = null; // To store special ability type (poison, explosive, etc.) self.specialData = {}; // For any special ability-specific data self.update = function () { self.x += Math.cos(self.rotation) * self.speed; self.y += Math.sin(self.rotation) * self.speed; // Remove if offscreen if (self.x < -100 || self.x > 2148 || self.y < -100 || self.y > 2832) { self.needsRemoval = true; } }; self.canHit = function (monster) { if (self.hitEnemies.indexOf(monster.id) !== -1) { return false; } return true; }; self.hit = function (monster) { self.hitEnemies.push(monster.id); self.pierceCount++; // Apply special effects if (self.specialType === "poison") { // Apply poison effect to monster if (!monster.poisoned) { monster.poisoned = true; monster.poisonDamage = self.damage * 0.2; // 20% of arrow damage per tick monster.poisonTicks = 5; // Duration in ticks monster.body.tint = 0x00FF00; // Green tint for poisoned monsters } } else if (self.specialType === "explosive") { // Create explosion effect and damage nearby monsters LK.effects.flashObject(self, 0xFF9900, 200); // Find and damage nearby monsters var now = Date.now(); for (var i = 0; i < monsters.length; i++) { var otherMonster = monsters[i]; if (otherMonster.id !== monster.id) { var dx = otherMonster.x - self.x; var dy = otherMonster.y - self.y; var dist = Math.sqrt(dx * dx + dy * dy); if (dist < 150) { // Explosion radius otherMonster.takeDamage(self.damage * 0.5); // 50% damage to nearby monsters } } } } else if (self.specialType === "freeze") { // Slow down monster monster.frozen = true; monster.originalSpeed = monster.speed; monster.speed = monster.speed * 0.5; // 50% slower monster.body.tint = 0x00FFFF; // Cyan tint for frozen monsters // Reset speed after 3 seconds LK.setTimeout(function () { if (monster && monster.frozen) { monster.frozen = false; monster.speed = monster.originalSpeed; monster.body.tint = 0xFFFFFF; // Reset tint } }, 3000); } else if (self.specialType === "fire") { // Apply burning effect to monster if (!monster.burning) { monster.burning = true; monster.burnDamage = self.damage * 0.3; // 30% of arrow damage per tick monster.burnTicks = 3; // Duration in ticks monster.body.tint = 0xFF3300; // Orange-red tint for burning monsters } } else if (self.specialType === "lightning") { // Chain lightning effect to nearby monsters LK.effects.flashObject(self, 0xFFFF00, 200); var chainedMonsters = []; chainedMonsters.push(monster.id); // Chain to up to 3 nearby monsters for (var i = 0; i < monsters.length && chainedMonsters.length < 4; i++) { var otherMonster = monsters[i]; if (chainedMonsters.indexOf(otherMonster.id) === -1) { var dx = otherMonster.x - monster.x; var dy = otherMonster.y - monster.y; var dist = Math.sqrt(dx * dx + dy * dy); if (dist < 200) { otherMonster.takeDamage(self.damage * 0.4); otherMonster.body.tint = 0xFFFF00; // Yellow tint for lightning chainedMonsters.push(otherMonster.id); LK.setTimeout(function () { if (otherMonster && otherMonster.body) { otherMonster.body.tint = 0xFFFFFF; } }, 300); } } } } else if (self.specialType === "vampiric") { // Heal player based on damage done if (player) { var healAmount = self.damage * 0.3; // Heal for 30% of damage dealt player.health = Math.min(player.health + healAmount, player.maxHealth); LK.effects.flashObject(player, 0xFF00FF, 200); // Purple flash for healing } } if (self.pierceCount > self.pierce) { self.needsRemoval = true; } }; return self; }); var Monster = Container.expand(function () { var self = Container.call(this); self.id = Date.now() + Math.floor(Math.random() * 10000); self.body = self.attachAsset('monster', { anchorX: 0.5, anchorY: 0.5 }); self.maxHealth = 20; self.health = self.maxHealth; self.speed = 2; self.damage = 10; self.lastAttackTime = 0; self.attackCooldown = 1000; self.update = function () { if (player && !paused) { var dx = player.x - self.x; var dy = player.y - self.y; var dist = Math.sqrt(dx * dx + dy * dy); if (dist > 10) { self.x += dx / dist * self.speed; self.y += dy / dist * self.speed; } var now = Date.now(); // Attack player if (dist < 100) { if (now - self.lastAttackTime > self.attackCooldown) { self.lastAttackTime = now; if (player.takeDamage(self.damage)) { LK.getSound('death').play(); gameOver(); } } } // Handle poison damage over time if (self.poisoned && self.poisonTicks > 0) { if (!self.lastPoisonTime || now - self.lastPoisonTime > 500) { // Every 0.5 seconds self.lastPoisonTime = now; self.poisonTicks--; self.takeDamage(self.poisonDamage); // Remove poison effect when done if (self.poisonTicks <= 0) { self.poisoned = false; self.body.tint = 0xFFFFFF; // Reset tint } } } // Handle burning damage over time if (self.burning && self.burnTicks > 0) { if (!self.lastBurnTime || now - self.lastBurnTime > 400) { // Every 0.4 seconds self.lastBurnTime = now; self.burnTicks--; self.takeDamage(self.burnDamage); // Remove burn effect when done if (self.burnTicks <= 0) { self.burning = false; self.body.tint = 0xFFFFFF; // Reset tint } } } } }; self.takeDamage = function (amount) { self.health -= amount; // Flash red when hit LK.effects.flashObject(self, 0xFF0000, 200); LK.getSound('hit').play(); if (self.health <= 0) { return true; } return false; }; return self; }); var OrbitalObject = Container.expand(function (type, angle, distance) { var self = Container.call(this); self.type = type; self.angle = angle || 0; self.distance = distance || 120; self.speed = 0.03; self.target = null; self.lastAttackTime = 0; // Set different properties based on type if (type === "shields") { self.damage = 10; self.attackCooldown = 800; // Faster attack rate } else if (type === "swords") { self.damage = 25; // Higher damage self.attackCooldown = 1200; } else if (type === "orbs") { self.damage = 18; self.attackCooldown = 1000; } else if (type === "flame_barrier") { self.damage = 15; self.attackCooldown = 600; // Very fast attack rate for flame barrier } else if (type === "ice_shards") { self.damage = 12; self.attackCooldown = 900; } else if (type === "spirit_guardians") { self.damage = 22; self.attackCooldown = 1100; } else { self.damage = 15; self.attackCooldown = 1000; } // Create the visual based on type if (type === "shields") { self.body = self.attachAsset('upgradeCard', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.2, scaleY: 0.2 }); self.body.tint = 0x3399FF; // Blue shields } else if (type === "swords") { self.body = self.attachAsset('arrow', { anchorX: 0.5, anchorY: 0.5, scaleX: 2, scaleY: 0.4 }); self.body.tint = 0xCCCCCC; // Silver swords } else if (type === "orbs") { self.body = self.attachAsset('powerIcon', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.5, scaleY: 0.5 }); self.body.tint = 0xFFCC00; // Yellow orbs } else if (type === "flame_barrier") { self.body = self.attachAsset('powerIcon', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.6, scaleY: 0.6 }); self.body.tint = 0xFF3300; // Orange-red for flame barrier } else if (type === "ice_shards") { self.body = self.attachAsset('upgradeCard', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.15, scaleY: 0.15 }); self.body.tint = 0x99CCFF; // Light blue for ice shards } else if (type === "spirit_guardians") { self.body = self.attachAsset('arrowHead', { anchorX: 0.5, anchorY: 0.5, scaleX: 3, scaleY: 3 }); self.body.tint = 0xDDDDFF; // Pale blue-white for spirits } self.update = function () { if (!player) return; // Update position around player self.angle += self.speed; self.x = player.x + Math.cos(self.angle) * self.distance; self.y = player.y + Math.sin(self.angle) * self.distance; // Rotate object to face direction of movement if (self.type === "swords" || self.type === "ice_shards") { self.rotation = self.angle + Math.PI / 2; } // Check for collisions with monsters for (var i = monsters.length - 1; i >= 0; i--) { var monster = monsters[i]; if (self.intersects(monster)) { var now = Date.now(); if (now - self.lastAttackTime > self.attackCooldown) { self.lastAttackTime = now; // Different effects based on type if (self.type === "shields") { // Shields push monsters back var dx = monster.x - player.x; var dy = monster.y - player.y; var dist = Math.sqrt(dx * dx + dy * dy); if (dist > 0) { var pushX = dx / dist * 50; var pushY = dy / dist * 50; monster.x += pushX; monster.y += pushY; } LK.effects.flashObject(self, 0x3399FF, 200); monster.takeDamage(5); // Shields do a little damage } else if (self.type === "swords" || self.type === "orbs") { // Swords and orbs deal damage if (monster.takeDamage(self.damage)) { game.removeChild(monster); monsters.splice(i, 1); monstersKilled++; scoreText.setText("Score: " + monstersKilled); } if (self.type === "swords") { LK.effects.flashObject(self, 0xFF0000, 200); } else { // Orbs have electricity effect LK.effects.flashObject(self, 0xFFFF00, 200); } } else if (self.type === "flame_barrier") { // Flame barrier burns enemies if (!monster.burning) { monster.burning = true; monster.burnDamage = self.damage * 0.2; monster.burnTicks = 3; monster.body.tint = 0xFF3300; } if (monster.takeDamage(self.damage)) { game.removeChild(monster); monsters.splice(i, 1); monstersKilled++; scoreText.setText("Score: " + monstersKilled); } LK.effects.flashObject(self, 0xFF3300, 200); } else if (self.type === "ice_shards") { // Ice shards slow enemies monster.frozen = true; monster.originalSpeed = monster.speed; monster.speed = monster.speed * 0.7; monster.body.tint = 0x99CCFF; // Reset after 2 seconds LK.setTimeout(function () { if (monster && monster.frozen) { monster.frozen = false; monster.speed = monster.originalSpeed; monster.body.tint = 0xFFFFFF; } }, 2000); if (monster.takeDamage(self.damage)) { game.removeChild(monster); monsters.splice(i, 1); monstersKilled++; scoreText.setText("Score: " + monstersKilled); } LK.effects.flashObject(self, 0x99CCFF, 200); } else if (self.type === "spirit_guardians") { // Spirit guardians pass through enemies if (monster.takeDamage(self.damage)) { game.removeChild(monster); monsters.splice(i, 1); monstersKilled++; scoreText.setText("Score: " + monstersKilled); } LK.effects.flashObject(self, 0xDDDDFF, 200); // Spirits heal player slightly if (player) { player.health = Math.min(player.health + 1, player.maxHealth); } } } } } }; return self; }); var Player = Container.expand(function () { var self = Container.call(this); self.body = self.attachAsset('player', { anchorX: 0.5, anchorY: 0.5 }); self.maxHealth = 100; self.health = self.maxHealth; self.attackSpeed = 2; self.lastAttackTime = 0; self.movementSpeed = 0; self.abilities = []; self.shoot = function (targetX, targetY) { var now = Date.now(); if (now - self.lastAttackTime < 1000 / self.attackSpeed) { return null; } self.lastAttackTime = now; var arrow = new Arrow(); arrow.x = self.x; arrow.y = self.y; var angle = Math.atan2(targetY - self.y, targetX - self.x); arrow.rotation = angle; LK.getSound('shoot').play(); return arrow; }; self.takeDamage = function (amount) { self.health -= amount; if (self.health <= 0) { self.health = 0; return true; } return false; }; self.addAbility = function (ability) { self.abilities.push(ability); // Apply ability effects if (ability.type === "attackSpeed") { self.attackSpeed += ability.value; } else if (ability.type === "health") { self.maxHealth += ability.value; self.health = Math.min(self.health + ability.value, self.maxHealth); } else if (ability.type === "arrowDamage") { arrowDamage += ability.value; } else if (ability.type === "arrowPierce") { arrowPierce += ability.value; } else if (ability.type === "arrowSpeed") { arrowSpeed += ability.value; } else if (ability.type === "special") { console.log("Added special ability: " + ability.specialType); // Track special abilities if (["poison", "explosive", "freeze", "fire", "lightning", "vampiric"].indexOf(ability.specialType) !== -1) { // Track arrow special abilities acquiredSpecialTypes.push(ability.specialType); } // Create orbital objects for shield, sword, orb, etc. abilities if (["shields", "swords", "orbs", "flame_barrier", "ice_shards", "spirit_guardians"].indexOf(ability.specialType) !== -1) { // Track orbital special abilities acquiredOrbitalTypes.push(ability.specialType); // Create 3 objects for each type, evenly spaced around the player for (var i = 0; i < 3; i++) { var angle = Math.PI * 2 / 3 * i; var orbitalObj = new OrbitalObject(ability.specialType, angle); orbitalObjects.push(orbitalObj); game.addChild(orbitalObj); } } } }; return self; }); var UpgradeCard = Container.expand(function (ability) { var self = Container.call(this); self.ability = ability; self.background = self.attachAsset('upgradeCard', { anchorX: 0.5, anchorY: 0.5 }); self.icon = self.attachAsset('powerIcon', { anchorX: 0.5, anchorY: 0.5, y: -150 }); // Title self.title = new Text2(ability.name, { size: 36, fill: 0x000000 }); self.title.anchor.set(0.5, 0.5); self.title.y = -50; self.addChild(self.title); // Description self.description = new Text2(ability.description, { size: 24, fill: 0x333333, wordWrap: 350 }); self.description.anchor.set(0.5, 0.5); self.description.y = 50; self.addChild(self.description); self.down = function (x, y, obj) { tween(self, { scaleX: 0.95, scaleY: 0.95 }, { duration: 100 }); }; self.up = function (x, y, obj) { tween(self, { scaleX: 1, scaleY: 1 }, { duration: 100, onFinish: function onFinish() { if (player) { player.addAbility(self.ability); hideUpgradeScreen(); startNextWave(); LK.getSound('levelup').play(); } } }); }; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ backgroundColor: 0x222222 }); /**** * Game Code ****/ // Game variables var player; var monsters = []; var arrows = []; var upgradeCards = []; var orbitalObjects = []; var paused = false; var currentWave = 0; var monstersKilled = 0; var lastSpawnTime = 0; var showingUpgrades = false; // Track acquired special abilities to prevent duplicates var acquiredSpecialTypes = []; var acquiredOrbitalTypes = []; // Arrow properties var arrowDamage = 20; var arrowPierce = 1; var arrowSpeed = 18; // Abilities pool var abilitiesPool = [{ name: "Quick Shot", description: "Increase attack speed by 15%", type: "attackSpeed", value: 0.15 }, { name: "Heavy Arrow", description: "Increase arrow damage by 5", type: "arrowDamage", value: 5 }, { name: "Fortify", description: "Increase max health by 20", type: "health", value: 20 }, { name: "Piercing Shot", description: "Arrows pierce through one additional enemy", type: "arrowPierce", value: 1 }, { name: "Swift Arrow", description: "Increase arrow speed by 2", type: "arrowSpeed", value: 2 }]; // Special power-up abilities var specialAbilitiesPool = [{ name: "Poison Arrows", description: "Arrows poison enemies, dealing damage over time", type: "special", specialType: "poison" }, { name: "Explosive Arrows", description: "Arrows explode on impact, damaging nearby enemies", type: "special", specialType: "explosive" }, { name: "Freezing Arrows", description: "Arrows slow down enemies for a short time", type: "special", specialType: "freeze" }, { name: "Fire Arrows", description: "Arrows burn enemies with intense flames", type: "special", specialType: "fire" }, { name: "Lightning Arrows", description: "Arrows chain lightning between nearby enemies", type: "special", specialType: "lightning" }, { name: "Vampiric Arrows", description: "Arrows steal health from enemies and heal you", type: "special", specialType: "vampiric" }, { name: "Orbiting Shields", description: "Three shields circle around you, blocking projectiles", type: "special", specialType: "shields" }, { name: "Rotating Swords", description: "Spinning swords that damage nearby enemies", type: "special", specialType: "swords" }, { name: "Energy Orbs", description: "Magical orbs circle you, zapping nearby enemies", type: "special", specialType: "orbs" }, { name: "Flame Barrier", description: "A ring of fire surrounds you, burning enemies", type: "special", specialType: "flame_barrier" }, { name: "Ice Shards", description: "Ice crystals orbit you, slowing nearby enemies", type: "special", specialType: "ice_shards" }, { name: "Spirit Guardians", description: "Ethereal spirits orbit and protect you", type: "special", specialType: "spirit_guardians" }]; // UI elements var waveText = new Text2("Wave: 1", { size: 60, fill: 0xFFFFFF }); waveText.anchor.set(0.5, 0); LK.gui.top.addChild(waveText); var scoreText = new Text2("Score: 0", { size: 60, fill: 0xFFFFFF }); scoreText.anchor.set(0, 0); scoreText.x = 150; scoreText.y = 10; LK.gui.topLeft.addChild(scoreText); var healthBarBg = LK.getAsset('healthBarBg', { anchorX: 0.5, anchorY: 0.5 }); var healthBar = LK.getAsset('healthBar', { anchorX: 0, anchorY: 0.5 }); healthBarBg.x = 2048 / 2; healthBarBg.y = 50; healthBar.x = healthBarBg.x - 100; healthBar.y = healthBarBg.y; LK.gui.addChild(healthBarBg); LK.gui.addChild(healthBar); var upgradeContainer = new Container(); upgradeContainer.visible = false; LK.gui.addChild(upgradeContainer); var upgradeTitle = new Text2("Choose One: Arrow Effect, Orbital, or Stat Upgrade", { size: 80, fill: 0xFFFFFF }); upgradeTitle.anchor.set(0.5, 0.5); upgradeTitle.x = 2048 / 2; upgradeTitle.y = 200; upgradeContainer.addChild(upgradeTitle); function initGame() { currentWave = 0; monstersKilled = 0; paused = false; showingUpgrades = false; monsters = []; arrows = []; // Reset acquired special abilities acquiredSpecialTypes = []; acquiredOrbitalTypes = []; // Clean up any existing orbital objects for (var i = 0; i < orbitalObjects.length; i++) { if (orbitalObjects[i].parent) { orbitalObjects[i].parent.removeChild(orbitalObjects[i]); } } orbitalObjects = []; // Initialize player player = new Player(); player.x = 2048 / 2; player.y = 2732 / 2; game.addChild(player); // Reset arrow properties to stronger defaults arrowDamage = 20; arrowPierce = 1; arrowSpeed = 18; // Update UI waveText.setText("Wave: 1"); scoreText.setText("Score: 0"); // Start first wave startNextWave(); // Play music LK.playMusic('gameMusic'); } function startNextWave() { currentWave++; waveText.setText("Wave: " + currentWave); lastSpawnTime = Date.now(); } function spawnMonster() { var monster = new Monster(); // Scale difficulty with wave, but with reduced health to make monsters easier to defeat monster.maxHealth = 10 + currentWave * 3; monster.health = monster.maxHealth; monster.speed = 1.5 + currentWave * 0.05; monster.damage = 5 + currentWave; // Change monster color based on wave difficulty if (currentWave <= 5) { monster.body.tint = 0xff3333; // Default red for early waves } else if (currentWave <= 10) { monster.body.tint = 0xff9900; // Orange for medium waves } else if (currentWave <= 15) { monster.body.tint = 0xffcc00; // Yellow-orange for harder waves } else if (currentWave <= 20) { monster.body.tint = 0x9900ff; // Purple for very hard waves } else { monster.body.tint = 0x000000; // Black for super difficult waves // Add a white outline effect with a flash LK.effects.flashObject(monster, 0xffffff, 300); } // Spawn from random edge of screen var side = Math.floor(Math.random() * 4); switch (side) { case 0: // Top monster.x = Math.random() * 2048; monster.y = -100; break; case 1: // Right monster.x = 2148; monster.y = Math.random() * 2732; break; case 2: // Bottom monster.x = Math.random() * 2048; monster.y = 2832; break; case 3: // Left monster.x = -100; monster.y = Math.random() * 2732; break; } monsters.push(monster); game.addChild(monster); return monster; } function showUpgradeScreen() { paused = true; showingUpgrades = true; upgradeContainer.visible = true; // Clear previous upgrade cards for (var i = 0; i < upgradeCards.length; i++) { upgradeCards[i].parent.removeChild(upgradeCards[i]); } upgradeCards = []; // Prepare for card selection var cardOptions = []; // Filter out already acquired special abilities var arrowSpecials = []; var orbitalSpecials = []; var nonOrbitalSpecials = []; for (var i = 0; i < specialAbilitiesPool.length; i++) { var ability = specialAbilitiesPool[i]; // Check for orbital types if (["shields", "swords", "orbs", "flame_barrier", "ice_shards", "spirit_guardians"].indexOf(ability.specialType) !== -1) { // Only add if we don't have this orbital type already if (acquiredOrbitalTypes.indexOf(ability.specialType) === -1) { orbitalSpecials.push(ability); } // Check for arrow special types } else if (["poison", "explosive", "freeze", "fire", "lightning", "vampiric"].indexOf(ability.specialType) !== -1) { // Only add if we don't have this arrow special already if (acquiredSpecialTypes.indexOf(ability.specialType) === -1) { arrowSpecials.push(ability); } } else { nonOrbitalSpecials.push(ability); } } // Always include one arrow special if available (separate card) if (arrowSpecials.length > 0) { var arrowSpecialIndex = Math.floor(Math.random() * arrowSpecials.length); var arrowSpecialAbility = arrowSpecials[arrowSpecialIndex]; cardOptions.push(arrowSpecialAbility); } // Always include one orbital special if available (separate card) if (orbitalSpecials.length > 0) { var orbitalIndex = Math.floor(Math.random() * orbitalSpecials.length); var orbitalAbility = orbitalSpecials[orbitalIndex]; cardOptions.push(orbitalAbility); } // Include one non-orbital special if available if (nonOrbitalSpecials.length > 0 && cardOptions.length < 2) { var nonOrbitalIndex = Math.floor(Math.random() * nonOrbitalSpecials.length); var nonOrbitalAbility = nonOrbitalSpecials[nonOrbitalIndex]; cardOptions.push(nonOrbitalAbility); } // Pick regular abilities for the remaining slots var availableAbilities = [].concat(abilitiesPool); while (cardOptions.length < 3 && availableAbilities.length > 0) { var index = Math.floor(Math.random() * availableAbilities.length); var ability = availableAbilities.splice(index, 1)[0]; cardOptions.push(ability); } // Show cards var cardCount = cardOptions.length; var cardWidth = 400; // Width of each card var spacing = 20; // Reduced spacing between cards var cardScale = 0.8; // Smaller card scale to ensure all three fit var totalWidth = cardWidth * cardScale * cardCount + spacing * (cardCount - 1); var startX = (2048 - totalWidth) / 2 + cardWidth * cardScale / 2; for (var i = 0; i < cardCount; i++) { var ability = cardOptions[i]; var card = new UpgradeCard(ability); // Set special icon colors for special abilities if (ability.type === "special") { if (ability.specialType === "poison") { card.icon.tint = 0x00FF00; // Green for poison } else if (ability.specialType === "explosive") { card.icon.tint = 0xFF9900; // Orange for explosive } else if (ability.specialType === "freeze") { card.icon.tint = 0x00FFFF; // Cyan for freeze } else if (ability.specialType === "fire") { card.icon.tint = 0xFF3300; // Orange-red for fire } else if (ability.specialType === "lightning") { card.icon.tint = 0xFFFF00; // Yellow for lightning } else if (ability.specialType === "vampiric") { card.icon.tint = 0xFF00FF; // Purple for vampiric } else if (ability.specialType === "shields") { card.icon.tint = 0x3399FF; // Blue for shields } else if (ability.specialType === "swords") { card.icon.tint = 0xCCCCCC; // Silver for swords } else if (ability.specialType === "orbs") { card.icon.tint = 0xFFFF00; // Yellow for orbs } else if (ability.specialType === "flame_barrier") { card.icon.tint = 0xFF3300; // Orange-red for flame barrier } else if (ability.specialType === "ice_shards") { card.icon.tint = 0x99CCFF; // Light blue for ice shards } else if (ability.specialType === "spirit_guardians") { card.icon.tint = 0xDDDDFF; // Pale blue-white for spirits } } // Position cards in a row - moved more to the left card.x = startX + i * (cardWidth * cardScale + spacing) - 200; // Move 200px to the left card.y = 2732 / 2; card.scale.set(cardScale, cardScale); // Smaller scale to fit all three cards upgradeCards.push(card); upgradeContainer.addChild(card); } } function hideUpgradeScreen() { paused = false; showingUpgrades = false; upgradeContainer.visible = false; } function updateHealthBar() { if (player) { var healthPercent = player.health / player.maxHealth; healthBar.width = 200 * healthPercent; } } function gameOver() { // Update high score in storage if (monstersKilled > storage.highscore) { storage.highscore = monstersKilled; } storage.totalGamesPlayed = (storage.totalGamesPlayed || 0) + 1; LK.showGameOver(); } function handleClick(x, y, obj) { if (paused || !player) return; var arrow = player.shoot(x, y); if (arrow) { arrow.damage = arrowDamage; arrow.pierce = arrowPierce; arrow.speed = arrowSpeed; // Apply special abilities to arrow var appliedSpecial = false; for (var i = 0; i < player.abilities.length; i++) { var ability = player.abilities[i]; if (ability.type === "special" && !appliedSpecial) { // Check if it's an arrow-type special ability (not orbital) if (["poison", "explosive", "freeze", "fire", "lightning", "vampiric"].indexOf(ability.specialType) !== -1) { arrow.specialType = ability.specialType; appliedSpecial = true; // Visual indicators for special arrows if (ability.specialType === "poison") { arrow.arrowBody.tint = 0x00FF00; // Green for poison arrow.arrowHead.tint = 0x00FF00; } else if (ability.specialType === "explosive") { arrow.arrowBody.tint = 0xFF9900; // Orange for explosive arrow.arrowHead.tint = 0xFF9900; } else if (ability.specialType === "freeze") { arrow.arrowBody.tint = 0x00FFFF; // Cyan for freeze arrow.arrowHead.tint = 0x00FFFF; } else if (ability.specialType === "fire") { arrow.arrowBody.tint = 0xFF3300; // Orange-red for fire arrow.arrowHead.tint = 0xFF3300; } else if (ability.specialType === "lightning") { arrow.arrowBody.tint = 0xFFFF00; // Yellow for lightning arrow.arrowHead.tint = 0xFFFF00; } else if (ability.specialType === "vampiric") { arrow.arrowBody.tint = 0xFF00FF; // Purple for vampiric arrow.arrowHead.tint = 0xFF00FF; } } } } arrows.push(arrow); game.addChild(arrow); } } game.down = handleClick; game.update = function () { if (paused) return; // Spawn monsters var now = Date.now(); var spawnInterval = Math.max(2000 - currentWave * 100, 500); var monstersPerWave = 2 + Math.floor(currentWave * 0.8); // Reduced monster count for shorter waves if (now - lastSpawnTime > spawnInterval && monsters.length < monstersPerWave) { spawnMonster(); } // Check if wave is complete - based on monsters killed rather than time if (monstersKilled >= currentWave * 10 || monsters.length === 0 && now - lastSpawnTime > spawnInterval * 2) { if (!showingUpgrades) { showUpgradeScreen(); } } // Update arrows for (var i = arrows.length - 1; i >= 0; i--) { if (arrows[i].needsRemoval) { game.removeChild(arrows[i]); arrows.splice(i, 1); continue; } } // Check for collisions for (var i = arrows.length - 1; i >= 0; i--) { var arrow = arrows[i]; for (var j = monsters.length - 1; j >= 0; j--) { var monster = monsters[j]; if (arrow.canHit(monster) && arrow.intersects(monster)) { arrow.hit(monster); if (monster.takeDamage(arrow.damage)) { game.removeChild(monster); monsters.splice(j, 1); monstersKilled++; scoreText.setText("Score: " + monstersKilled); } if (arrow.needsRemoval) { game.removeChild(arrow); arrows.splice(i, 1); break; } } } } // Update orbital objects for (var i = orbitalObjects.length - 1; i >= 0; i--) { orbitalObjects[i].update(); } // Update health bar updateHealthBar(); }; // Start the game initGame();
===================================================================
--- original.js
+++ change.js
@@ -472,18 +472,19 @@
y: -150
});
// Title
self.title = new Text2(ability.name, {
- size: 40,
+ size: 36,
fill: 0x000000
});
self.title.anchor.set(0.5, 0.5);
self.title.y = -50;
self.addChild(self.title);
// Description
self.description = new Text2(ability.description, {
- size: 30,
- fill: 0x333333
+ size: 24,
+ fill: 0x333333,
+ wordWrap: 350
});
self.description.anchor.set(0.5, 0.5);
self.description.y = 50;
self.addChild(self.description);