User prompt
Changes the color of the enemy's health text
User prompt
Changes the color of the enemy health text
User prompt
Make the enemy's life bar longer
User prompt
Changes the color of the player's life text
User prompt
Set the player to 200 health and the healing to 100
User prompt
Make the Spare progress bar use a different asset
User prompt
Make a sound play when the Spare button is pressed
User prompt
Make action buttons appear half a second after the player's turn starts ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
Make the player action buttons a little bigger
User prompt
Make the enemy's damage in phase 3 double
User prompt
Make the purple gradient more transparent and natural
User prompt
Que el degradado morado empieze desde abajo
User prompt
Q Make the purple gradient more transparent
User prompt
Let the bottom part have a purple gradient
User prompt
Make the background have purple particles coming out of the bottom of the screen ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
Make the bullets aligned with the player's movement so that they
User prompt
Make the enemy unable to attack on the player's turn
User prompt
Make attack patterns a little more difficult so that the player can't stay still all the time.
User prompt
Make the movement buttons bigger and farther apart
User prompt
Make phase 2 a little easier and reduce the enemy's health to 5000 and each phase to 33.33% of the health.
User prompt
Make the player have 160 health and the healing heals 80
User prompt
Add 3 phases depending on the life of the enemy or the Spare, each one becoming more difficult, but phase 1 being easy.
User prompt
Reduces the number of bullets that can be held at one time to 50
User prompt
Add attack patterns that force the player to move, also make it so the enemy can only mix 3 patterns
User prompt
That when a projectile is generated it makes a sound and a sound
/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); /**** * Classes ****/ var Player = Container.expand(function () { var self = Container.call(this); self.moveSpeed = 8; self.isMoving = false; self.targetX = 0; self.targetY = 0; var playerGraphics = self.attachAsset('player', { anchorX: 0.5, anchorY: 0.5 }); self.moveTo = function (x, y) { if (x < battleBoxLeft + 30) x = battleBoxLeft + 30; if (x > battleBoxRight - 30) x = battleBoxRight - 30; if (y < battleBoxTop + 30) y = battleBoxTop + 30; if (y > battleBoxBottom - 30) y = battleBoxBottom - 30; self.targetX = x; self.targetY = y; self.isMoving = true; }; self.update = function () { if (self.isMoving) { var dx = self.targetX - self.x; var dy = self.targetY - self.y; var distance = Math.sqrt(dx * dx + dy * dy); if (distance < self.moveSpeed) { self.x = self.targetX; self.y = self.targetY; self.isMoving = false; } else { self.x += dx / distance * self.moveSpeed; self.y += dy / distance * self.moveSpeed; } } }; return self; }); var Projectile = Container.expand(function () { var self = Container.call(this); self.velocityX = 0; self.velocityY = 0; self.isActive = true; var projectileGraphics = self.attachAsset('projectile', { anchorX: 0.5, anchorY: 0.5 }); self.setVelocity = function (vx, vy) { self.velocityX = vx; self.velocityY = vy; }; self.update = function () { if (self.isActive) { self.x += self.velocityX; self.y += self.velocityY; // Remove if out of battle box bounds if (self.x < battleBoxLeft - 50 || self.x > battleBoxRight + 50 || self.y < battleBoxTop - 50 || self.y > battleBoxBottom + 50) { self.isActive = false; } } }; return self; }); var PurpleParticle = Container.expand(function () { var self = Container.call(this); self.isActive = true; self.velocityX = 0; self.velocityY = 0; self.lifeTime = 0; self.maxLifeTime = 300; // 5 seconds at 60fps var particleGraphics = self.attachAsset('purpleParticle', { anchorX: 0.5, anchorY: 0.5 }); self.setVelocity = function (vx, vy) { self.velocityX = vx; self.velocityY = vy; }; self.update = function () { if (self.isActive) { self.x += self.velocityX; self.y += self.velocityY; self.lifeTime++; // Fade out over time var fadeRatio = 1 - self.lifeTime / self.maxLifeTime; particleGraphics.alpha = fadeRatio; // Remove if lifetime exceeded or out of bounds if (self.lifeTime >= self.maxLifeTime || self.y < 0) { self.isActive = false; } } }; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ backgroundColor: 0x111111 }); /**** * Game Code ****/ // Game state variables var gameState = 'attack'; // 'attack' or 'defense' var playerHealth = 200; var maxHealth = 200; var enemyHealth = 5000; var maxEnemyHealth = 5000; var projectiles = []; var defenseTimer = 0; var defenseDuration = 300; // 5 seconds at 60fps var spareCount = 0; var maxSpareCount = 15; var healCount = 0; var maxHealCount = 8; var isInvulnerable = false; var invulnerabilityDuration = 90; // 1.5 seconds at 60fps var playerTP = 0; var maxTP = 100; var narrowDodgeDistance = 80; // Distance threshold for narrow dodge var usedPatterns = []; // Track used patterns var maxPatterns = 3; // Maximum number of patterns to mix var forceMovementPatterns = [0, 1, 2]; // Patterns that force movement // Phase system variables var currentPhase = 1; var maxPhases = 3; var phase1Threshold = 0.66; // 66% health remaining var phase2Threshold = 0.33; // 33% health remaining // Purple particle system variables var purpleParticles = []; var particleSpawnTimer = 0; var maxParticles = 20; // Purple gradient variables var purpleGradientLayers = []; var gradientLayerCount = 8; // Battle box boundaries var battleBoxLeft = 1024 - 400; var battleBoxRight = 1024 + 400; var battleBoxTop = 1366 - 300; var battleBoxBottom = 1366 + 300; // Create battle box var battleBox = game.addChild(LK.getAsset('battleBox', { anchorX: 0.5, anchorY: 0.5 })); battleBox.x = 1024; battleBox.y = 1366; // Create player var player = game.addChild(new Player()); player.x = 1024; player.y = 1366; // Create TP hitbox visual var tpHitbox = game.addChild(LK.getAsset('tpHitbox', { anchorX: 0.5, anchorY: 0.5 })); tpHitbox.x = player.x; tpHitbox.y = player.y; tpHitbox.alpha = 0.3; // Create health bar background var healthBarBg = game.addChild(LK.getAsset('healthBarBg', { anchorX: 0.5, anchorY: 0.5 })); healthBarBg.x = 1024; healthBarBg.y = 1700; // Create health bar var healthBar = game.addChild(LK.getAsset('healthBar', { anchorX: 0.5, anchorY: 0.5 })); healthBar.x = 1024; healthBar.y = 1700; // Create enemy sprite var enemy = game.addChild(LK.getAsset('enemy', { anchorX: 0.5, anchorY: 0.5 })); enemy.x = 1024; enemy.y = 800; // Create attack button var attackButton = game.addChild(LK.getAsset('attackButton', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.3, scaleY: 1.3 })); attackButton.x = 650; attackButton.y = 1800; // Create spare button var spareButton = game.addChild(LK.getAsset('spareButton', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.3, scaleY: 1.3 })); spareButton.x = 1398; spareButton.y = 1800; // Create heal button var healButton = game.addChild(LK.getAsset('healButton', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.3, scaleY: 1.3 })); healButton.x = 1149; healButton.y = 1800; // Create special attack button var specialAttackButton = game.addChild(LK.getAsset('specialAttackButton', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.3, scaleY: 1.3 })); specialAttackButton.x = 899; specialAttackButton.y = 1800; // Create movement buttons var upButton = game.addChild(LK.getAsset('upButton', { anchorX: 0.5, anchorY: 0.5 })); upButton.x = 1024; upButton.y = 1800; var downButton = game.addChild(LK.getAsset('downButton', { anchorX: 0.5, anchorY: 0.5 })); downButton.x = 1024; downButton.y = 2200; var leftButton = game.addChild(LK.getAsset('leftButton', { anchorX: 0.5, anchorY: 0.5 })); leftButton.x = 750; leftButton.y = 2000; var rightButton = game.addChild(LK.getAsset('rightButton', { anchorX: 0.5, anchorY: 0.5 })); rightButton.x = 1298; rightButton.y = 2000; // Create UI text var phaseText = new Text2('ATTACK PHASE', { size: 80, fill: 0xFFFF00 }); phaseText.anchor.set(0.5, 0); phaseText.x = 1024; phaseText.y = 200; game.addChild(phaseText); var healthText = new Text2('HP: 200/200', { size: 50, fill: 0xffffff }); healthText.anchor.set(0.5, 0.5); healthText.x = 1024; healthText.y = 1700; game.addChild(healthText); // Create enemy health bar background var enemyHealthBarBg = game.addChild(LK.getAsset('healthBarBg', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.5 })); enemyHealthBarBg.x = 400; enemyHealthBarBg.y = 1950; // Create enemy health bar var enemyHealthBar = game.addChild(LK.getAsset('Enemybar', { anchorX: 0.5, anchorY: 0.5 })); enemyHealthBar.x = 400; enemyHealthBar.y = 1950; enemyHealthBar.tint = 0xff0000; var enemyHealthText = new Text2('Enemy HP: 5000/5000', { size: 50, fill: 0x0066ff }); enemyHealthText.anchor.set(0.5, 0.5); enemyHealthText.x = 400; enemyHealthText.y = 1950; game.addChild(enemyHealthText); // Create spare bar background var spareBarBg = game.addChild(LK.getAsset('healthBarBg', { anchorX: 0.5, anchorY: 0.5 })); spareBarBg.x = 1648; spareBarBg.y = 1950; // Create spare bar var spareBar = game.addChild(LK.getAsset('spareProgressBar', { anchorX: 0.5, anchorY: 0.5 })); spareBar.x = 1648; spareBar.y = 1950; var spareText = new Text2('Spare Progress: 0/15', { size: 50, fill: 0x00ff66 }); spareText.anchor.set(0.5, 0.5); spareText.x = 1648; spareText.y = 1950; game.addChild(spareText); var healText = new Text2('Heals: 8/8', { size: 50, fill: 0x00ff00 }); healText.anchor.set(0.5, 0); healText.x = 1024; healText.y = 2250; game.addChild(healText); // Create TP bar background var tpBarBg = game.addChild(LK.getAsset('healthBarBg', { anchorX: 0.5, anchorY: 0.5 })); tpBarBg.x = 1024; tpBarBg.y = 400; // Create TP bar var tpBar = game.addChild(LK.getAsset('healthBar', { anchorX: 0.5, anchorY: 0.5 })); tpBar.x = 1024; tpBar.y = 400; tpBar.tint = 0xffff00; var tpText = new Text2('TP: 0/100', { size: 50, fill: 0xffff00 }); tpText.anchor.set(0.5, 0); tpText.x = 1024; tpText.y = 450; game.addChild(tpText); // Button event handlers attackButton.down = function () { if (gameState === 'attack') { var damage = Math.floor(Math.random() * 101) + 100; // Random damage between 100-200 enemyHealth -= damage; // Add 6 TP when attacking playerTP = Math.min(playerTP + 6, maxTP); playerTP = Math.round(playerTP * 10) / 10; updateTPBar(); updateEnemyHealthBar(); LK.getSound('attack').play(); if (enemyHealth <= 0) { LK.showYouWin(); return; } startDefensePhase(); } }; spareButton.down = function () { if (gameState === 'attack') { spareCount++; updateSpareProgress(); LK.getSound('spare').play(); if (spareCount >= maxSpareCount) { LK.showYouWin(); return; } startDefensePhase(); } }; healButton.down = function () { if (gameState === 'attack' && healCount < maxHealCount && playerHealth < maxHealth) { healCount++; playerHealth = Math.min(playerHealth + 100, maxHealth); updateHealthBar(); updateHealCount(); LK.getSound('heal').play(); LK.effects.flashObject(player, 0x00ff00, 300); startDefensePhase(); } }; upButton.down = function () { if (gameState === 'defense') { player.moveTo(player.x, player.y - 60); LK.getSound('dodge').play(); } }; downButton.down = function () { if (gameState === 'defense') { player.moveTo(player.x, player.y + 60); LK.getSound('dodge').play(); } }; leftButton.down = function () { if (gameState === 'defense') { player.moveTo(player.x - 60, player.y); LK.getSound('dodge').play(); } }; rightButton.down = function () { if (gameState === 'defense') { player.moveTo(player.x + 60, player.y); LK.getSound('dodge').play(); } }; specialAttackButton.down = function () { if (gameState === 'attack' && playerTP >= 50) { var damage = Math.floor(Math.random() * 201) + 500; // Random damage between 500-700 enemyHealth -= damage; playerTP -= 50; playerTP = Math.round(playerTP * 10) / 10; updateEnemyHealthBar(); updateTPBar(); LK.getSound('skill').play(); LK.effects.flashObject(enemy, 0xff6600, 500); if (enemyHealth <= 0) { LK.showYouWin(); return; } startDefensePhase(); } }; function startDefensePhase() { gameState = 'defense'; defenseTimer = 0; currentPhase = getCurrentPhase(); // Adjust defense phase based on current phase if (currentPhase === 1) { defenseDuration = 180; // 3 seconds - easy maxPatterns = 2; // Use only 2 patterns phaseText.setText('DEFENSE PHASE - PHASE 1'); } else if (currentPhase === 2) { defenseDuration = 210; // 3.5 seconds - medium (reduced from 240) maxPatterns = 2; // Use only 2 patterns (reduced from 3) phaseText.setText('DEFENSE PHASE - PHASE 2'); } else { defenseDuration = 300; // 5 seconds - hard maxPatterns = 3; // Use all 3 patterns phaseText.setText('DEFENSE PHASE - PHASE 3'); } phaseText.tint = 0xff0000; // Reset used patterns for new defense phase usedPatterns = []; // Hide attack buttons, show movement buttons attackButton.visible = false; spareButton.visible = false; healButton.visible = false; specialAttackButton.visible = false; upButton.visible = true; downButton.visible = true; leftButton.visible = true; rightButton.visible = true; } function startAttackPhase() { gameState = 'attack'; phaseText.setText('ATTACK PHASE'); phaseText.tint = 0xffff00; // Clear all projectiles for (var i = projectiles.length - 1; i >= 0; i--) { projectiles[i].destroy(); projectiles.splice(i, 1); } // Hide movement buttons immediately upButton.visible = false; downButton.visible = false; leftButton.visible = false; rightButton.visible = false; // Hide attack buttons initially attackButton.visible = false; spareButton.visible = false; healButton.visible = false; specialAttackButton.visible = false; // Show attack buttons after half a second delay LK.setTimeout(function () { attackButton.visible = true; spareButton.visible = true; healButton.visible = true; specialAttackButton.visible = true; }, 500); } function spawnProjectile(x, y, vx, vy) { // Limit the number of projectiles to 50 if (projectiles.length >= 50) { return; // Don't spawn new projectile if limit reached } var projectile = new Projectile(); projectile.x = x; projectile.y = y; projectile.setVelocity(vx, vy); projectiles.push(projectile); game.addChild(projectile); LK.getSound('projectile').play(); } function updateProjectilePattern() { // Only spawn projectiles during defense phase if (gameState !== 'defense') { return; } // Adjust spawn frequency based on phase var spawnFrequency; if (currentPhase === 1) { spawnFrequency = 40; // Spawn every 0.67 seconds - easy } else if (currentPhase === 2) { spawnFrequency = 30; // Spawn every 0.5 seconds - medium } else { spawnFrequency = 18; // Spawn every 0.3 seconds - hard } if (defenseTimer % spawnFrequency === 0) { var patternType; // Reset used patterns if we've used all allowed patterns if (usedPatterns.length >= maxPatterns) { usedPatterns = []; } // Select a pattern that forces movement and hasn't been used yet var availablePatterns = []; for (var p = 0; p < forceMovementPatterns.length; p++) { var pattern = forceMovementPatterns[p]; var isUsed = false; for (var u = 0; u < usedPatterns.length; u++) { if (usedPatterns[u] === pattern) { isUsed = true; break; } } if (!isUsed) { availablePatterns.push(pattern); } } // If no available patterns, reset and use any force movement pattern if (availablePatterns.length === 0) { usedPatterns = []; availablePatterns = forceMovementPatterns.slice(); // Copy array } // Select random pattern from available ones patternType = availablePatterns[Math.floor(Math.random() * availablePatterns.length)]; usedPatterns.push(patternType); if (patternType === 0) { // Horizontal sweep - aligned with player's vertical position var projectileCount = currentPhase === 1 ? 5 : currentPhase === 2 ? 7 : 9; var speed = currentPhase === 1 ? 4 : currentPhase === 2 ? 6 : 8; var playerY = player.y; var spreadRange = 200; // How much to spread around player position for (var i = 0; i < projectileCount; i++) { var yOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount); var targetY = Math.max(battleBoxTop + 30, Math.min(battleBoxBottom - 30, playerY + yOffset)); spawnProjectile(battleBoxLeft - 30, targetY, speed, 0); } // Add delayed second wave only in phase 2 and 3 if (currentPhase >= 2) { LK.setTimeout(function () { var currentPlayerY = player.y; for (var i = 0; i < projectileCount; i++) { var yOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount) + 40; var targetY = Math.max(battleBoxTop + 30, Math.min(battleBoxBottom - 30, currentPlayerY + yOffset)); spawnProjectile(battleBoxLeft - 30, targetY, speed, 0); } }, currentPhase === 2 ? 500 : 300); } // Add third wave for phase 3 if (currentPhase === 3) { LK.setTimeout(function () { var currentPlayerY = player.y; for (var i = 0; i < projectileCount; i++) { var yOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount) - 40; var targetY = Math.max(battleBoxTop + 30, Math.min(battleBoxBottom - 30, currentPlayerY + yOffset)); spawnProjectile(battleBoxLeft - 30, targetY, speed, 0); } }, 600); } } else if (patternType === 1) { // Vertical sweep - aligned with player's horizontal position var projectileCount = currentPhase === 1 ? 6 : currentPhase === 2 ? 8 : 10; var speed = currentPhase === 1 ? 4 : currentPhase === 2 ? 5 : 7; var playerX = player.x; var spreadRange = 300; // How much to spread around player position for (var i = 0; i < projectileCount; i++) { var xOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount); var targetX = Math.max(battleBoxLeft + 30, Math.min(battleBoxRight - 30, playerX + xOffset)); spawnProjectile(targetX, battleBoxTop - 30, 0, speed); } // Add delayed second wave only in phase 2 and 3 if (currentPhase >= 2) { LK.setTimeout(function () { var currentPlayerX = player.x; for (var i = 0; i < projectileCount; i++) { var xOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount) + 40; var targetX = Math.max(battleBoxLeft + 30, Math.min(battleBoxRight - 30, currentPlayerX + xOffset)); spawnProjectile(targetX, battleBoxTop - 30, 0, speed); } }, currentPhase === 2 ? 500 : 300); } // Add third wave for phase 3 if (currentPhase === 3) { LK.setTimeout(function () { var currentPlayerX = player.x; for (var i = 0; i < projectileCount; i++) { var xOffset = (i - Math.floor(projectileCount / 2)) * (spreadRange / projectileCount) - 40; var targetX = Math.max(battleBoxLeft + 30, Math.min(battleBoxRight - 30, currentPlayerX + xOffset)); spawnProjectile(targetX, battleBoxTop - 30, 0, speed); } }, 600); } } else if (patternType === 2) { // Closing walls pattern - converges on player position var playerX = player.x; var playerY = player.y; var wallCount = currentPhase === 1 ? 8 : currentPhase === 2 ? 10 : 12; var speed = currentPhase === 1 ? 2 : currentPhase === 2 ? 3 : 4; // Create walls from all sides that converge on player for (var i = 0; i < wallCount; i++) { // Calculate direction vectors towards player var leftY = battleBoxTop + i * (600 / wallCount); var rightY = battleBoxTop + i * (600 / wallCount); var topX = battleBoxLeft + i * (800 / wallCount); var bottomX = battleBoxLeft + i * (800 / wallCount); // Left wall - aim towards player var leftDx = playerX - battleBoxLeft; var leftDy = playerY - leftY; var leftDist = Math.sqrt(leftDx * leftDx + leftDy * leftDy); spawnProjectile(battleBoxLeft - 30, leftY, speed * leftDx / leftDist, speed * leftDy / leftDist); // Right wall - aim towards player var rightDx = playerX - battleBoxRight; var rightDy = playerY - rightY; var rightDist = Math.sqrt(rightDx * rightDx + rightDy * rightDy); spawnProjectile(battleBoxRight + 30, rightY, speed * rightDx / rightDist, speed * rightDy / rightDist); // Top wall - aim towards player var topDx = playerX - topX; var topDy = playerY - battleBoxTop; var topDist = Math.sqrt(topDx * topDx + topDy * topDy); spawnProjectile(topX, battleBoxTop - 30, speed * topDx / topDist, speed * topDy / topDist); // Bottom wall - aim towards player var bottomDx = playerX - bottomX; var bottomDy = playerY - battleBoxBottom; var bottomDist = Math.sqrt(bottomDx * bottomDx + bottomDy * bottomDy); spawnProjectile(bottomX, battleBoxBottom + 30, speed * bottomDx / bottomDist, speed * bottomDy / bottomDist); } // Add diagonal projectiles aimed at player position LK.setTimeout(function () { var currentPlayerX = player.x; var currentPlayerY = player.y; var diagSpeed = speed * 0.7; // Calculate diagonal directions towards player var corners = [{ x: battleBoxLeft - 30, y: battleBoxTop - 30 }, { x: battleBoxRight + 30, y: battleBoxTop - 30 }, { x: battleBoxLeft - 30, y: battleBoxBottom + 30 }, { x: battleBoxRight + 30, y: battleBoxBottom + 30 }]; for (var i = 0; i < corners.length; i++) { var corner = corners[i]; var dx = currentPlayerX - corner.x; var dy = currentPlayerY - corner.y; var dist = Math.sqrt(dx * dx + dy * dy); spawnProjectile(corner.x, corner.y, diagSpeed * dx / dist, diagSpeed * dy / dist); } }, 400); // Add tracking projectiles in phase 3 if (currentPhase === 3) { LK.setTimeout(function () { var currentPlayerX = player.x; var currentPlayerY = player.y; // Create tracking projectiles that aim at player's current position for (var i = 0; i < 4; i++) { var angle = i * Math.PI / 2; var startX = battleBoxLeft + 400 + Math.cos(angle) * 350; var startY = battleBoxTop + 300 + Math.sin(angle) * 250; var dx = currentPlayerX - startX; var dy = currentPlayerY - startY; var dist = Math.sqrt(dx * dx + dy * dy); spawnProjectile(startX, startY, 4 * dx / dist, 4 * dy / dist); } }, 600); } } } } function updateHealthBar() { var healthPercent = playerHealth / maxHealth; healthBar.scaleX = healthPercent; healthBar.x = 1024 - 200 * (1 - healthPercent); healthText.setText('HP: ' + playerHealth + '/' + maxHealth); } function updateEnemyHealthBar() { var enemyHealthPercent = enemyHealth / maxEnemyHealth; enemyHealthBar.scaleX = enemyHealthPercent; enemyHealthBar.x = 400 - 300 * (1 - enemyHealthPercent); enemyHealthText.setText('Enemy HP: ' + enemyHealth + '/' + maxEnemyHealth); } function updateSpareProgress() { var sparePercent = spareCount / maxSpareCount; spareBar.scaleX = sparePercent; spareBar.x = 1648 - 200 * (1 - sparePercent); spareText.setText('Spare Progress: ' + spareCount + '/' + maxSpareCount); } function updateHealCount() { var remaining = maxHealCount - healCount; healText.setText('Heals: ' + remaining + '/' + maxHealCount); if (remaining === 0) { healButton.alpha = 0.5; } } function updateTPBar() { var tpPercent = playerTP / maxTP; tpBar.scaleX = tpPercent; tpBar.x = 1024 - 200 * (1 - tpPercent); var roundedTP = Math.round(playerTP * 10) / 10; tpText.setText('TP: ' + roundedTP + '/' + maxTP); } function getCurrentPhase() { var healthPercent = enemyHealth / maxEnemyHealth; var sparePercent = spareCount / maxSpareCount; var combinedPercent = Math.max(healthPercent, sparePercent); if (combinedPercent > phase1Threshold) { return 1; // Phase 1: Easy (above 66%) } else if (combinedPercent > phase2Threshold) { return 2; // Phase 2: Medium (33-66%) } else { return 3; // Phase 3: Hard (below 33%) } } function checkNarrowDodge() { var hasNarrowDodge = false; for (var i = 0; i < projectiles.length; i++) { var projectile = projectiles[i]; if (projectile.isActive) { var dx = player.x - projectile.x; var dy = player.y - projectile.y; var distance = Math.sqrt(dx * dx + dy * dy); if (distance <= narrowDodgeDistance && distance > 30) { hasNarrowDodge = true; break; // Exit loop once we find one narrow dodge } } } if (hasNarrowDodge) { playerTP = Math.min(playerTP + 0.1, maxTP); playerTP = Math.round(playerTP * 10) / 10; updateTPBar(); LK.effects.flashObject(player, 0xffff00, 200); } } function checkCollisions() { for (var i = projectiles.length - 1; i >= 0; i--) { var projectile = projectiles[i]; if (projectile.isActive && player.intersects(projectile) && !isInvulnerable) { // Player hit - damage doubles in phase 3 var damage = currentPhase === 3 ? 20 : 10; playerHealth -= damage; LK.getSound('hit').play(); LK.effects.flashObject(player, 0xff0000, 200); // Start invulnerability isInvulnerable = true; player.alpha = 0.5; // Use tween to make player flash during invulnerability tween(player, { alpha: 1 }, { duration: 250, easing: tween.easeInOut, onFinish: function onFinish() { tween(player, { alpha: 0.5 }, { duration: 250, easing: tween.easeInOut }); } }); // Set timeout to end invulnerability LK.setTimeout(function () { isInvulnerable = false; tween.stop(player, { alpha: true }); player.alpha = 1; }, invulnerabilityDuration * 1000 / 60); // Convert frames to milliseconds // Remove projectile projectile.destroy(); projectiles.splice(i, 1); updateHealthBar(); if (playerHealth <= 0) { LK.showGameOver(); return; } } } } // Initialize UI state updateHealthBar(); updateEnemyHealthBar(); updateSpareProgress(); updateHealCount(); updateTPBar(); upButton.visible = false; downButton.visible = false; leftButton.visible = false; rightButton.visible = false; specialAttackButton.visible = true; // Create purple gradient at bottom for (var g = 0; g < gradientLayerCount; g++) { var gradientLayer = game.addChild(LK.getAsset('purpleGradient', { anchorX: 0.5, anchorY: 0.0 })); gradientLayer.x = 1024; gradientLayer.y = 2732 - 400 + g * 40; // Start from bottom and stack layers upward with tighter spacing gradientLayer.alpha = 0.15 - g * 0.018; // Much more transparent - start at 0.15 and fade out more gradually gradientLayer.height = 450 - g * 25; // Slightly larger layers with more gradual size reduction purpleGradientLayers.push(gradientLayer); } // Start battle music LK.playMusic('He2'); game.update = function () { // Update TP hitbox position to follow player tpHitbox.x = player.x; tpHitbox.y = player.y; // Show/hide TP hitbox based on game state tpHitbox.visible = gameState === 'defense'; // Purple particle system particleSpawnTimer++; if (particleSpawnTimer >= 30) { // Spawn every 0.5 seconds particleSpawnTimer = 0; if (purpleParticles.length < maxParticles) { var particle = new PurpleParticle(); // Random position at bottom of screen particle.x = Math.random() * 2048; particle.y = 2732; // Bottom of screen // Random upward velocity with slight horizontal drift var vx = (Math.random() - 0.5) * 2; // -1 to 1 horizontal drift var vy = -(Math.random() * 3 + 1); // -1 to -4 upward velocity particle.setVelocity(vx, vy); purpleParticles.push(particle); game.addChild(particle); // Animate particle with tween for scaling effect tween(particle, { scaleX: 1.5, scaleY: 1.5 }, { duration: 2000, easing: tween.easeOut }); } } // Update and clean up purple particles for (var i = purpleParticles.length - 1; i >= 0; i--) { if (!purpleParticles[i].isActive) { purpleParticles[i].destroy(); purpleParticles.splice(i, 1); } } if (gameState === 'defense') { defenseTimer++; // Update projectile patterns updateProjectilePattern(); // Check for narrow dodges checkNarrowDodge(); // Check for collisions checkCollisions(); // Remove inactive projectiles for (var i = projectiles.length - 1; i >= 0; i--) { if (!projectiles[i].isActive) { projectiles[i].destroy(); projectiles.splice(i, 1); } } // End defense phase if (defenseTimer >= defenseDuration) { startAttackPhase(); } } };
===================================================================
--- original.js
+++ change.js
@@ -282,9 +282,9 @@
enemyHealthBar.y = 1950;
enemyHealthBar.tint = 0xff0000;
var enemyHealthText = new Text2('Enemy HP: 5000/5000', {
size: 50,
- fill: 0xff0000
+ fill: 0x0066ff
});
enemyHealthText.anchor.set(0.5, 0.5);
enemyHealthText.x = 400;
enemyHealthText.y = 1950;
Appearance: An advanced and dramatically redesigned robotic version of Mettaton. It has futuristic armor, energy wings, and a stylized design reminiscent of an anime mecha. He have a heels, 2d pixel art
Red heart pixel art. In-Game asset. 2d. High contrast. No shadows
Black button with an orange outline that says "attack" and has a sword icon, pixel art. In-Game asset. 2d. High contrast. No shadows
Just a square border white no details. In-Game asset. 2d. High contrast. No shadows
Black button with an orange outline that says "Item" and has a Bag icon, pixel art. In-Game asset. 2d. High contrast. No shadows
Black button with an orange outline that says "Spare" and has a X icon, pixel art. In-Game asset. 2d. High contrast. No shadows
Black button with an orange outline that says "Spell" and has a fire icon, pixel art. In-Game asset. 2d. High contrast. No shadows
Energy ball. In-Game asset. 2d. High contrast. No shadows