User prompt
Please fix the bug: 'Error: Invalid value. Only literals or 1-level deep objects/arrays containing literals are allowed.' in or related to this line: 'storage.leaderboard = leaderboard;' Line Number: 574 ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
ask players to insert their names in the beginning and keep track of every player that played the game and make a leaderboard with the best 10 players name and scores ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
player can choose the spinning level between -20 to 20
User prompt
goalkeeper should sometimes saves the ball ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
make the goalkeeper saves the shots that are close to the middle of the goal. only the balls that goes to the close to the corner of the goals will not be saved by the goalkeeper ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
bring the goalkeeper in front of the goal
User prompt
goalkeeper should return to its initial position after each shot ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
goalkeeper moves faster to save the goal and sometimes the goalkeeper will save ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
goalkeeper now moves towards the balls direction to save from scoring ↪💡 Consider importing and using the following plugins: @upit/tween.v1
User prompt
bring the defenders in front of the goal, they shouldnt stay inside of the goal
User prompt
adjust the scoring zone in line with the goal zone, only if the ball touches to goal or the inside lines it will be counted as a score
User prompt
can you adjust goalkeeper to lower of the screen like he is standing in front of the goal
User prompt
I want lighter pink
User prompt
I changed my mind. I want pink background
User prompt
I want a little darker green
User prompt
can you change background color to lighter green
User prompt
move the buttons for spin to a little bit left and right just to adjust according to the text
User prompt
make all the texts and buttons bigger by 25%
User prompt
make all the texts and buttons bigger by x2
User prompt
can you add to the instruction page the info of "inside of the lines are counted as scores as well"
User prompt
can you add personal best score to the game screen? so that player can compete with its personal best ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
make the 2 defenders stay at the same place side by side, but make the other 2 players randomly
User prompt
starting from to 10th round put 1 random defender in front of the goal
User prompt
starting from to 10th round put 1 random defender close the goal
User prompt
change button press mechanism to clicking the arrows to change spin levels
/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); var storage = LK.import("@upit/storage.v1"); /**** * Classes ****/ var Ball = Container.expand(function () { var self = Container.call(this); var ballGraphics = self.attachAsset('ball', { anchorX: 0.5, anchorY: 0.5 }); self.velocityX = 0; self.velocityY = 0; self.gravity = 0; self.friction = 0.98; self.isMoving = false; self.spinForce = 0; self.spinDecay = 0.98; self.shoot = function (power, angle, spin) { self.velocityX = Math.cos(angle) * power; self.velocityY = Math.sin(angle) * power; self.spinForce = spin || 0; self.isMoving = true; LK.getSound('kick').play(); }; self.reset = function () { self.x = ballStartX; self.y = ballStartY; self.velocityX = 0; self.velocityY = 0; self.isMoving = false; self.spinForce = 0; }; self.update = function () { if (self.isMoving) { // Apply spin curve effect if (self.spinForce !== 0) { // Calculate perpendicular force to current velocity for curve var speed = Math.sqrt(self.velocityX * self.velocityX + self.velocityY * self.velocityY); if (speed > 0) { var normalX = -self.velocityY / speed; var normalY = self.velocityX / speed; self.velocityX += normalX * self.spinForce * 0.1; self.velocityY += normalY * self.spinForce * 0.1; } // Decay spin over time self.spinForce *= self.spinDecay; } self.x += self.velocityX; self.y += self.velocityY; // No friction applied - ball maintains constant velocity // Bounds checking if (self.x < 0 || self.x > 2048 || self.y > 2732) { self.isMoving = false; ballMissed(); } } }; return self; }); var Defender = Container.expand(function () { var self = Container.call(this); var defenderGraphics = self.attachAsset('defender', { anchorX: 0.5, anchorY: 1.0 }); return self; }); var Goalkeeper = Container.expand(function () { var self = Container.call(this); var keeperGraphics = self.attachAsset('goalkeeper', { anchorX: 0.5, anchorY: 1.0 }); return self; }); var TrajectoryDot = Container.expand(function () { var self = Container.call(this); var dotGraphics = self.attachAsset('trajectory', { anchorX: 0.5, anchorY: 0.5 }); dotGraphics.alpha = 0.6; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ backgroundColor: 0x7DD87D }); /**** * Game Code ****/ // Game variables var currentRound = 1; var attemptsLeft = 3; var ballStartX = 1024; var ballStartY = 2500; var goalX = 1024; var goalY = 400; var isAiming = false; var dragStartX = 0; var dragStartY = 0; var dragCurrentX = 0; var dragCurrentY = 0; var trajectoryDots = []; var defenders = []; // Player name and leaderboard variables var playerName = ''; var nameEntered = false; var nameInputText = ''; var alphabet = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'; var currentLetterIndex = 0; var leaderboardNames = storage.leaderboardNames || []; var leaderboardScores = storage.leaderboardScores || []; var showingLeaderboard = false; // Swipe tracking variables var swipePath = []; var swipeStartTime = 0; var swipeSpeed = 0; var swipeCurve = 0; var maxSwipePoints = 10; // Create grass field var grass = game.addChild(LK.getAsset('grass', { anchorX: 0, anchorY: 0, x: 0, y: 0 })); // Create goal structure var goal = game.addChild(LK.getAsset('goal', { anchorX: 0.5, anchorY: 0.5, x: goalX, y: goalY + 100 })); goal.alpha = 0.3; // Make goal semi-transparent so we can see the ball // Create goalkeeper var goalkeeper = game.addChild(new Goalkeeper()); goalkeeper.x = goalX; goalkeeper.y = goalY + 450; // Move goalkeeper in front of the goal // Store goalkeeper's initial position for reset var goalkeeperInitialX = goalkeeper.x; var goalkeeperInitialY = goalkeeper.y; // Create ball var ball = game.addChild(new Ball()); ball.reset(); // UI Elements var roundText = new Text2('Round: 1', { size: 100, fill: 0xFFFFFF }); roundText.anchor.set(0.5, 0); LK.gui.top.addChild(roundText); var attemptsText = new Text2('Attempts: 3', { size: 75, fill: 0xFFFFFF }); attemptsText.anchor.set(1.0, 0); LK.gui.topRight.addChild(attemptsText); var personalBest = storage.personalBest || 0; var personalBestText = new Text2('Best: ' + personalBest, { size: 75, fill: 0x00FF00 }); personalBestText.anchor.set(0, 0); LK.gui.topLeft.addChild(personalBestText); personalBestText.x = 120; // Move away from platform menu icon var powerText = new Text2('', { size: 62, fill: 0xFFFF00 }); powerText.anchor.set(0.5, 0.5); game.addChild(powerText); var curveText = new Text2('Spin: 0', { size: 75, fill: 0xFFFFFF }); curveText.anchor.set(0.5, 0.5); curveText.x = 1024; curveText.y = 200; game.addChild(curveText); var selectedCurve = 0; var maxCurve = 20; var curveValues = [-20, -18, -16, -14, -12, -10, -8, -6, -4, -2, -1, 0, 1, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20]; var curveIndex = 11; // Start at 0 curve (index 11 in the new array) var fixedSpeed = 35; // Create curve adjustment buttons var leftCurveButton = new Text2('<', { size: 125, fill: 0xFFFF00 }); leftCurveButton.anchor.set(0.5, 0.5); leftCurveButton.x = 850; leftCurveButton.y = 200; game.addChild(leftCurveButton); var rightCurveButton = new Text2('>', { size: 125, fill: 0xFFFF00 }); rightCurveButton.anchor.set(0.5, 0.5); rightCurveButton.x = 1198; rightCurveButton.y = 200; game.addChild(rightCurveButton); // Function to update curve display function updateCurveDisplay() { selectedCurve = curveValues[curveIndex]; if (selectedCurve === 0) { curveText.setText('Spin: 0'); } else { curveText.setText('Spin: ' + (selectedCurve > 0 ? '+' : '') + selectedCurve); } console.log('Curve updated to:', selectedCurve, 'Index:', curveIndex); } // Initialize curve display updateCurveDisplay(); // Initialize defenders for current round function setupRound() { // Clear existing defenders for (var i = 0; i < defenders.length; i++) { defenders[i].destroy(); } defenders = []; // Add defenders based on round var numDefenders = Math.min(currentRound - 1, 4); for (var i = 0; i < numDefenders; i++) { var defender = game.addChild(new Defender()); if (i < 2) { // First 2 defenders stay side by side in fixed positions var spacing = 120; var startX = goalX - spacing / 2; defender.x = startX + i * spacing; defender.y = goalY + 450 + currentRound * 30; } else { // Other 2 defenders are placed randomly var randomX = goalX + (Math.random() - 0.5) * 600; // Random X within a reasonable area var randomY = goalY + 400 + Math.random() * 200; // Random Y in front of goal defender.x = randomX; defender.y = randomY; } defenders.push(defender); } // Starting from round 10, add 1 random defender in front of the goal if (currentRound >= 10) { var randomDefender = game.addChild(new Defender()); // Random position in front of goal area var randomX = goalX + (Math.random() - 0.5) * 800; // Random X within goal width area var randomY = goalY + 350 + Math.random() * 150; // Random Y in front of goal randomDefender.x = randomX; randomDefender.y = randomY; defenders.push(randomDefender); } roundText.setText('Round: ' + currentRound); attemptsText.setText('Attempts: ' + attemptsLeft); } // Create trajectory preview function createTrajectoryPreview(power, angle, spin) { // Clear existing dots for (var i = 0; i < trajectoryDots.length; i++) { trajectoryDots[i].destroy(); } trajectoryDots = []; // Calculate trajectory points var steps = 15; var stepTime = 0.8; var tempVelX = Math.cos(angle) * power * 0.7; var tempVelY = Math.sin(angle) * power * 0.7; var tempX = ball.x; var tempY = ball.y; var tempSpin = spin || 0; for (var i = 0; i < steps; i++) { // Apply spin curve effect in preview if (tempSpin !== 0) { var speed = Math.sqrt(tempVelX * tempVelX + tempVelY * tempVelY); if (speed > 0) { var normalX = -tempVelY / speed; var normalY = tempVelX / speed; tempVelX += normalX * tempSpin * 0.1; tempVelY += normalY * tempSpin * 0.1; } tempSpin *= 0.98; } tempX += tempVelX * stepTime; tempY += tempVelY * stepTime; // No gravity applied to trajectory preview tempVelX *= 0.98; tempVelY *= 0.98; if (tempY > 2732 || tempX < 0 || tempX > 2048) break; var dot = game.addChild(new TrajectoryDot()); dot.x = tempX; dot.y = tempY; trajectoryDots.push(dot); } } // Clear trajectory preview function clearTrajectoryPreview() { for (var i = 0; i < trajectoryDots.length; i++) { trajectoryDots[i].destroy(); } trajectoryDots = []; } // Calculate curve from swipe path function calculateSwipeCurve() { if (swipePath.length < 3) return 0; var totalCurvature = 0; var validSegments = 0; var curvatureSum = 0; var pathLength = 0; // Calculate curvature at each point in the path for (var i = 1; i < swipePath.length - 1; i++) { var p1 = swipePath[i - 1]; var p2 = swipePath[i]; var p3 = swipePath[i + 1]; // Calculate vectors var v1x = p2.x - p1.x; var v1y = p2.y - p1.y; var v2x = p3.x - p2.x; var v2y = p3.y - p2.y; // Calculate cross product to determine curve direction var crossProduct = v1x * v2y - v1y * v2x; // Calculate magnitudes var mag1 = Math.sqrt(v1x * v1x + v1y * v1y); var mag2 = Math.sqrt(v2x * v2x + v2y * v2y); if (mag1 > 5 && mag2 > 5) { // Only consider significant movements curvatureSum += crossProduct / (mag1 * mag2); validSegments++; pathLength += mag1; } } if (validSegments > 0) { totalCurvature = curvatureSum / validSegments; // Scale based on path length and speed var lengthFactor = Math.min(pathLength / 200, 2); var speedFactor = Math.min(swipeSpeed / 500, 2); var finalCurve = totalCurvature * lengthFactor * speedFactor * 15; return Math.max(-10, Math.min(10, finalCurve)); } return 0; } // Calculate swipe speed function calculateSwipeSpeed() { if (swipePath.length < 2) return 0; var totalDistance = 0; var totalTime = 0; for (var i = 1; i < swipePath.length; i++) { var p1 = swipePath[i - 1]; var p2 = swipePath[i]; var dx = p2.x - p1.x; var dy = p2.y - p1.y; totalDistance += Math.sqrt(dx * dx + dy * dy); totalTime += p2.time - p1.time; } return totalTime > 0 ? totalDistance / totalTime * 1000 : 0; } // Ball collision detection function checkCollisions() { // Check goalkeeper collision first - this prevents scoring if (ball.intersects(goalkeeper)) { // Enhanced goalkeeper save logic based on ball position relative to goal var goalLeft = goalX - 400; // Left side of goal var goalRight = goalX + 400; // Right side of goal var goalWidth = 800; // Total goal width var goalCenter = goalX; // Goal center X position var distanceFromCenter = Math.abs(ball.x - goalCenter); var distanceFromGoalEdge = Math.min(Math.abs(ball.x - goalLeft), Math.abs(ball.x - goalRight)); var ballSpeed = Math.sqrt(ball.velocityX * ball.velocityX + ball.velocityY * ball.velocityY); // Calculate save chance based on position in goal var saveChance = 0; // Define middle zone (center 60% of goal) and corner zones (outer 20% each side) var middleZoneWidth = goalWidth * 0.6; // 480 pixels from center var cornerZoneWidth = goalWidth * 0.2; // 160 pixels each corner if (distanceFromCenter <= middleZoneWidth / 2) { // Ball is in the middle zone - high save chance saveChance = 0.95; // 95% save chance in middle } else if (distanceFromGoalEdge <= cornerZoneWidth) { // Ball is in corner zone - very low save chance saveChance = 0.1; // Only 10% save chance in corners } else { // Ball is in transition zone between middle and corner saveChance = 0.4; // Moderate save chance in transition } // Adjust save chance based on ball speed (faster balls harder to save) if (ballSpeed > 30) saveChance -= 0.2; if (ballSpeed > 40) saveChance -= 0.2; // Ensure save chance stays within reasonable bounds saveChance = Math.max(0.05, Math.min(0.98, saveChance)); // Random save attempt - increased base save chances var adjustedSaveChance = saveChance; // Boost save chances significantly if (distanceFromCenter <= middleZoneWidth / 2) { // Ball is in the middle zone - very high save chance adjustedSaveChance = 0.85; // 85% save chance in middle } else if (distanceFromGoalEdge <= cornerZoneWidth) { // Ball is in corner zone - still some save chance adjustedSaveChance = 0.25; // 25% save chance in corners } else { // Ball is in transition zone adjustedSaveChance = 0.55; // 55% save chance in transition } // Adjust save chance based on ball speed (faster balls harder to save) if (ballSpeed > 30) adjustedSaveChance -= 0.15; if (ballSpeed > 40) adjustedSaveChance -= 0.15; // Ensure save chance stays within reasonable bounds adjustedSaveChance = Math.max(0.15, Math.min(0.95, adjustedSaveChance)); console.log('Save attempt - Ball X:', ball.x, 'Distance from center:', distanceFromCenter, 'Save chance:', adjustedSaveChance); if (Math.random() < adjustedSaveChance) { // Successful save console.log('GOALKEEPER SAVE!'); ball.isMoving = false; LK.getSound('save').play(); LK.effects.flashObject(goalkeeper, 0x00ff00, 800); // Green flash for save LK.effects.flashScreen(0x00ff00, 300); // Screen flash for dramatic effect // Animate goalkeeper dive with tween - more dramatic tween(goalkeeper, { scaleX: 1.5, scaleY: 0.7, rotation: ball.x > goalkeeper.x ? 0.3 : -0.3 // Dive towards ball }, { duration: 400, easing: tween.easeOut, onFinish: function onFinish() { tween(goalkeeper, { scaleX: 1.0, scaleY: 1.0, rotation: 0 }, { duration: 300, onFinish: function onFinish() { resetGoalkeeper(); // Reset goalkeeper position after dive animation } }); } }); ballMissed(); return; } else { // Goalkeeper fails to save - ball continues console.log('Goalkeeper missed the save'); LK.effects.flashObject(goalkeeper, 0xff6666, 300); } } // Check goal scoring - ball must be inside goal area including side lines // Goal asset is positioned at goalY + 100 and has height 584.38, width 800 var goalLeft = goalX - 400; // Left side line of goal (800/2 = 400) var goalRight = goalX + 400; // Right side line of goal var goalTop = goalY + 100 - 292; // Top of goal (goalY + 100 - height/2) var goalBottom = goalY + 100 + 292; // Bottom of goal (goalY + 100 + height/2) if (ball.x >= goalLeft && ball.x <= goalRight && ball.y >= goalTop && ball.y <= goalBottom) { // Goal scored! Ball touched inside goal area or side lines ball.isMoving = false; LK.getSound('goal').play(); LK.effects.flashScreen(0x00ff00, 500); LK.setScore(LK.getScore() + 1); // Check and update personal best var currentScore = LK.getScore(); if (currentScore > personalBest) { personalBest = currentScore; storage.personalBest = personalBest; personalBestText.setText('Best: ' + personalBest); LK.effects.flashObject(personalBestText, 0xFFFF00, 1000); } currentRound++; // Reset attempts for next round attemptsLeft = 3; LK.setTimeout(function () { ball.reset(); resetGoalkeeper(); // Reset goalkeeper position setupRound(); }, 1000); return; } // Check defender collisions for (var i = 0; i < defenders.length; i++) { if (ball.intersects(defenders[i])) { ball.isMoving = false; LK.effects.flashObject(defenders[i], 0xff0000, 500); ballMissed(); return; } } // Goal structure collision removed to allow ball to pass through for scoring } // Function to reset goalkeeper to initial position function resetGoalkeeper() { tween(goalkeeper, { x: goalkeeperInitialX, y: goalkeeperInitialY }, { duration: 800, easing: tween.easeOut }); } // Function to update name display function updateNameDisplay() { nameDisplayText.setText(nameInputText); currentLetterText.setText(alphabet[currentLetterIndex]); } // Function to add current letter to name function addCurrentLetter() { if (nameInputText.length < 8) { // Limit name length nameInputText += alphabet[currentLetterIndex]; updateNameDisplay(); } } // Function to finish name entry function finishNameEntry() { if (nameInputText.length > 0) { playerName = nameInputText; nameEntered = true; // Hide name input UI namePromptText.alpha = 0; nameDisplayText.alpha = 0; currentLetterText.alpha = 0; leftNameButton.alpha = 0; rightNameButton.alpha = 0; addLetterButton.alpha = 0; finishNameButton.alpha = 0; // Show game instructions instructionsText.alpha = 1; startButton.alpha = 1; } } // Function to add score to leaderboard function addToLeaderboard(name, score) { leaderboardNames.push(name); leaderboardScores.push(score); // Create temporary array for sorting var tempLeaderboard = []; for (var i = 0; i < leaderboardNames.length; i++) { tempLeaderboard.push({ name: leaderboardNames[i], score: leaderboardScores[i] }); } // Sort by score descending tempLeaderboard.sort(function (a, b) { return b.score - a.score; }); // Keep only top 10 if (tempLeaderboard.length > 10) { tempLeaderboard = tempLeaderboard.slice(0, 10); } // Update arrays with sorted data leaderboardNames = []; leaderboardScores = []; for (var i = 0; i < tempLeaderboard.length; i++) { leaderboardNames.push(tempLeaderboard[i].name); leaderboardScores.push(tempLeaderboard[i].score); } // Save to storage as separate arrays storage.leaderboardNames = leaderboardNames; storage.leaderboardScores = leaderboardScores; } // Function to show leaderboard function showLeaderboard() { showingLeaderboard = true; // Create leaderboard display var leaderboardText = 'TOP 10 PLAYERS:\n\n'; for (var i = 0; i < Math.min(10, leaderboardNames.length); i++) { leaderboardText += i + 1 + '. ' + leaderboardNames[i] + ' - ' + leaderboardScores[i] + '\n'; } if (leaderboardNames.length === 0) { leaderboardText += 'No scores yet!'; } var leaderboardDisplay = new Text2(leaderboardText, { size: 60, fill: 0xFFFFFF, align: 'center' }); leaderboardDisplay.anchor.set(0.5, 0.5); leaderboardDisplay.x = 1024; leaderboardDisplay.y = 1366; game.addChild(leaderboardDisplay); // Auto-hide after 5 seconds LK.setTimeout(function () { if (leaderboardDisplay && leaderboardDisplay.parent) { leaderboardDisplay.destroy(); showingLeaderboard = false; } }, 5000); } function ballMissed() { attemptsLeft--; attemptsText.setText('Attempts: ' + attemptsLeft); if (attemptsLeft <= 0) { LK.effects.flashScreen(0xff0000, 1000); // Add score to leaderboard before game over if (playerName && LK.getScore() > 0) { addToLeaderboard(playerName, LK.getScore()); } LK.setTimeout(function () { // Show leaderboard before game over if (leaderboardNames.length > 0) { showLeaderboard(); LK.setTimeout(function () { LK.showGameOver(); // Show game over screen and reset game }, 3000); } else { LK.showGameOver(); // Show game over screen and reset game } }, 1500); } else { LK.setTimeout(function () { ball.reset(); resetGoalkeeper(); // Reset goalkeeper position }, 1000); } } // Game controls are now defined as variables above game.update = function () { if (ball.isMoving) { // Goalkeeper AI - move towards ball's predicted position if (ball.y < goalY + 400) { // Only react when ball is getting close to goal var ballTargetX = ball.x + ball.velocityX * 15; // Predict where ball will be (increased prediction) var keeperSpeed = 15; // Increased goalkeeper movement speed var maxKeeperX = goalX + 350; // Right boundary for keeper movement var minKeeperX = goalX - 350; // Left boundary for keeper movement // Clamp keeper target position within goal area ballTargetX = Math.max(minKeeperX, Math.min(maxKeeperX, ballTargetX)); // Move keeper towards predicted ball position with tween animation var deltaX = ballTargetX - goalkeeper.x; if (Math.abs(deltaX) > 5) { // Use tween for smooth goalkeeper movement tween(goalkeeper, { x: ballTargetX }, { duration: 200, easing: tween.easeOut }); } } checkCollisions(); } }; // Game instructions // Name input UI var namePromptText = new Text2('ENTER YOUR NAME:', { size: 80, fill: 0xFFFFFF, align: 'center' }); namePromptText.anchor.set(0.5, 0.5); namePromptText.x = 1024; namePromptText.y = 1200; game.addChild(namePromptText); var nameDisplayText = new Text2('', { size: 100, fill: 0x00FF00, align: 'center' }); nameDisplayText.anchor.set(0.5, 0.5); nameDisplayText.x = 1024; nameDisplayText.y = 1350; game.addChild(nameDisplayText); var currentLetterText = new Text2('A', { size: 120, fill: 0xFFFF00, align: 'center' }); currentLetterText.anchor.set(0.5, 0.5); currentLetterText.x = 1024; currentLetterText.y = 1500; game.addChild(currentLetterText); var leftNameButton = new Text2('<', { size: 100, fill: 0xFFFF00 }); leftNameButton.anchor.set(0.5, 0.5); leftNameButton.x = 900; leftNameButton.y = 1500; game.addChild(leftNameButton); var rightNameButton = new Text2('>', { size: 100, fill: 0xFFFF00 }); rightNameButton.anchor.set(0.5, 0.5); rightNameButton.x = 1148; rightNameButton.y = 1500; game.addChild(rightNameButton); var addLetterButton = new Text2('ADD LETTER', { size: 60, fill: 0x00FF00 }); addLetterButton.anchor.set(0.5, 0.5); addLetterButton.x = 1024; addLetterButton.y = 1650; game.addChild(addLetterButton); var finishNameButton = new Text2('START GAME', { size: 80, fill: 0xFF0000 }); finishNameButton.anchor.set(0.5, 0.5); finishNameButton.x = 1024; finishNameButton.y = 1750; game.addChild(finishNameButton); var instructionsText = new Text2('Swipe to aim and shoot!\nUse < > buttons to adjust spin.\nSwipe direction sets aim, spin is manual.\nInside of the lines are counted as scores as well.', { size: 75, fill: 0xFFFFFF, align: 'center' }); instructionsText.anchor.set(0.5, 0.5); instructionsText.x = 1024; instructionsText.y = 1366; instructionsText.alpha = 0; // Hidden initially game.addChild(instructionsText); var startButton = new Text2('TAP TO START', { size: 100, fill: 0x00FF00 }); startButton.anchor.set(0.5, 0.5); startButton.x = 1024; startButton.y = 1600; startButton.alpha = 0; // Hidden initially game.addChild(startButton); var gameStarted = false; // Store the actual game control functions var originalDown = function originalDown(x, y, obj) { if (!ball.isMoving && ball.y > 2000) { isAiming = true; dragStartX = x; dragStartY = y; swipePath = [{ x: x, y: y, time: Date.now() }]; swipeStartTime = Date.now(); } }; var originalMove = function originalMove(x, y, obj) { if (isAiming && !ball.isMoving) { dragCurrentX = x; dragCurrentY = y; // Track swipe path var currentTime = Date.now(); swipePath.push({ x: x, y: y, time: currentTime }); // Keep only recent points if (swipePath.length > maxSwipePoints) { swipePath.shift(); } var deltaX = x - dragStartX; var deltaY = y - dragStartY; var distance = Math.sqrt(deltaX * deltaX + deltaY * deltaY); var power = fixedSpeed; var angle = Math.atan2(-deltaY, deltaX); powerText.x = ball.x; powerText.y = ball.y - 100; powerText.setText(''); // Show trajectory with current manual curve setting createTrajectoryPreview(power, angle, selectedCurve); } }; var originalUp = function originalUp(x, y, obj) { if (isAiming && !ball.isMoving) { var deltaX = x - dragStartX; var deltaY = y - dragStartY; var distance = Math.sqrt(deltaX * deltaX + deltaY * deltaY); if (distance > 20) { var power = fixedSpeed; var angle = Math.atan2(-deltaY, deltaX); // Use manually selected curve var spin = selectedCurve; ball.shoot(power, angle, spin); } isAiming = false; powerText.setText(''); clearTrajectoryPreview(); // Clear swipe path swipePath = []; } }; // Add click handlers to name input buttons leftNameButton.down = function (x, y, obj) { if (!nameEntered) { if (currentLetterIndex > 0) { currentLetterIndex--; } else { currentLetterIndex = alphabet.length - 1; } updateNameDisplay(); LK.effects.flashObject(leftNameButton, 0x00ff00, 200); } }; rightNameButton.down = function (x, y, obj) { if (!nameEntered) { if (currentLetterIndex < alphabet.length - 1) { currentLetterIndex++; } else { currentLetterIndex = 0; } updateNameDisplay(); LK.effects.flashObject(rightNameButton, 0x00ff00, 200); } }; addLetterButton.down = function (x, y, obj) { if (!nameEntered) { addCurrentLetter(); LK.effects.flashObject(addLetterButton, 0x00ff00, 200); } }; finishNameButton.down = function (x, y, obj) { if (!nameEntered) { finishNameEntry(); LK.effects.flashObject(finishNameButton, 0x00ff00, 200); } }; // Add click handlers to curve buttons leftCurveButton.down = function (x, y, obj) { if (gameStarted && !ball.isMoving) { if (curveIndex > 0) { curveIndex--; updateCurveDisplay(); LK.effects.flashObject(leftCurveButton, 0x00ff00, 200); } } }; rightCurveButton.down = function (x, y, obj) { if (gameStarted && !ball.isMoving) { if (curveIndex < curveValues.length - 1) { curveIndex++; updateCurveDisplay(); LK.effects.flashObject(rightCurveButton, 0x00ff00, 200); } } }; // Initialize name display updateNameDisplay(); // Override game controls until game starts game.down = function (x, y, obj) { if (!nameEntered) { // Still in name input phase, do nothing (buttons handle their own events) return; } if (!gameStarted) { // Start the game gameStarted = true; instructionsText.destroy(); startButton.destroy(); // Restore original controls game.down = originalDown; game.move = originalMove; game.up = originalUp; // Initialize first round setupRound(); // Call the original down handler for this event originalDown(x, y, obj); return; } }; game.move = function (x, y, obj) { // Do nothing until game starts }; game.up = function (x, y, obj) { // Do nothing until game starts };
===================================================================
--- original.js
+++ change.js
@@ -117,9 +117,10 @@
var nameEntered = false;
var nameInputText = '';
var alphabet = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
var currentLetterIndex = 0;
-var leaderboard = storage.leaderboard || [];
+var leaderboardNames = storage.leaderboardNames || [];
+var leaderboardScores = storage.leaderboardScores || [];
var showingLeaderboard = false;
// Swipe tracking variables
var swipePath = [];
var swipeStartTime = 0;
@@ -529,33 +530,46 @@
}
}
// Function to add score to leaderboard
function addToLeaderboard(name, score) {
- leaderboard.push({
- name: name,
- score: score
- });
+ leaderboardNames.push(name);
+ leaderboardScores.push(score);
+ // Create temporary array for sorting
+ var tempLeaderboard = [];
+ for (var i = 0; i < leaderboardNames.length; i++) {
+ tempLeaderboard.push({
+ name: leaderboardNames[i],
+ score: leaderboardScores[i]
+ });
+ }
// Sort by score descending
- leaderboard.sort(function (a, b) {
+ tempLeaderboard.sort(function (a, b) {
return b.score - a.score;
});
// Keep only top 10
- if (leaderboard.length > 10) {
- leaderboard = leaderboard.slice(0, 10);
+ if (tempLeaderboard.length > 10) {
+ tempLeaderboard = tempLeaderboard.slice(0, 10);
}
- // Save to storage
- storage.leaderboard = leaderboard;
+ // Update arrays with sorted data
+ leaderboardNames = [];
+ leaderboardScores = [];
+ for (var i = 0; i < tempLeaderboard.length; i++) {
+ leaderboardNames.push(tempLeaderboard[i].name);
+ leaderboardScores.push(tempLeaderboard[i].score);
+ }
+ // Save to storage as separate arrays
+ storage.leaderboardNames = leaderboardNames;
+ storage.leaderboardScores = leaderboardScores;
}
// Function to show leaderboard
function showLeaderboard() {
showingLeaderboard = true;
// Create leaderboard display
var leaderboardText = 'TOP 10 PLAYERS:\n\n';
- for (var i = 0; i < Math.min(10, leaderboard.length); i++) {
- var entry = leaderboard[i];
- leaderboardText += i + 1 + '. ' + entry.name + ' - ' + entry.score + '\n';
+ for (var i = 0; i < Math.min(10, leaderboardNames.length); i++) {
+ leaderboardText += i + 1 + '. ' + leaderboardNames[i] + ' - ' + leaderboardScores[i] + '\n';
}
- if (leaderboard.length === 0) {
+ if (leaderboardNames.length === 0) {
leaderboardText += 'No scores yet!';
}
var leaderboardDisplay = new Text2(leaderboardText, {
size: 60,
@@ -584,9 +598,9 @@
addToLeaderboard(playerName, LK.getScore());
}
LK.setTimeout(function () {
// Show leaderboard before game over
- if (leaderboard.length > 0) {
+ if (leaderboardNames.length > 0) {
showLeaderboard();
LK.setTimeout(function () {
LK.showGameOver(); // Show game over screen and reset game
}, 3000);