/****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1");
/****
* Classes
****/
var Checkpoint = Container.expand(function (x, y) {
var self = Container.call(this);
var checkpointGraphics = self.attachAsset('checkpoint', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
self.activated = false;
self.activate = function () {
if (!self.activated) {
self.activated = true;
lastCheckpointX = self.x;
lastCheckpointY = self.y - 10;
LK.getSound('checkpoint').play();
LK.effects.flashObject(self, 0x00ff00, 300);
}
};
return self;
});
var Goal = Container.expand(function (x, y) {
var self = Container.call(this);
var goalGraphics = self.attachAsset('goal', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
return self;
});
var MovingPlatform = Container.expand(function (x, y, moveDistance, moveSpeed) {
var self = Container.call(this);
var platformGraphics = self.attachAsset('movingPlatform', {
anchorX: 0,
anchorY: 0
});
self.x = x;
self.y = y;
self.startX = x;
self.moveDistance = moveDistance || 200;
self.moveSpeed = moveSpeed || 2;
self.direction = 1;
self.update = function () {
self.x += self.moveSpeed * self.direction;
if (self.x >= self.startX + self.moveDistance || self.x <= self.startX) {
self.direction *= -1;
}
};
return self;
});
var Platform = Container.expand(function (width, height, x, y) {
var self = Container.call(this);
var platformGraphics = self.attachAsset('ground', {
width: width,
height: height,
anchorX: 0,
anchorY: 0
});
self.x = x;
self.y = y;
return self;
});
var Player = Container.expand(function () {
var self = Container.call(this);
var playerGraphics = self.attachAsset('player', {
anchorX: 0.5,
anchorY: 1.0
});
self.velocityY = 0;
self.velocityX = 0;
self.isGrounded = false;
self.jumpPower = -25;
self.gravity = 1.2;
self.moveSpeed = 8;
self.isDead = false;
self.startX = 0;
self.startY = 0;
self.jump = function () {
if (self.isGrounded && !self.isDead) {
self.velocityY = self.jumpPower;
self.isGrounded = false;
LK.getSound('jump').play();
}
};
self.die = function () {
if (!self.isDead) {
self.isDead = true;
attempts++;
LK.getSound('death').play();
LK.effects.flashScreen(0xff0000, 500);
// Reset player position after brief delay
LK.setTimeout(function () {
self.reset();
}, 500);
}
};
self.reset = function () {
self.x = lastCheckpointX;
self.y = lastCheckpointY;
self.velocityX = 0;
self.velocityY = 0;
self.isGrounded = false;
self.isDead = false;
};
self.update = function () {
if (self.isDead) return;
// Apply gravity
self.velocityY += self.gravity;
// Horizontal movement (auto-run)
self.velocityX = self.moveSpeed;
// Update position
self.x += self.velocityX;
self.y += self.velocityY;
// Keep player in bounds
if (self.x < 0) {
self.x = 0;
self.velocityX = 0;
}
// Death if falling too far
if (self.y > 2732 + 200) {
self.die();
}
};
return self;
});
var Spike = Container.expand(function (x, y) {
var self = Container.call(this);
var spikeGraphics = self.attachAsset('spike', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x1a1a2e
});
/****
* Game Code
****/
// Game variables
var currentLevel = storage.currentLevel || 1;
var attempts = 0;
var startTime = Date.now();
var lastCheckpointX = 200;
var lastCheckpointY = 2400;
// Game objects
var player;
var platforms = [];
var spikes = [];
var movingPlatforms = [];
var goal;
var checkpoints = [];
// Camera offset
var cameraOffsetX = 0;
// UI Elements
var levelTxt = new Text2('Level ' + currentLevel, {
size: 80,
fill: 0xFFFFFF
});
levelTxt.anchor.set(0.5, 0);
LK.gui.top.addChild(levelTxt);
levelTxt.y = 50;
var attemptsTxt = new Text2('Attempts: 0', {
size: 60,
fill: 0xFFFFFF
});
attemptsTxt.anchor.set(1, 0);
LK.gui.topRight.addChild(attemptsTxt);
attemptsTxt.x = -20;
attemptsTxt.y = 20;
var resetButton = new Text2('RESET', {
size: 50,
fill: 0xFF4444
});
resetButton.anchor.set(1, 0);
LK.gui.topRight.addChild(resetButton);
resetButton.x = -20;
resetButton.y = 90;
// Initialize level
function initLevel() {
// Clear existing objects
platforms = [];
spikes = [];
movingPlatforms = [];
checkpoints = [];
// Remove all children from game
while (game.children.length > 0) {
game.children[0].destroy();
}
// Create player
player = game.addChild(new Player());
player.x = lastCheckpointX;
player.y = lastCheckpointY;
// Level 1 - Basic jumping
if (currentLevel === 1) {
// Starting platform
platforms.push(game.addChild(new Platform(300, 40, 100, 2450)));
// Gap with platform
platforms.push(game.addChild(new Platform(200, 40, 500, 2400)));
// Spike obstacle
spikes.push(game.addChild(new Spike(750, 2400)));
// Higher platform
platforms.push(game.addChild(new Platform(250, 40, 850, 2300)));
// Checkpoint
checkpoints.push(game.addChild(new Checkpoint(1000, 2300)));
// Moving platform section
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2250, 150, 2)));
// Final platform with spikes
platforms.push(game.addChild(new Platform(300, 40, 1500, 2150)));
spikes.push(game.addChild(new Spike(1520, 2150)));
spikes.push(game.addChild(new Spike(1560, 2150)));
spikes.push(game.addChild(new Spike(1600, 2150)));
// Goal
goal = game.addChild(new Goal(1750, 2100));
}
// Level 2 - Moving platforms and timing challenges
else if (currentLevel === 2) {
// Starting platform
platforms.push(game.addChild(new Platform(250, 40, 100, 2450)));
// First moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(400, 2350, 200, 3)));
// Spike trap after moving platform
spikes.push(game.addChild(new Spike(650, 2350)));
spikes.push(game.addChild(new Spike(690, 2350)));
// High jump section
platforms.push(game.addChild(new Platform(150, 40, 800, 2250)));
platforms.push(game.addChild(new Platform(120, 40, 1050, 2150)));
// Checkpoint at mid-level
checkpoints.push(game.addChild(new Checkpoint(1120, 2150)));
// Double moving platform challenge
movingPlatforms.push(game.addChild(new MovingPlatform(1300, 2100, 180, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2050, 150, 2)));
// Spike gauntlet
platforms.push(game.addChild(new Platform(400, 40, 1850, 2000)));
spikes.push(game.addChild(new Spike(1900, 2000)));
spikes.push(game.addChild(new Spike(1940, 2000)));
spikes.push(game.addChild(new Spike(1980, 2000)));
spikes.push(game.addChild(new Spike(2020, 2000)));
spikes.push(game.addChild(new Spike(2060, 2000)));
// Final platform section
platforms.push(game.addChild(new Platform(200, 40, 2300, 1900)));
// Fast moving platform to goal
movingPlatforms.push(game.addChild(new MovingPlatform(2600, 1850, 200, 4)));
// Goal
goal = game.addChild(new Goal(2850, 1850));
}
// Level 3 - Devil's Challenge with precise timing
else if (currentLevel === 3) {
// Narrow starting platform
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Immediate spike danger
spikes.push(game.addChild(new Spike(320, 2450)));
// First precise jump
platforms.push(game.addChild(new Platform(100, 40, 380, 2350)));
// Triple moving platforms in sequence
movingPlatforms.push(game.addChild(new MovingPlatform(550, 2300, 120, 3.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(750, 2250, 100, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(950, 2200, 150, 2.8)));
// Spike corridor
platforms.push(game.addChild(new Platform(80, 40, 1200, 2200)));
spikes.push(game.addChild(new Spike(1220, 2200)));
platforms.push(game.addChild(new Platform(80, 40, 1320, 2200)));
spikes.push(game.addChild(new Spike(1340, 2200)));
platforms.push(game.addChild(new Platform(80, 40, 1440, 2200)));
// Checkpoint before final section
checkpoints.push(game.addChild(new Checkpoint(1480, 2200)));
// Fast alternating platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2100, 200, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1900, 2050, 180, 4.5)));
// Spike maze finale
platforms.push(game.addChild(new Platform(300, 40, 2200, 2000)));
spikes.push(game.addChild(new Spike(2250, 2000)));
spikes.push(game.addChild(new Spike(2290, 2000)));
platforms.push(game.addChild(new Platform(100, 40, 2350, 2000)));
spikes.push(game.addChild(new Spike(2370, 2000)));
platforms.push(game.addChild(new Platform(100, 40, 2500, 1950)));
// Final ultra-fast moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(2650, 1900, 250, 6)));
// Goal at the end
goal = game.addChild(new Goal(2950, 1900));
}
// Level 4 - Vertical Escape
else if (currentLevel === 4) {
// Starting platform at bottom
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Vertical tower with alternating platforms
platforms.push(game.addChild(new Platform(120, 40, 350, 2350)));
spikes.push(game.addChild(new Spike(380, 2350)));
platforms.push(game.addChild(new Platform(120, 40, 200, 2250)));
spikes.push(game.addChild(new Spike(230, 2250)));
platforms.push(game.addChild(new Platform(120, 40, 400, 2150)));
// Moving platform elevator
movingPlatforms.push(game.addChild(new MovingPlatform(600, 2400, 0, 0))); // Vertical moving platform
movingPlatforms[movingPlatforms.length - 1].moveDistance = 300;
movingPlatforms[movingPlatforms.length - 1].moveSpeed = 2;
movingPlatforms[movingPlatforms.length - 1].startY = 2400;
movingPlatforms[movingPlatforms.length - 1].y = 2400;
// Checkpoint at mid-height
checkpoints.push(game.addChild(new Checkpoint(650, 2100)));
// Spike wall section
platforms.push(game.addChild(new Platform(80, 40, 800, 2050)));
spikes.push(game.addChild(new Spike(820, 2050)));
spikes.push(game.addChild(new Spike(860, 2050)));
spikes.push(game.addChild(new Spike(900, 2050)));
platforms.push(game.addChild(new Platform(80, 40, 950, 2000)));
// Final ascending platforms
platforms.push(game.addChild(new Platform(100, 40, 1150, 1950)));
platforms.push(game.addChild(new Platform(100, 40, 1350, 1900)));
movingPlatforms.push(game.addChild(new MovingPlatform(1550, 1850, 150, 3)));
// Goal on top
goal = game.addChild(new Goal(1700, 1800));
}
// Level 5 - Speed Run Gauntlet
else if (currentLevel === 5) {
// Fast-paced level with quick decisions
platforms.push(game.addChild(new Platform(150, 40, 100, 2450)));
// Rapid spike sequence
for (var s = 0; s < 8; s++) {
if (s % 2 === 0) {
platforms.push(game.addChild(new Platform(60, 40, 300 + s * 80, 2400 - s * 20)));
} else {
spikes.push(game.addChild(new Spike(320 + s * 80, 2400 - s * 20)));
}
}
// Fast moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(900, 2250, 200, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2200, 180, 4.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1500, 2150, 160, 5.5)));
// Checkpoint
checkpoints.push(game.addChild(new Checkpoint(1700, 2150)));
// Spike tunnel
platforms.push(game.addChild(new Platform(400, 40, 1800, 2100)));
for (var st = 0; st < 6; st++) {
spikes.push(game.addChild(new Spike(1850 + st * 50, 2100)));
}
// Final dash
movingPlatforms.push(game.addChild(new MovingPlatform(2300, 2050, 250, 6)));
goal = game.addChild(new Goal(2600, 2000));
}
// Level 6 - The Pendulum
else if (currentLevel === 6) {
// Complex moving platform patterns
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Pendulum-like moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(400, 2350, 300, 3)));
movingPlatforms.push(game.addChild(new MovingPlatform(800, 2300, 250, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(1150, 2250, 200, 3.5)));
// Spike barriers
spikes.push(game.addChild(new Spike(450, 2350)));
spikes.push(game.addChild(new Spike(600, 2350)));
spikes.push(game.addChild(new Spike(850, 2300)));
spikes.push(game.addChild(new Spike(950, 2300)));
// Checkpoint platform
checkpoints.push(game.addChild(new Checkpoint(1400, 2200)));
// Synchronized moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2150, 150, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1850, 2100, 150, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(2100, 2050, 150, 2.5)));
// Final spike maze
platforms.push(game.addChild(new Platform(300, 40, 2350, 2000)));
spikes.push(game.addChild(new Spike(2400, 2000)));
spikes.push(game.addChild(new Spike(2450, 2000)));
spikes.push(game.addChild(new Spike(2500, 2000)));
goal = game.addChild(new Goal(2700, 1950));
}
// Level 7 - Chaos Theory
else if (currentLevel === 7) {
// Ultra-challenging with unpredictable patterns
platforms.push(game.addChild(new Platform(150, 40, 100, 2450)));
// Chaotic spike placement
var chaosSpikes = [350, 380, 420, 480, 520, 580];
for (var cs = 0; cs < chaosSpikes.length; cs++) {
spikes.push(game.addChild(new Spike(chaosSpikes[cs], 2450 - cs * 15)));
if (cs % 2 === 0) {
platforms.push(game.addChild(new Platform(60, 40, chaosSpikes[cs] + 40, 2450 - cs * 15)));
}
}
// Ultra-fast moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(700, 2300, 180, 6)));
movingPlatforms.push(game.addChild(new MovingPlatform(950, 2250, 160, 7)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2200, 140, 6.5)));
// Mid-level checkpoint
checkpoints.push(game.addChild(new Checkpoint(1400, 2150)));
// Alternating spike walls
for (var wall = 0; wall < 5; wall++) {
platforms.push(game.addChild(new Platform(60, 40, 1500 + wall * 120, 2100 - wall * 30)));
spikes.push(game.addChild(new Spike(1520 + wall * 120, 2100 - wall * 30)));
spikes.push(game.addChild(new Spike(1540 + wall * 120, 2100 - wall * 30)));
}
// Final impossible section
movingPlatforms.push(game.addChild(new MovingPlatform(2100, 1950, 200, 8)));
goal = game.addChild(new Goal(2400, 1900));
}
// Level 8 - Precision Master
else if (currentLevel === 8) {
// Extremely precise jumps required
platforms.push(game.addChild(new Platform(120, 40, 100, 2450)));
// Tiny platforms with death below
for (var tiny = 0; tiny < 12; tiny++) {
platforms.push(game.addChild(new Platform(40, 40, 250 + tiny * 70, 2400 - Math.sin(tiny) * 50)));
if (tiny > 0 && tiny < 11) {
spikes.push(game.addChild(new Spike(270 + tiny * 70, 2450)));
}
}
// Moving precision platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1000, 2200, 80, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2150, 60, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1350, 2100, 100, 3.5)));
// Checkpoint after precision section
checkpoints.push(game.addChild(new Checkpoint(1500, 2050)));
// Narrow corridor with spikes
platforms.push(game.addChild(new Platform(200, 40, 1600, 2000)));
for (var narrow = 0; narrow < 8; narrow++) {
spikes.push(game.addChild(new Spike(1630 + narrow * 20, 2000)));
}
// Final micro-platforms
platforms.push(game.addChild(new Platform(30, 40, 1900, 1950)));
platforms.push(game.addChild(new Platform(30, 40, 2000, 1920)));
platforms.push(game.addChild(new Platform(30, 40, 2100, 1890)));
goal = game.addChild(new Goal(2200, 1860));
}
// Level 9 - The Impossible
else if (currentLevel === 9) {
// Near-impossible difficulty
platforms.push(game.addChild(new Platform(100, 40, 100, 2450)));
// Immediate death trap
spikes.push(game.addChild(new Spike(220, 2450)));
spikes.push(game.addChild(new Spike(240, 2450)));
// Tiny moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(300, 2350, 50, 8)));
// Spike field
for (var field = 0; field < 15; field++) {
spikes.push(game.addChild(new Spike(400 + field * 30, 2400 - Math.random() * 100)));
if (field % 3 === 0) {
platforms.push(game.addChild(new Platform(25, 40, 415 + field * 30, 2380)));
}
}
// Ultra-fast sequence
movingPlatforms.push(game.addChild(new MovingPlatform(900, 2200, 120, 9)));
movingPlatforms.push(game.addChild(new MovingPlatform(1100, 2150, 100, 8.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1280, 2100, 80, 9.5)));
// Critical checkpoint
checkpoints.push(game.addChild(new Checkpoint(1400, 2050)));
// Final nightmare section
for (var nightmare = 0; nightmare < 10; nightmare++) {
platforms.push(game.addChild(new Platform(20, 40, 1500 + nightmare * 60, 2000 - nightmare * 25)));
spikes.push(game.addChild(new Spike(1510 + nightmare * 60, 2000 - nightmare * 25)));
spikes.push(game.addChild(new Spike(1530 + nightmare * 60, 2000 - nightmare * 25)));
}
goal = game.addChild(new Goal(2200, 1750));
}
// Level 10 - Devil's Final Test
else if (currentLevel === 10) {
// The ultimate challenge
platforms.push(game.addChild(new Platform(80, 40, 100, 2450)));
// Instant punishment
spikes.push(game.addChild(new Spike(200, 2450)));
// Micro-precision start
platforms.push(game.addChild(new Platform(20, 40, 250, 2400)));
platforms.push(game.addChild(new Platform(20, 40, 300, 2380)));
platforms.push(game.addChild(new Platform(20, 40, 350, 2360)));
// Hell's moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(450, 2300, 30, 10)));
movingPlatforms.push(game.addChild(new MovingPlatform(550, 2250, 40, 9.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(650, 2200, 35, 11)));
// Spike apocalypse
for (var apocalypse = 0; apocalypse < 20; apocalypse++) {
spikes.push(game.addChild(new Spike(750 + apocalypse * 25, 2300 - apocalypse * 15)));
if (apocalypse % 4 === 0) {
platforms.push(game.addChild(new Platform(15, 40, 760 + apocalypse * 25, 2290 - apocalypse * 15)));
}
}
// Mid-hell checkpoint
checkpoints.push(game.addChild(new Checkpoint(1300, 2000)));
// Lightning platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1400, 1950, 60, 12)));
movingPlatforms.push(game.addChild(new MovingPlatform(1550, 1900, 50, 11.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1700, 1850, 70, 13)));
// Final death corridor
platforms.push(game.addChild(new Platform(300, 40, 1850, 1800)));
for (var _final = 0; _final < 12; _final++) {
spikes.push(game.addChild(new Spike(1870 + _final * 20, 1800)));
}
// Victory platform
platforms.push(game.addChild(new Platform(100, 40, 2200, 1750)));
goal = game.addChild(new Goal(2250, 1750));
}
}
// Input handling
var isJumpPressed = false;
var jumpHoldTime = 0;
var maxJumpHoldTime = 15;
game.down = function (x, y, obj) {
isJumpPressed = true;
jumpHoldTime = 0;
player.jump();
};
game.up = function (x, y, obj) {
isJumpPressed = false;
jumpHoldTime = 0;
};
// Reset button functionality
resetButton.down = function (x, y, obj) {
// Reset level variables
attempts = 0;
startTime = Date.now();
lastCheckpointX = 200;
lastCheckpointY = 2400;
// Flash effect to show reset activated
LK.effects.flashScreen(0x4444FF, 300);
// Reinitialize current level
initLevel();
};
// Collision detection
function checkCollisions() {
if (player.isDead) return;
player.isGrounded = false;
// Platform collisions
for (var i = 0; i < platforms.length; i++) {
var platform = platforms[i];
if (player.intersects(platform)) {
if (player.velocityY > 0 && player.y - 30 < platform.y) {
player.y = platform.y;
player.velocityY = 0;
player.isGrounded = true;
}
}
}
// Moving platform collisions
for (var i = 0; i < movingPlatforms.length; i++) {
var platform = movingPlatforms[i];
if (player.intersects(platform)) {
if (player.velocityY > 0 && player.y - 30 < platform.y) {
player.y = platform.y;
player.velocityY = 0;
player.isGrounded = true;
// Move player with platform
player.x += platform.moveSpeed * platform.direction;
}
}
}
// Spike collisions
for (var i = 0; i < spikes.length; i++) {
var spike = spikes[i];
if (player.intersects(spike)) {
player.die();
return;
}
}
// Checkpoint collisions
for (var i = 0; i < checkpoints.length; i++) {
var checkpoint = checkpoints[i];
if (player.intersects(checkpoint)) {
checkpoint.activate();
}
}
// Goal collision
if (goal && player.intersects(goal)) {
// Level complete
var completionTime = Math.floor((Date.now() - startTime) / 1000);
var score = Math.max(1000 - attempts * 50 - completionTime, 100);
LK.setScore(LK.getScore() + score);
LK.getSound('levelComplete').play();
LK.effects.flashScreen(0x00ff00, 1000);
// Next level
currentLevel++;
storage.currentLevel = currentLevel;
if (currentLevel > 10) {
LK.showYouWin();
} else {
// Reset for next level
attempts = 0;
startTime = Date.now();
lastCheckpointX = 200;
lastCheckpointY = 2400;
levelTxt.setText('Level ' + currentLevel);
LK.setTimeout(function () {
initLevel();
}, 1000);
}
}
}
// Camera follow
function updateCamera() {
if (player) {
// Follow player horizontally with some offset
var targetOffsetX = -(player.x - 1024);
cameraOffsetX += (targetOffsetX - cameraOffsetX) * 0.1;
// Clamp camera to reasonable bounds
cameraOffsetX = Math.max(cameraOffsetX, -2000);
cameraOffsetX = Math.min(cameraOffsetX, 200);
game.x = cameraOffsetX;
}
}
// Variable jump mechanics
function handleJumpInput() {
if (isJumpPressed && jumpHoldTime < maxJumpHoldTime && player.velocityY < 0) {
player.velocityY -= 0.8; // Additional upward force while holding
jumpHoldTime++;
}
}
// Main game loop
game.update = function () {
handleJumpInput();
// Update moving platforms
for (var i = 0; i < movingPlatforms.length; i++) {
movingPlatforms[i].update();
}
checkCollisions();
updateCamera();
// Update UI
attemptsTxt.setText('Attempts: ' + attempts);
};
// Initialize the game
initLevel(); /****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1");
/****
* Classes
****/
var Checkpoint = Container.expand(function (x, y) {
var self = Container.call(this);
var checkpointGraphics = self.attachAsset('checkpoint', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
self.activated = false;
self.activate = function () {
if (!self.activated) {
self.activated = true;
lastCheckpointX = self.x;
lastCheckpointY = self.y - 10;
LK.getSound('checkpoint').play();
LK.effects.flashObject(self, 0x00ff00, 300);
}
};
return self;
});
var Goal = Container.expand(function (x, y) {
var self = Container.call(this);
var goalGraphics = self.attachAsset('goal', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
return self;
});
var MovingPlatform = Container.expand(function (x, y, moveDistance, moveSpeed) {
var self = Container.call(this);
var platformGraphics = self.attachAsset('movingPlatform', {
anchorX: 0,
anchorY: 0
});
self.x = x;
self.y = y;
self.startX = x;
self.moveDistance = moveDistance || 200;
self.moveSpeed = moveSpeed || 2;
self.direction = 1;
self.update = function () {
self.x += self.moveSpeed * self.direction;
if (self.x >= self.startX + self.moveDistance || self.x <= self.startX) {
self.direction *= -1;
}
};
return self;
});
var Platform = Container.expand(function (width, height, x, y) {
var self = Container.call(this);
var platformGraphics = self.attachAsset('ground', {
width: width,
height: height,
anchorX: 0,
anchorY: 0
});
self.x = x;
self.y = y;
return self;
});
var Player = Container.expand(function () {
var self = Container.call(this);
var playerGraphics = self.attachAsset('player', {
anchorX: 0.5,
anchorY: 1.0
});
self.velocityY = 0;
self.velocityX = 0;
self.isGrounded = false;
self.jumpPower = -25;
self.gravity = 1.2;
self.moveSpeed = 8;
self.isDead = false;
self.startX = 0;
self.startY = 0;
self.jump = function () {
if (self.isGrounded && !self.isDead) {
self.velocityY = self.jumpPower;
self.isGrounded = false;
LK.getSound('jump').play();
}
};
self.die = function () {
if (!self.isDead) {
self.isDead = true;
attempts++;
LK.getSound('death').play();
LK.effects.flashScreen(0xff0000, 500);
// Reset player position after brief delay
LK.setTimeout(function () {
self.reset();
}, 500);
}
};
self.reset = function () {
self.x = lastCheckpointX;
self.y = lastCheckpointY;
self.velocityX = 0;
self.velocityY = 0;
self.isGrounded = false;
self.isDead = false;
};
self.update = function () {
if (self.isDead) return;
// Apply gravity
self.velocityY += self.gravity;
// Horizontal movement (auto-run)
self.velocityX = self.moveSpeed;
// Update position
self.x += self.velocityX;
self.y += self.velocityY;
// Keep player in bounds
if (self.x < 0) {
self.x = 0;
self.velocityX = 0;
}
// Death if falling too far
if (self.y > 2732 + 200) {
self.die();
}
};
return self;
});
var Spike = Container.expand(function (x, y) {
var self = Container.call(this);
var spikeGraphics = self.attachAsset('spike', {
anchorX: 0.5,
anchorY: 1.0
});
self.x = x;
self.y = y;
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x1a1a2e
});
/****
* Game Code
****/
// Game variables
var currentLevel = storage.currentLevel || 1;
var attempts = 0;
var startTime = Date.now();
var lastCheckpointX = 200;
var lastCheckpointY = 2400;
// Game objects
var player;
var platforms = [];
var spikes = [];
var movingPlatforms = [];
var goal;
var checkpoints = [];
// Camera offset
var cameraOffsetX = 0;
// UI Elements
var levelTxt = new Text2('Level ' + currentLevel, {
size: 80,
fill: 0xFFFFFF
});
levelTxt.anchor.set(0.5, 0);
LK.gui.top.addChild(levelTxt);
levelTxt.y = 50;
var attemptsTxt = new Text2('Attempts: 0', {
size: 60,
fill: 0xFFFFFF
});
attemptsTxt.anchor.set(1, 0);
LK.gui.topRight.addChild(attemptsTxt);
attemptsTxt.x = -20;
attemptsTxt.y = 20;
var resetButton = new Text2('RESET', {
size: 50,
fill: 0xFF4444
});
resetButton.anchor.set(1, 0);
LK.gui.topRight.addChild(resetButton);
resetButton.x = -20;
resetButton.y = 90;
// Initialize level
function initLevel() {
// Clear existing objects
platforms = [];
spikes = [];
movingPlatforms = [];
checkpoints = [];
// Remove all children from game
while (game.children.length > 0) {
game.children[0].destroy();
}
// Create player
player = game.addChild(new Player());
player.x = lastCheckpointX;
player.y = lastCheckpointY;
// Level 1 - Basic jumping
if (currentLevel === 1) {
// Starting platform
platforms.push(game.addChild(new Platform(300, 40, 100, 2450)));
// Gap with platform
platforms.push(game.addChild(new Platform(200, 40, 500, 2400)));
// Spike obstacle
spikes.push(game.addChild(new Spike(750, 2400)));
// Higher platform
platforms.push(game.addChild(new Platform(250, 40, 850, 2300)));
// Checkpoint
checkpoints.push(game.addChild(new Checkpoint(1000, 2300)));
// Moving platform section
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2250, 150, 2)));
// Final platform with spikes
platforms.push(game.addChild(new Platform(300, 40, 1500, 2150)));
spikes.push(game.addChild(new Spike(1520, 2150)));
spikes.push(game.addChild(new Spike(1560, 2150)));
spikes.push(game.addChild(new Spike(1600, 2150)));
// Goal
goal = game.addChild(new Goal(1750, 2100));
}
// Level 2 - Moving platforms and timing challenges
else if (currentLevel === 2) {
// Starting platform
platforms.push(game.addChild(new Platform(250, 40, 100, 2450)));
// First moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(400, 2350, 200, 3)));
// Spike trap after moving platform
spikes.push(game.addChild(new Spike(650, 2350)));
spikes.push(game.addChild(new Spike(690, 2350)));
// High jump section
platforms.push(game.addChild(new Platform(150, 40, 800, 2250)));
platforms.push(game.addChild(new Platform(120, 40, 1050, 2150)));
// Checkpoint at mid-level
checkpoints.push(game.addChild(new Checkpoint(1120, 2150)));
// Double moving platform challenge
movingPlatforms.push(game.addChild(new MovingPlatform(1300, 2100, 180, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2050, 150, 2)));
// Spike gauntlet
platforms.push(game.addChild(new Platform(400, 40, 1850, 2000)));
spikes.push(game.addChild(new Spike(1900, 2000)));
spikes.push(game.addChild(new Spike(1940, 2000)));
spikes.push(game.addChild(new Spike(1980, 2000)));
spikes.push(game.addChild(new Spike(2020, 2000)));
spikes.push(game.addChild(new Spike(2060, 2000)));
// Final platform section
platforms.push(game.addChild(new Platform(200, 40, 2300, 1900)));
// Fast moving platform to goal
movingPlatforms.push(game.addChild(new MovingPlatform(2600, 1850, 200, 4)));
// Goal
goal = game.addChild(new Goal(2850, 1850));
}
// Level 3 - Devil's Challenge with precise timing
else if (currentLevel === 3) {
// Narrow starting platform
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Immediate spike danger
spikes.push(game.addChild(new Spike(320, 2450)));
// First precise jump
platforms.push(game.addChild(new Platform(100, 40, 380, 2350)));
// Triple moving platforms in sequence
movingPlatforms.push(game.addChild(new MovingPlatform(550, 2300, 120, 3.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(750, 2250, 100, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(950, 2200, 150, 2.8)));
// Spike corridor
platforms.push(game.addChild(new Platform(80, 40, 1200, 2200)));
spikes.push(game.addChild(new Spike(1220, 2200)));
platforms.push(game.addChild(new Platform(80, 40, 1320, 2200)));
spikes.push(game.addChild(new Spike(1340, 2200)));
platforms.push(game.addChild(new Platform(80, 40, 1440, 2200)));
// Checkpoint before final section
checkpoints.push(game.addChild(new Checkpoint(1480, 2200)));
// Fast alternating platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2100, 200, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1900, 2050, 180, 4.5)));
// Spike maze finale
platforms.push(game.addChild(new Platform(300, 40, 2200, 2000)));
spikes.push(game.addChild(new Spike(2250, 2000)));
spikes.push(game.addChild(new Spike(2290, 2000)));
platforms.push(game.addChild(new Platform(100, 40, 2350, 2000)));
spikes.push(game.addChild(new Spike(2370, 2000)));
platforms.push(game.addChild(new Platform(100, 40, 2500, 1950)));
// Final ultra-fast moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(2650, 1900, 250, 6)));
// Goal at the end
goal = game.addChild(new Goal(2950, 1900));
}
// Level 4 - Vertical Escape
else if (currentLevel === 4) {
// Starting platform at bottom
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Vertical tower with alternating platforms
platforms.push(game.addChild(new Platform(120, 40, 350, 2350)));
spikes.push(game.addChild(new Spike(380, 2350)));
platforms.push(game.addChild(new Platform(120, 40, 200, 2250)));
spikes.push(game.addChild(new Spike(230, 2250)));
platforms.push(game.addChild(new Platform(120, 40, 400, 2150)));
// Moving platform elevator
movingPlatforms.push(game.addChild(new MovingPlatform(600, 2400, 0, 0))); // Vertical moving platform
movingPlatforms[movingPlatforms.length - 1].moveDistance = 300;
movingPlatforms[movingPlatforms.length - 1].moveSpeed = 2;
movingPlatforms[movingPlatforms.length - 1].startY = 2400;
movingPlatforms[movingPlatforms.length - 1].y = 2400;
// Checkpoint at mid-height
checkpoints.push(game.addChild(new Checkpoint(650, 2100)));
// Spike wall section
platforms.push(game.addChild(new Platform(80, 40, 800, 2050)));
spikes.push(game.addChild(new Spike(820, 2050)));
spikes.push(game.addChild(new Spike(860, 2050)));
spikes.push(game.addChild(new Spike(900, 2050)));
platforms.push(game.addChild(new Platform(80, 40, 950, 2000)));
// Final ascending platforms
platforms.push(game.addChild(new Platform(100, 40, 1150, 1950)));
platforms.push(game.addChild(new Platform(100, 40, 1350, 1900)));
movingPlatforms.push(game.addChild(new MovingPlatform(1550, 1850, 150, 3)));
// Goal on top
goal = game.addChild(new Goal(1700, 1800));
}
// Level 5 - Speed Run Gauntlet
else if (currentLevel === 5) {
// Fast-paced level with quick decisions
platforms.push(game.addChild(new Platform(150, 40, 100, 2450)));
// Rapid spike sequence
for (var s = 0; s < 8; s++) {
if (s % 2 === 0) {
platforms.push(game.addChild(new Platform(60, 40, 300 + s * 80, 2400 - s * 20)));
} else {
spikes.push(game.addChild(new Spike(320 + s * 80, 2400 - s * 20)));
}
}
// Fast moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(900, 2250, 200, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2200, 180, 4.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1500, 2150, 160, 5.5)));
// Checkpoint
checkpoints.push(game.addChild(new Checkpoint(1700, 2150)));
// Spike tunnel
platforms.push(game.addChild(new Platform(400, 40, 1800, 2100)));
for (var st = 0; st < 6; st++) {
spikes.push(game.addChild(new Spike(1850 + st * 50, 2100)));
}
// Final dash
movingPlatforms.push(game.addChild(new MovingPlatform(2300, 2050, 250, 6)));
goal = game.addChild(new Goal(2600, 2000));
}
// Level 6 - The Pendulum
else if (currentLevel === 6) {
// Complex moving platform patterns
platforms.push(game.addChild(new Platform(200, 40, 100, 2450)));
// Pendulum-like moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(400, 2350, 300, 3)));
movingPlatforms.push(game.addChild(new MovingPlatform(800, 2300, 250, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(1150, 2250, 200, 3.5)));
// Spike barriers
spikes.push(game.addChild(new Spike(450, 2350)));
spikes.push(game.addChild(new Spike(600, 2350)));
spikes.push(game.addChild(new Spike(850, 2300)));
spikes.push(game.addChild(new Spike(950, 2300)));
// Checkpoint platform
checkpoints.push(game.addChild(new Checkpoint(1400, 2200)));
// Synchronized moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1600, 2150, 150, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1850, 2100, 150, 2.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(2100, 2050, 150, 2.5)));
// Final spike maze
platforms.push(game.addChild(new Platform(300, 40, 2350, 2000)));
spikes.push(game.addChild(new Spike(2400, 2000)));
spikes.push(game.addChild(new Spike(2450, 2000)));
spikes.push(game.addChild(new Spike(2500, 2000)));
goal = game.addChild(new Goal(2700, 1950));
}
// Level 7 - Chaos Theory
else if (currentLevel === 7) {
// Ultra-challenging with unpredictable patterns
platforms.push(game.addChild(new Platform(150, 40, 100, 2450)));
// Chaotic spike placement
var chaosSpikes = [350, 380, 420, 480, 520, 580];
for (var cs = 0; cs < chaosSpikes.length; cs++) {
spikes.push(game.addChild(new Spike(chaosSpikes[cs], 2450 - cs * 15)));
if (cs % 2 === 0) {
platforms.push(game.addChild(new Platform(60, 40, chaosSpikes[cs] + 40, 2450 - cs * 15)));
}
}
// Ultra-fast moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(700, 2300, 180, 6)));
movingPlatforms.push(game.addChild(new MovingPlatform(950, 2250, 160, 7)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2200, 140, 6.5)));
// Mid-level checkpoint
checkpoints.push(game.addChild(new Checkpoint(1400, 2150)));
// Alternating spike walls
for (var wall = 0; wall < 5; wall++) {
platforms.push(game.addChild(new Platform(60, 40, 1500 + wall * 120, 2100 - wall * 30)));
spikes.push(game.addChild(new Spike(1520 + wall * 120, 2100 - wall * 30)));
spikes.push(game.addChild(new Spike(1540 + wall * 120, 2100 - wall * 30)));
}
// Final impossible section
movingPlatforms.push(game.addChild(new MovingPlatform(2100, 1950, 200, 8)));
goal = game.addChild(new Goal(2400, 1900));
}
// Level 8 - Precision Master
else if (currentLevel === 8) {
// Extremely precise jumps required
platforms.push(game.addChild(new Platform(120, 40, 100, 2450)));
// Tiny platforms with death below
for (var tiny = 0; tiny < 12; tiny++) {
platforms.push(game.addChild(new Platform(40, 40, 250 + tiny * 70, 2400 - Math.sin(tiny) * 50)));
if (tiny > 0 && tiny < 11) {
spikes.push(game.addChild(new Spike(270 + tiny * 70, 2450)));
}
}
// Moving precision platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1000, 2200, 80, 4)));
movingPlatforms.push(game.addChild(new MovingPlatform(1200, 2150, 60, 5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1350, 2100, 100, 3.5)));
// Checkpoint after precision section
checkpoints.push(game.addChild(new Checkpoint(1500, 2050)));
// Narrow corridor with spikes
platforms.push(game.addChild(new Platform(200, 40, 1600, 2000)));
for (var narrow = 0; narrow < 8; narrow++) {
spikes.push(game.addChild(new Spike(1630 + narrow * 20, 2000)));
}
// Final micro-platforms
platforms.push(game.addChild(new Platform(30, 40, 1900, 1950)));
platforms.push(game.addChild(new Platform(30, 40, 2000, 1920)));
platforms.push(game.addChild(new Platform(30, 40, 2100, 1890)));
goal = game.addChild(new Goal(2200, 1860));
}
// Level 9 - The Impossible
else if (currentLevel === 9) {
// Near-impossible difficulty
platforms.push(game.addChild(new Platform(100, 40, 100, 2450)));
// Immediate death trap
spikes.push(game.addChild(new Spike(220, 2450)));
spikes.push(game.addChild(new Spike(240, 2450)));
// Tiny moving platform
movingPlatforms.push(game.addChild(new MovingPlatform(300, 2350, 50, 8)));
// Spike field
for (var field = 0; field < 15; field++) {
spikes.push(game.addChild(new Spike(400 + field * 30, 2400 - Math.random() * 100)));
if (field % 3 === 0) {
platforms.push(game.addChild(new Platform(25, 40, 415 + field * 30, 2380)));
}
}
// Ultra-fast sequence
movingPlatforms.push(game.addChild(new MovingPlatform(900, 2200, 120, 9)));
movingPlatforms.push(game.addChild(new MovingPlatform(1100, 2150, 100, 8.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1280, 2100, 80, 9.5)));
// Critical checkpoint
checkpoints.push(game.addChild(new Checkpoint(1400, 2050)));
// Final nightmare section
for (var nightmare = 0; nightmare < 10; nightmare++) {
platforms.push(game.addChild(new Platform(20, 40, 1500 + nightmare * 60, 2000 - nightmare * 25)));
spikes.push(game.addChild(new Spike(1510 + nightmare * 60, 2000 - nightmare * 25)));
spikes.push(game.addChild(new Spike(1530 + nightmare * 60, 2000 - nightmare * 25)));
}
goal = game.addChild(new Goal(2200, 1750));
}
// Level 10 - Devil's Final Test
else if (currentLevel === 10) {
// The ultimate challenge
platforms.push(game.addChild(new Platform(80, 40, 100, 2450)));
// Instant punishment
spikes.push(game.addChild(new Spike(200, 2450)));
// Micro-precision start
platforms.push(game.addChild(new Platform(20, 40, 250, 2400)));
platforms.push(game.addChild(new Platform(20, 40, 300, 2380)));
platforms.push(game.addChild(new Platform(20, 40, 350, 2360)));
// Hell's moving platforms
movingPlatforms.push(game.addChild(new MovingPlatform(450, 2300, 30, 10)));
movingPlatforms.push(game.addChild(new MovingPlatform(550, 2250, 40, 9.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(650, 2200, 35, 11)));
// Spike apocalypse
for (var apocalypse = 0; apocalypse < 20; apocalypse++) {
spikes.push(game.addChild(new Spike(750 + apocalypse * 25, 2300 - apocalypse * 15)));
if (apocalypse % 4 === 0) {
platforms.push(game.addChild(new Platform(15, 40, 760 + apocalypse * 25, 2290 - apocalypse * 15)));
}
}
// Mid-hell checkpoint
checkpoints.push(game.addChild(new Checkpoint(1300, 2000)));
// Lightning platforms
movingPlatforms.push(game.addChild(new MovingPlatform(1400, 1950, 60, 12)));
movingPlatforms.push(game.addChild(new MovingPlatform(1550, 1900, 50, 11.5)));
movingPlatforms.push(game.addChild(new MovingPlatform(1700, 1850, 70, 13)));
// Final death corridor
platforms.push(game.addChild(new Platform(300, 40, 1850, 1800)));
for (var _final = 0; _final < 12; _final++) {
spikes.push(game.addChild(new Spike(1870 + _final * 20, 1800)));
}
// Victory platform
platforms.push(game.addChild(new Platform(100, 40, 2200, 1750)));
goal = game.addChild(new Goal(2250, 1750));
}
}
// Input handling
var isJumpPressed = false;
var jumpHoldTime = 0;
var maxJumpHoldTime = 15;
game.down = function (x, y, obj) {
isJumpPressed = true;
jumpHoldTime = 0;
player.jump();
};
game.up = function (x, y, obj) {
isJumpPressed = false;
jumpHoldTime = 0;
};
// Reset button functionality
resetButton.down = function (x, y, obj) {
// Reset level variables
attempts = 0;
startTime = Date.now();
lastCheckpointX = 200;
lastCheckpointY = 2400;
// Flash effect to show reset activated
LK.effects.flashScreen(0x4444FF, 300);
// Reinitialize current level
initLevel();
};
// Collision detection
function checkCollisions() {
if (player.isDead) return;
player.isGrounded = false;
// Platform collisions
for (var i = 0; i < platforms.length; i++) {
var platform = platforms[i];
if (player.intersects(platform)) {
if (player.velocityY > 0 && player.y - 30 < platform.y) {
player.y = platform.y;
player.velocityY = 0;
player.isGrounded = true;
}
}
}
// Moving platform collisions
for (var i = 0; i < movingPlatforms.length; i++) {
var platform = movingPlatforms[i];
if (player.intersects(platform)) {
if (player.velocityY > 0 && player.y - 30 < platform.y) {
player.y = platform.y;
player.velocityY = 0;
player.isGrounded = true;
// Move player with platform
player.x += platform.moveSpeed * platform.direction;
}
}
}
// Spike collisions
for (var i = 0; i < spikes.length; i++) {
var spike = spikes[i];
if (player.intersects(spike)) {
player.die();
return;
}
}
// Checkpoint collisions
for (var i = 0; i < checkpoints.length; i++) {
var checkpoint = checkpoints[i];
if (player.intersects(checkpoint)) {
checkpoint.activate();
}
}
// Goal collision
if (goal && player.intersects(goal)) {
// Level complete
var completionTime = Math.floor((Date.now() - startTime) / 1000);
var score = Math.max(1000 - attempts * 50 - completionTime, 100);
LK.setScore(LK.getScore() + score);
LK.getSound('levelComplete').play();
LK.effects.flashScreen(0x00ff00, 1000);
// Next level
currentLevel++;
storage.currentLevel = currentLevel;
if (currentLevel > 10) {
LK.showYouWin();
} else {
// Reset for next level
attempts = 0;
startTime = Date.now();
lastCheckpointX = 200;
lastCheckpointY = 2400;
levelTxt.setText('Level ' + currentLevel);
LK.setTimeout(function () {
initLevel();
}, 1000);
}
}
}
// Camera follow
function updateCamera() {
if (player) {
// Follow player horizontally with some offset
var targetOffsetX = -(player.x - 1024);
cameraOffsetX += (targetOffsetX - cameraOffsetX) * 0.1;
// Clamp camera to reasonable bounds
cameraOffsetX = Math.max(cameraOffsetX, -2000);
cameraOffsetX = Math.min(cameraOffsetX, 200);
game.x = cameraOffsetX;
}
}
// Variable jump mechanics
function handleJumpInput() {
if (isJumpPressed && jumpHoldTime < maxJumpHoldTime && player.velocityY < 0) {
player.velocityY -= 0.8; // Additional upward force while holding
jumpHoldTime++;
}
}
// Main game loop
game.update = function () {
handleJumpInput();
// Update moving platforms
for (var i = 0; i < movingPlatforms.length; i++) {
movingPlatforms[i].update();
}
checkCollisions();
updateCamera();
// Update UI
attemptsTxt.setText('Attempts: ' + attempts);
};
// Initialize the game
initLevel();
Modern App Store icon, high definition, square with rounded corners, for a game titled "Devil's Parkour Challenge" and with the description "Navigate treacherous obstacle courses filled with spikes and moving platforms in this challenging parkour platformer that tests your timing and precision.". No text on icon!