User prompt
oyun daha canlı olsun
User prompt
oyun daha canlı ve hareketli olsun
User prompt
arka ilerledikce arka pilanda ilerlesin ve farklı gezegenler cıksın
User prompt
arka pilan siyah olsun
User prompt
arka pilan uzay olsun
User prompt
arka pilanı hareket len dir
User prompt
Please fix the bug: 'Cannot read properties of undefined (reading 'length')' in or related to this line: 'for (var i = 0; i < backgroundPlanets.length; i++) {' Line Number: 175
User prompt
arka pilan uzay olsun ve arkada gezegenler olsun
User prompt
arka pilanı kaldır
User prompt
arkadaki dikenli topları kaldır
User prompt
arka pilanı degistir
User prompt
son ekledigin seyi kaldır
User prompt
grafikleri geliştir
User prompt
oyunu daha canlı yap
User prompt
ARKA PİLANI UZAY YAP VE ARKADA BAZEN GEZEGENLER GÖZÜKSÜN
User prompt
BULUTLARI GERİ EKLE
User prompt
oyunu sıfırla
User prompt
oyunu 4k yap
User prompt
oyunun kalitesini arrtır
User prompt
oyunun kalitesini arttır
Code edit (1 edits merged)
Please save this source code
User prompt
Nyan Cat Sky Dash
User prompt
ana karakter nyan cat olsun
Initial prompt
bana flapy bird gibi bir oyun yap
/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); /**** * Classes ****/ // Nyan Cat class var NyanCat = Container.expand(function () { var self = Container.call(this); // Rainbow trail (visual only, not collidable) var rainbow = self.attachAsset('rainbow', { anchorX: 1, anchorY: 0.5, x: -90, y: 0, scaleY: 1.2 }); // Add a soft highlight to rainbow for polish rainbow.alpha = 0.92; rainbow.tint = 0xffe0fa; // Add additional rainbow bands for a lively animated effect self.rainbowBands = []; var rainbowColors = [0xfe6cd1, 0xf9d423, 0x7ed957, 0x4a90e2, 0x9b59b6, 0xffffff]; for (var i = 0; i < rainbowColors.length; i++) { var band = self.attachAsset('rainbow', { anchorX: 1, anchorY: 0.5, x: -90, y: (i - 2.5) * 18, // stack vertically scaleY: 0.18, scaleX: 1.0 }); band.alpha = 0.82; band.tint = rainbowColors[i]; self.addChildAt(band, i); self.rainbowBands.push(band); } // Nyan Cat sprite var cat = self.attachAsset('nyanCat', { anchorX: 0.5, anchorY: 0.5, x: 0, y: 0 }); // Add a soft shadow to Nyan Cat for depth cat.alpha = 1; cat.tint = 0xffffff; self.catShadow = LK.getAsset('nyanCat', { anchorX: 0.5, anchorY: 0.5, x: 8, y: 18 }); self.catShadow.alpha = 0.22; self.catShadow.tint = 0x000000; self.addChildAt(self.catShadow, 0); // For collision, use the cat's bounds (not rainbow) self.getCollisionBounds = function () { return { x: self.x - cat.width / 2, y: self.y - cat.height / 2, width: cat.width, height: cat.height }; }; // Flash effect on hit self.flash = function () { tween(cat, { alpha: 0.3 }, { duration: 80, onFinish: function onFinish() { tween(cat, { alpha: 1 }, { duration: 120 }); } }); }; // Rainbow parallax movement for quality polish self.update = function () { // Rainbow trail parallax: slight horizontal movement for visual polish rainbow.x = -90 + Math.sin(LK.ticks * 0.12) * 12; // Animate rainbow bands for a lively, wavy effect for (var i = 0; i < self.rainbowBands.length; i++) { var band = self.rainbowBands[i]; // Wavy movement: each band has a phase offset band.x = -90 + Math.sin(LK.ticks * 0.12 + i * 0.5) * (12 + i * 2); band.y = (i - 2.5) * 18 + Math.sin(LK.ticks * 0.18 + i * 0.7) * 8; // Animate alpha for shimmer band.alpha = 0.7 + 0.25 * Math.abs(Math.sin(LK.ticks * 0.09 + i)); // Animate scale for a breathing effect band.scaleX = 1.0 + 0.13 * Math.sin(LK.ticks * 0.11 + i * 0.8); } }; return self; }); // Obstacle class (cloud or star) var Obstacle = Container.expand(function () { var self = Container.call(this); // Randomly choose cloud or star var isStar = Math.random() < 0.4; var assetId = isStar ? 'star' : 'cloud'; var asset = self.attachAsset(assetId, { anchorX: 0.5, anchorY: 0.5 }); // Add soft shadow for depth self.shadow = self.attachAsset(assetId, { anchorX: 0.5, anchorY: 0.5, x: 10, y: 18 }); self.shadow.alpha = 0.18; self.shadow.tint = 0x000000; self.addChildAt(self.shadow, 0); self.isStar = isStar; // For collision self.getCollisionBounds = function () { return { x: self.x - asset.width / 2, y: self.y - asset.height / 2, width: asset.width, height: asset.height }; }; // Speed will be set on spawn self.speed = 0; self.update = function () { self.x -= self.speed; }; return self; }); // Shooting Star class for lively background var ShootingStar = Container.expand(function () { var self = Container.call(this); // Use the 'star' asset, small and bright var star = self.attachAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.32, scaleY: 0.32 }); self.star = star; // Randomize speed and angle self.speed = 18 + Math.random() * 10; //{U} // Reduced speed for slower falling stars self.angle = Math.PI * (0.18 + Math.random() * 0.12); // ~10deg downward self.alpha = 0.7 + Math.random() * 0.3; // Trail effect (simple, fade out) self.update = function () { self.x += Math.cos(self.angle) * self.speed; self.y += Math.sin(self.angle) * self.speed; self.alpha -= 0.018 + Math.random() * 0.008; if (self.alpha <= 0.01) { self.destroy(); } }; return self; }); // Treat class (collectible) var Treat = Container.expand(function () { var self = Container.call(this); var treat = self.attachAsset('treat', { anchorX: 0.5, anchorY: 0.5 }); // Add soft shadow for treat self.shadow = self.attachAsset('treat', { anchorX: 0.5, anchorY: 0.5, x: 10, y: 18 }); self.shadow.alpha = 0.18; self.shadow.tint = 0x000000; self.addChildAt(self.shadow, 0); // For collision self.getCollisionBounds = function () { return { x: self.x - treat.width / 2, y: self.y - treat.height / 2, width: treat.width, height: treat.height }; }; // Speed will be set on spawn self.speed = 0; self.update = function () { self.x -= self.speed; }; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ // No title, no description // Always backgroundColor is black backgroundColor: 0x000000 }); /**** * Game Code ****/ // --- Main Menu Overlay --- // UFO asset var mainMenuOverlay = new Container(); mainMenuOverlay.visible = true; // Hide in-game UI when menu is visible if (typeof scoreTxt !== "undefined" && scoreTxt !== null) scoreTxt.visible = false; if (typeof pauseBtnBg !== "undefined" && pauseBtnBg !== null) pauseBtnBg.visible = false; if (typeof pauseBtnText !== "undefined" && pauseBtnText !== null) pauseBtnText.visible = false; // Ensure backgroundPlanets is always defined before menu background is created if (typeof backgroundPlanets === "undefined" || !backgroundPlanets) backgroundPlanets = []; // Take a screenshot of the game area for menu background (simulate by rendering planets and Nyan Cat in background) function createMenuBackground() { // Remove all children from overlay while (mainMenuOverlay.children.length > 0) mainMenuOverlay.removeChildAt(0); // Add background planets (simulate by copying their positions) for (var i = 0; i < backgroundPlanets.length; i++) { var p = backgroundPlanets[i]; var planet = LK.getAsset(p.assetId || p._assetId || p.id || 'planetBlue', { anchorX: 0.5, anchorY: 0.5 }); planet.x = p.x; planet.y = p.y; planet.scaleX = planet.scaleY = p.scaleX || 1; planet.alpha = p.alpha || 0.18; mainMenuOverlay.addChild(planet); } // Add Nyan Cat in the center (large, faded) var menuCat = LK.getAsset('nyanCat', { anchorX: 0.5, anchorY: 0.5 }); menuCat.x = 2048; menuCat.y = 1200; menuCat.scaleX = menuCat.scaleY = 2.2; menuCat.alpha = 0.18; mainMenuOverlay.addChild(menuCat); } // Game Title var titleText = new Text2('NYAN CAT SPACE RUN', { size: 220, fill: "#fff", font: "Impact, Arial Black, Tahoma" }); titleText.anchor.set(0.5, 0.5); titleText.x = 2048; titleText.y = 420; mainMenuOverlay.addChild(titleText); // Play Button var playBtnBg = LK.getAsset('planetYellow', { anchorX: 0.5, anchorY: 0.5 }); playBtnBg.x = 2048; playBtnBg.y = 1200 + 420; playBtnBg.scaleX = playBtnBg.scaleY = 2.2; mainMenuOverlay.addChild(playBtnBg); var playBtnText = new Text2('OYNA', { size: 180, fill: "#222" }); playBtnText.anchor.set(0.5, 0.5); playBtnText.x = 2048; playBtnText.y = 1200 + 420; mainMenuOverlay.addChild(playBtnText); // Play button interaction mainMenuOverlay.down = function (x, y, obj) { // Check if touch is inside play button var dx = x - playBtnBg.x; var dy = y - playBtnBg.y; var r = playBtnBg.width * playBtnBg.scaleX * 0.5; if (dx * dx + dy * dy < r * r) { // Hide menu, start game mainMenuOverlay.visible = false; game.paused = false; // Show in-game UI when menu is hidden scoreTxt.visible = true; pauseBtnBg.visible = true; pauseBtnText.visible = true; // Make sure in-game UI is visible and up to date scoreTxt.visible = true; pauseBtnBg.visible = true; pauseBtnText.visible = true; // Reset game state LK.setScore(0); scoreTxt.setText('0'); for (var i = 0; i < obstacles.length; i++) obstacles[i].destroy(); obstacles = []; for (var j = 0; j < treats.length; j++) treats[j].destroy(); treats = []; nyanCat.x = 3840 * 0.25; nyanCat.y = 2160 * 0.6; nyanCatBaseY = nyanCat.y; speed = baseSpeed; spawnInterval = 70; treatInterval = 110; dragNode = null; lastHit = false; // Resume music LK.playMusic('nyanMusic'); } }; mainMenuOverlay.move = function (x, y, obj) {}; mainMenuOverlay.up = function (x, y, obj) {}; // Add overlay to GUI (centered, covers all) LK.gui.center.addChild(mainMenuOverlay); // Show menu at start game.paused = true; createMenuBackground(); // Animate planets in menu LK.on('tick', function () { if (mainMenuOverlay.visible) { // Animate title titleText.y = 420 + Math.sin(LK.ticks * 0.06) * 24; titleText.scaleX = titleText.scaleY = 1.0 + Math.sin(LK.ticks * 0.09) * 0.04; // Animate play button playBtnBg.scaleX = playBtnBg.scaleY = 2.2 + Math.sin(LK.ticks * 0.13) * 0.13; playBtnText.scaleX = playBtnText.scaleY = 1.0 + Math.sin(LK.ticks * 0.13) * 0.04; } }); // Animate background planets (subtle drifting and glow, and spawn new ones as needed) var backgroundPlanets = []; // --- Drifting Planets for Extra Parallax --- if (!game.backgroundDriftPlanets) game.backgroundDriftPlanets = []; // Spawn drifting planets if needed if (game.backgroundDriftPlanets.length < 3 && Math.random() < 0.04) { var driftPlanetTypes = ['planetBlue', 'planetGreen', 'planetPurple', 'planetRed', 'planetYellow']; var driftId = driftPlanetTypes[Math.floor(Math.random() * driftPlanetTypes.length)]; var driftScale = 0.7 + Math.random() * 0.7; var driftAlpha = 0.10 + Math.random() * 0.10; var driftSpeed = 0.18 + Math.random() * 0.18; var driftY = 200 + Math.random() * (GAME_BOTTOM - 400); var driftPlanet = LK.getAsset(driftId, { anchorX: 0.5, anchorY: 0.5 }); driftPlanet.x = GAME_RIGHT + 600 + Math.random() * 400; driftPlanet.y = driftY; driftPlanet.scaleX = driftPlanet.scaleY = driftScale; driftPlanet.alpha = driftAlpha; driftPlanet._speed = driftSpeed; driftPlanet._drift = 0.03 + Math.random() * 0.07; driftPlanet._driftPhase = Math.random() * Math.PI * 2; game.backgroundDriftPlanets.push(driftPlanet); game.addChildAt(driftPlanet, 0); } // Animate drifting planets for (var dp = game.backgroundDriftPlanets.length - 1; dp >= 0; dp--) { var driftPlanet = game.backgroundDriftPlanets[dp]; driftPlanet.x -= driftPlanet._speed; driftPlanet._driftPhase += driftPlanet._drift; driftPlanet.y += Math.sin(driftPlanet._driftPhase) * 1.2; // Subtle alpha pulsing driftPlanet.alpha = Math.abs(Math.sin(LK.ticks * 0.007 + dp)) * 0.06 + 0.10; // Remove if off screen if (driftPlanet.x < -600) { if (driftPlanet.destroy) driftPlanet.destroy(); game.backgroundDriftPlanets.splice(dp, 1); } } // Sparkle and nebula arrays for lively background if (!game.backgroundSparkles) game.backgroundSparkles = []; if (!game.backgroundNebulas) game.backgroundNebulas = []; if (!game.backgroundAuroras) game.backgroundAuroras = []; // --- Add more planets, flying UFOs, and large moving asteroids to the background --- if (!game.backgroundUFOs) game.backgroundUFOs = []; if (!game.backgroundAsteroids) game.backgroundAsteroids = []; // --- Animate Planets --- for (var i = backgroundPlanets.length - 1; i >= 0; i--) { var p = backgroundPlanets[i]; // Parallax horizontal movement for planets (move left, speed up with game speed) // Make background move faster/slower based on Nyan Cat's movement (if being dragged) var parallaxSpeed = (0.7 + speed * 0.18) * (1 + p.drift * 2); if (dragNode === nyanCat && typeof nyanCat.lastX !== "undefined") { // If Nyan Cat is being dragged, adjust parallax based on delta X var deltaX = nyanCat.x - nyanCat.lastX; // Planets move opposite to Nyan Cat's movement for parallax parallaxSpeed += -deltaX * (0.08 + p.drift * 0.12); } p.x -= parallaxSpeed; // If planet is off screen to the left, remove and spawn a new one at right if (p.x < -500) { p.destroy(); backgroundPlanets.splice(i, 1); // Randomly pick a planet type var planetTypes = ['planetBlue', 'planetGreen', 'planetPurple', 'planetRed', 'planetYellow']; var newId = planetTypes[Math.floor(Math.random() * planetTypes.length)]; var newScale = 0.8 + Math.random() * 0.8; var newAlpha = 0.12 + Math.random() * 0.13; var newDrift = 0.04 + Math.random() * 0.08; var newDriftMag = 18 + Math.random() * 30; var newY = 300 + Math.random() * (GAME_BOTTOM - 600); var newPlanet = LK.getAsset(newId, { anchorX: 0.5, anchorY: 0.5 }); newPlanet.x = GAME_RIGHT + 500 + Math.random() * 400; newPlanet.y = newY; newPlanet.scaleX = newPlanet.scaleY = newScale; newPlanet.alpha = newAlpha; newPlanet.drift = newDrift; newPlanet.driftMag = newDriftMag; backgroundPlanets.push(newPlanet); game.addChildAt(newPlanet, 0); continue; } // Subtle drifting p.x += Math.sin(LK.ticks * p.drift + i) * 0.2; p.y += Math.cos(LK.ticks * p.drift + i) * 0.2; // Subtle alpha pulsing for glow p.alpha = Math.abs(Math.sin(LK.ticks * 0.008 + i)) * 0.08 + 0.13 + p.drift * 0.7; // Twinkle effect: scale planets up/down slightly for more life var twinkle = 1 + Math.sin(LK.ticks * 0.04 + i * 1.7) * 0.018; p.scaleX = p.scaleY = (p.scaleX || 1) * twinkle; } // --- Flying UFOs (background) --- if (game.backgroundUFOs.length < 2 && Math.random() < 0.04) { var ufo = LK.getAsset('ufo', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.7 + Math.random() * 0.5, scaleY: 0.7 + Math.random() * 0.5 }); ufo.x = GAME_RIGHT + 300 + Math.random() * 400; ufo.y = 200 + Math.random() * (GAME_BOTTOM - 400); ufo.alpha = 0.7 + Math.random() * 0.2; ufo._speed = 9 + Math.random() * 4; ufo._drift = 0.04 + Math.random() * 0.09; ufo._driftPhase = Math.random() * Math.PI * 2; // Add a glow under the UFO for effect ufo._glow = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.38 + Math.random() * 0.18, scaleY: 0.18 + Math.random() * 0.12 }); ufo._glow.x = 0; ufo._glow.y = ufo.height * 0.22; ufo._glow.alpha = 0.18; ufo._glow.tint = 0x4a90e2; ufo.addChildAt(ufo._glow, 0); game.backgroundUFOs.push(ufo); game.addChild(ufo); } // --- Animated Satellites (background) --- if (!game.backgroundSatellites) game.backgroundSatellites = []; if (game.backgroundSatellites.length < 2 && Math.random() < 0.03) { // Use 'rainbow' asset as a placeholder for a satellite body, with a star as a solar panel var sat = LK.getAsset('rainbow', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.5 + Math.random() * 0.4, scaleY: 0.18 + Math.random() * 0.12 }); sat.x = GAME_RIGHT + 200 + Math.random() * 600; sat.y = 200 + Math.random() * (GAME_BOTTOM - 400); sat.alpha = 0.19 + Math.random() * 0.13; sat.tint = 0x4a90e2 + Math.floor(Math.random() * 0x222222); // blueish sat._speed = 6 + Math.random() * 3; sat._drift = 0.03 + Math.random() * 0.07; sat._driftPhase = Math.random() * Math.PI * 2; sat._rotSpeed = 0.01 + Math.random() * 0.02; // Add solar panel (star) to each side var panelL = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.18, scaleY: 0.18 }); panelL.x = -60; panelL.y = 0; panelL.alpha = 0.18; panelL.tint = 0xf9d423; var panelR = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.18, scaleY: 0.18 }); panelR.x = 60; panelR.y = 0; panelR.alpha = 0.18; panelR.tint = 0xf9d423; sat.addChildAt(panelL, 0); sat.addChildAt(panelR, 0); game.backgroundSatellites.push(sat); game.addChild(sat); } // Animate satellites if (game.backgroundSatellites) { for (var s = game.backgroundSatellites.length - 1; s >= 0; s--) { var sat = game.backgroundSatellites[s]; sat.x -= sat._speed; sat._driftPhase += sat._drift; sat.y += Math.sin(sat._driftPhase) * 1.2; sat.rotation = (sat.rotation || 0) + sat._rotSpeed; // Remove if off screen if (sat.x < -400) { if (sat.destroy) sat.destroy(); game.backgroundSatellites.splice(s, 1); } } } // Animate UFOs for (var u = game.backgroundUFOs.length - 1; u >= 0; u--) { var ufo = game.backgroundUFOs[u]; ufo.x -= ufo._speed; ufo._driftPhase += ufo._drift; ufo.y += Math.sin(ufo._driftPhase) * 1.2; ufo._glow.alpha = 0.13 + Math.abs(Math.sin(LK.ticks * 0.09 + u)) * 0.13; // Remove if off screen if (ufo.x < -400) { if (ufo.destroy) ufo.destroy(); game.backgroundUFOs.splice(u, 1); } } // --- Large Asteroids (background) --- if (game.backgroundAsteroids.length < 2 && Math.random() < 0.03) { // Use 'planetRed' or 'planetPurple' as a placeholder for big asteroid, squashed and tinted var asteroidTypes = ['planetRed', 'planetPurple']; var asteroidId = asteroidTypes[Math.floor(Math.random() * asteroidTypes.length)]; var asteroid = LK.getAsset(asteroidId, { anchorX: 0.5, anchorY: 0.5, scaleX: 0.7 + Math.random() * 0.7, scaleY: 0.38 + Math.random() * 0.22 }); asteroid.x = GAME_RIGHT + 600 + Math.random() * 400; asteroid.y = 200 + Math.random() * (GAME_BOTTOM - 400); asteroid.alpha = 0.19 + Math.random() * 0.13; asteroid.tint = 0x888888 + Math.floor(Math.random() * 0x222222); // grayish asteroid._speed = 10 + Math.random() * 6; asteroid._drift = 0.03 + Math.random() * 0.07; asteroid._driftPhase = Math.random() * Math.PI * 2; asteroid._rotSpeed = 0.01 + Math.random() * 0.02; game.backgroundAsteroids.push(asteroid); game.addChild(asteroid); } // --- Space Debris (background) --- if (!game.backgroundDebris) game.backgroundDebris = []; if (game.backgroundDebris.length < 3 && Math.random() < 0.04) { // Use 'rainbow' or 'planetYellow' as placeholder for debris var debrisTypes = ['rainbow', 'planetYellow']; var debrisId = debrisTypes[Math.floor(Math.random() * debrisTypes.length)]; var debris = LK.getAsset(debrisId, { anchorX: 0.5, anchorY: 0.5, scaleX: 0.18 + Math.random() * 0.22, scaleY: 0.18 + Math.random() * 0.22 }); debris.x = GAME_RIGHT + 200 + Math.random() * 800; debris.y = 200 + Math.random() * (GAME_BOTTOM - 400); debris.alpha = 0.13 + Math.random() * 0.13; debris.tint = 0x888888 + Math.floor(Math.random() * 0x222222); debris._speed = 8 + Math.random() * 4; debris._drift = 0.04 + Math.random() * 0.09; debris._driftPhase = Math.random() * Math.PI * 2; debris._rotSpeed = 0.02 + Math.random() * 0.03; game.backgroundDebris.push(debris); game.addChild(debris); } // Animate debris if (game.backgroundDebris) { for (var d = game.backgroundDebris.length - 1; d >= 0; d--) { var debris = game.backgroundDebris[d]; debris.x -= debris._speed; debris._driftPhase += debris._drift; debris.y += Math.sin(debris._driftPhase) * 1.2; debris.rotation = (debris.rotation || 0) + debris._rotSpeed; // Remove if off screen if (debris.x < -400) { if (debris.destroy) debris.destroy(); game.backgroundDebris.splice(d, 1); } } } // Animate asteroids for (var a = game.backgroundAsteroids.length - 1; a >= 0; a--) { var asteroid = game.backgroundAsteroids[a]; asteroid.x -= asteroid._speed; asteroid._driftPhase += asteroid._drift; asteroid.y += Math.sin(asteroid._driftPhase) * 2.2; asteroid.rotation = (asteroid.rotation || 0) + asteroid._rotSpeed; // Remove if off screen if (asteroid.x < -600) { if (asteroid.destroy) asteroid.destroy(); game.backgroundAsteroids.splice(a, 1); } } // --- Sparkle background effect --- if (game.backgroundSparkles.length < 32 && Math.random() < 0.18) { // Add a new sparkle at random position, random size var sparkle = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.13 + Math.random() * 0.11, scaleY: 0.13 + Math.random() * 0.11 }); sparkle.x = Math.random() * (GAME_RIGHT + 400) - 200; sparkle.y = Math.random() * (GAME_BOTTOM + 400) - 200; sparkle.alpha = 0.13 + Math.random() * 0.13; sparkle._twinklePhase = Math.random() * Math.PI * 2; sparkle._twinkleSpeed = 0.04 + Math.random() * 0.07; sparkle._baseAlpha = sparkle.alpha; sparkle._baseScale = sparkle.scaleX; game.backgroundSparkles.push(sparkle); game.addChildAt(sparkle, 0); } // --- Parallax dust particles for extra movement --- if (!game.backgroundDust) game.backgroundDust = []; if (game.backgroundDust.length < 18 && Math.random() < 0.13) { var dust = LK.getAsset('cloud', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.18 + Math.random() * 0.22, scaleY: 0.18 + Math.random() * 0.22 }); dust.x = Math.random() * (GAME_RIGHT + 400) - 200; dust.y = Math.random() * (GAME_BOTTOM + 400) - 200; dust.alpha = 0.06 + Math.random() * 0.07; dust._speed = 0.13 + Math.random() * 0.09; dust._drift = 0.04 + Math.random() * 0.09; dust._driftPhase = Math.random() * Math.PI * 2; game.backgroundDust.push(dust); game.addChildAt(dust, 0); } // Animate dust for (var d = game.backgroundDust.length - 1; d >= 0; d--) { var dust = game.backgroundDust[d]; dust.x -= dust._speed; dust._driftPhase += dust._drift; dust.y += Math.sin(dust._driftPhase) * 0.7; // Subtle alpha pulsing dust.alpha = Math.abs(Math.sin(LK.ticks * 0.009 + d)) * 0.03 + 0.06; // Remove if off screen if (dust.x < -400 || dust.y < -400 || dust.y > GAME_BOTTOM + 400) { if (dust.destroy) dust.destroy(); game.backgroundDust.splice(d, 1); } } // Animate sparkles for (var s = game.backgroundSparkles.length - 1; s >= 0; s--) { var sparkle = game.backgroundSparkles[s]; // Twinkle alpha and scale sparkle._twinklePhase += sparkle._twinkleSpeed; sparkle.alpha = sparkle._baseAlpha * (0.7 + 0.6 * Math.abs(Math.sin(sparkle._twinklePhase))); sparkle.scaleX = sparkle.scaleY = sparkle._baseScale * (0.9 + 0.2 * Math.abs(Math.cos(sparkle._twinklePhase * 0.7))); // Slow drift sparkle.x += Math.sin(sparkle._twinklePhase * 0.5) * 0.13; sparkle.y += Math.cos(sparkle._twinklePhase * 0.5) * 0.13; // Remove if off screen if (sparkle.x < -300 || sparkle.x > GAME_RIGHT + 300 || sparkle.y < -300 || sparkle.y > GAME_BOTTOM + 300) { if (sparkle.destroy) sparkle.destroy(); game.backgroundSparkles.splice(s, 1); } } // --- Nebula cloud effect (soft colored clouds drifting) --- if (game.backgroundNebulas.length < 5 && Math.random() < 0.04) { var nebulaColors = [0xf9d423, 0x9b59b6, 0x4a90e2, 0x7ed957, 0xe94e77]; var color = nebulaColors[Math.floor(Math.random() * nebulaColors.length)]; var nebula = LK.getAsset('cloud', { anchorX: 0.5, anchorY: 0.5, scaleX: 1.2 + Math.random() * 1.8, scaleY: 1.2 + Math.random() * 1.8 }); nebula.x = GAME_RIGHT + 400 + Math.random() * 400; nebula.y = 200 + Math.random() * (GAME_BOTTOM - 400); nebula.alpha = 0.08 + Math.random() * 0.08; nebula.tint = color; nebula._speed = 0.18 + Math.random() * 0.22; nebula._drift = 0.12 + Math.random() * 0.13; nebula._driftPhase = Math.random() * Math.PI * 2; game.backgroundNebulas.push(nebula); game.addChildAt(nebula, 0); } // Animate nebulas for (var n = game.backgroundNebulas.length - 1; n >= 0; n--) { var nebula = game.backgroundNebulas[n]; nebula.x -= nebula._speed; nebula._driftPhase += nebula._drift; nebula.y += Math.sin(nebula._driftPhase) * 0.7; // Subtle alpha pulsing nebula.alpha = Math.abs(Math.sin(LK.ticks * 0.006 + n)) * 0.04 + 0.08; // Remove if off screen if (nebula.x < -600) { if (nebula.destroy) nebula.destroy(); game.backgroundNebulas.splice(n, 1); } } // --- Aurora band effect (animated colored bands drifting horizontally) --- if (game.backgroundAuroras.length < 3 && Math.random() < 0.03) { var auroraColors = [0x7ed957, 0x4a90e2, 0xfe6cd1, 0xf9d423, 0x9b59b6]; var color = auroraColors[Math.floor(Math.random() * auroraColors.length)]; var aurora = LK.getAsset('rainbow', { anchorX: 0.5, anchorY: 0.5, scaleX: 18 + Math.random() * 6, scaleY: 0.7 + Math.random() * 0.5 }); aurora.x = GAME_RIGHT + 800 + Math.random() * 400; aurora.y = 400 + Math.random() * (GAME_BOTTOM - 800); aurora.alpha = 0.09 + Math.random() * 0.07; aurora.tint = color; aurora._speed = 0.11 + Math.random() * 0.13; aurora._wavePhase = Math.random() * Math.PI * 2; aurora._waveSpeed = 0.008 + Math.random() * 0.012; aurora._baseY = aurora.y; game.backgroundAuroras.push(aurora); game.addChildAt(aurora, 0); } // Animate auroras for (var a = game.backgroundAuroras.length - 1; a >= 0; a--) { var aurora = game.backgroundAuroras[a]; aurora.x -= aurora._speed; aurora._wavePhase += aurora._waveSpeed; aurora.y = aurora._baseY + Math.sin(aurora._wavePhase + a) * 38; // Subtle alpha pulsing aurora.alpha = Math.abs(Math.sin(LK.ticks * 0.004 + a)) * 0.05 + 0.09; // Remove if off screen if (aurora.x < -1200) { if (aurora.destroy) aurora.destroy(); game.backgroundAuroras.splice(a, 1); } } // --- Comet trail effect (fast-moving, glowing comets with fading tails) --- if (!game.backgroundComets) game.backgroundComets = []; if (game.backgroundComets.length < 4 && Math.random() < 0.04) { var comet = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: 0.22 + Math.random() * 0.18, scaleY: 0.22 + Math.random() * 0.18 }); comet.x = -200 - Math.random() * 400; comet.y = 200 + Math.random() * (GAME_BOTTOM - 400); comet.alpha = 0.19 + Math.random() * 0.13; comet._speed = 18 + Math.random() * 12; comet._angle = Math.PI * (0.01 + Math.random() * 0.08); // slight downward comet._tail = []; comet._tailColor = [0xf9d423, 0x9b59b6, 0x4a90e2, 0x7ed957, 0xe94e77][Math.floor(Math.random() * 5)]; // Add a glow for more dynamic effect comet._glow = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: comet.scaleX * 2.2, scaleY: comet.scaleY * 2.2 }); comet._glow.x = 0; comet._glow.y = 0; comet._glow.alpha = 0.13; comet._glow.tint = comet._tailColor; comet.addChildAt(comet._glow, 0); game.backgroundComets.push(comet); game.addChildAt(comet, 1); } // Animate comets and their tails for (var c = game.backgroundComets.length - 1; c >= 0; c--) { var comet = game.backgroundComets[c]; // Move comet comet.x += Math.cos(comet._angle) * comet._speed; comet.y += Math.sin(comet._angle) * comet._speed; // Fade out slightly comet.alpha -= 0.002 + Math.random() * 0.002; if (comet._glow) { comet._glow.alpha = comet.alpha * 0.5; comet._glow.scaleX = comet._glow.scaleY = comet.scaleX * (2.1 + Math.sin(LK.ticks * 0.13 + c) * 0.2); } // Store tail positions if (!comet._tail) comet._tail = []; comet._tail.unshift({ x: comet.x, y: comet.y, alpha: comet.alpha, scale: comet.scaleX }); if (comet._tail.length > 14) comet._tail.pop(); // Draw tail as faded stars for (var t = 1; t < comet._tail.length; t += 2) { var tail = comet._tail[t]; if (!tail._sprite) { tail._sprite = LK.getAsset('star', { anchorX: 0.5, anchorY: 0.5, scaleX: comet.scaleX * (1 - t * 0.06), scaleY: comet.scaleY * (1 - t * 0.06) }); tail._sprite.x = tail.x; tail._sprite.y = tail.y; tail._sprite.alpha = comet.alpha * (0.5 - t * 0.04); tail._sprite.tint = comet._tailColor; game.addChildAt(tail._sprite, 0); } else { tail._sprite.x = tail.x; tail._sprite.y = tail.y; tail._sprite.alpha = comet.alpha * (0.5 - t * 0.04); tail._sprite.scaleX = tail._sprite.scaleY = comet.scaleX * (1 - t * 0.06); } } // Remove if off screen if (comet.x > GAME_RIGHT + 400 || comet.y > GAME_BOTTOM + 400 || comet.alpha < 0.01) { // Remove tail sprites for (var t = 1; t < comet._tail.length; t += 2) { var tail = comet._tail[t]; if (tail._sprite && tail._sprite.destroy) tail._sprite.destroy(); } if (comet._glow && comet._glow.destroy) comet._glow.destroy(); if (comet.destroy) comet.destroy(); game.backgroundComets.splice(c, 1); } } function spawnBackgroundPlanets() { // Remove any existing for (var i = 0; i < backgroundPlanets.length; i++) { backgroundPlanets[i].destroy(); } backgroundPlanets = []; // Place a few planets at random positions, different depths/colors var planetDefs = [{ id: 'planetBlue', x: 900, y: 400, scale: 1.2, alpha: 0.22, drift: 0.08, driftMag: 40 }, { id: 'planetGreen', x: 3200, y: 600, scale: 1.1, alpha: 0.18, drift: 0.06, driftMag: 30 }, { id: 'planetPurple', x: 2600, y: 1700, scale: 1.4, alpha: 0.16, drift: 0.07, driftMag: 36 }, { id: 'planetRed', x: 1800, y: 1400, scale: 1.0, alpha: 0.19, drift: 0.09, driftMag: 28 }, { id: 'planetYellow', x: 3400, y: 1800, scale: 0.9, alpha: 0.13, drift: 0.05, driftMag: 22 }]; for (var i = 0; i < planetDefs.length; i++) { var def = planetDefs[i]; var planet = LK.getAsset(def.id, { anchorX: 0.5, anchorY: 0.5 }); planet.x = def.x; planet.y = def.y; planet.scaleX = planet.scaleY = def.scale; planet.alpha = def.alpha; planet.drift = def.drift; planet.driftMag = def.driftMag; backgroundPlanets.push(planet); game.addChildAt(planet, 0); // Always behind everything } } spawnBackgroundPlanets(); // Music // Sound effects // Rainbow trail // Treat (pop tart) // Obstacle (star) // Obstacle (cloud) // Nyan Cat (main character) // Game area margins var GAME_TOP = 0; var GAME_BOTTOM = 2160; var GAME_LEFT = 0; var GAME_RIGHT = 3840; // Avoid top left 100x100 for menu var SAFE_TOP = 120; // Main character var nyanCat = new NyanCat(); game.addChild(nyanCat); // Center Nyan Cat horizontally, place at 60% height nyanCat.x = 3840 * 0.25; nyanCat.y = 2160 * 0.6; var nyanCatBaseY = nyanCat.y; // --- In-Game UI Overlay --- // Score display (smaller, always visible at top center) var scoreTxt = new Text2('0', { size: 120, fill: "#fff" }); scoreTxt.anchor.set(0.5, 0); scoreTxt.x = 2048; scoreTxt.y = 20; LK.gui.top.addChild(scoreTxt); // Pause button (top right, avoid top left 100x100) var pauseBtnBg = LK.getAsset('planetPurple', { anchorX: 0.5, anchorY: 0.5 }); pauseBtnBg.x = 2048 * 2 - 180; pauseBtnBg.y = 100; pauseBtnBg.scaleX = pauseBtnBg.scaleY = 0.7; pauseBtnBg.alpha = 0.85; LK.gui.top.addChild(pauseBtnBg); var pauseBtnText = new Text2('II', { size: 90, fill: "#fff" }); pauseBtnText.anchor.set(0.5, 0.5); pauseBtnText.x = pauseBtnBg.x; pauseBtnText.y = pauseBtnBg.y; LK.gui.top.addChild(pauseBtnText); // Pause button interaction pauseBtnBg.down = function (x, y, obj) { // Pause the game and show the menu overlay if (!mainMenuOverlay.visible) { mainMenuOverlay.visible = true; game.paused = true; createMenuBackground(); LK.stopMusic(); } }; pauseBtnText.down = pauseBtnBg.down; // Arrays for obstacles and treats var obstacles = []; var treats = []; // Difficulty parameters var baseSpeed = 12; var speed = baseSpeed; var spawnInterval = 70; // ticks between spawns var treatInterval = 110; // ticks between treat spawns var minSpawnInterval = 30; var maxSpeed = 32; // Dragging var dragNode = null; // Last collision state var lastHit = false; // Play music LK.playMusic('nyanMusic'); // Helper: collision check (AABB) function isColliding(a, b) { var ab = a.getCollisionBounds(); var bb = b.getCollisionBounds(); return ab.x < bb.x + bb.width && ab.x + ab.width > bb.x && ab.y < bb.y + bb.height && ab.y + ab.height > bb.y; } // Move handler (drag Nyan Cat) function handleMove(x, y, obj) { if (dragNode) { // Clamp to game area, avoid top left 100x100 var cat = dragNode; var bounds = cat.getCollisionBounds(); var halfW = bounds.width / 2; var halfH = bounds.height / 2; var minX = GAME_LEFT + halfW; var maxX = GAME_RIGHT - halfW; var minY = Math.max(GAME_TOP + halfH, SAFE_TOP + halfH); var maxY = GAME_BOTTOM - halfH; cat.x = Math.max(minX, Math.min(maxX, x)); cat.y = Math.max(minY, Math.min(maxY, y)); } } game.move = handleMove; game.down = function (x, y, obj) { // Only allow drag if touch is on Nyan Cat var bounds = nyanCat.getCollisionBounds(); if (x >= bounds.x && x <= bounds.x + bounds.width && y >= bounds.y && y <= bounds.y + bounds.height) { dragNode = nyanCat; handleMove(x, y, obj); } }; game.up = function (x, y, obj) { dragNode = null; }; // Game update loop game.update = function () { // Only planets are used for the space background; no starfield, clouds, or other backgrounds // Animate shooting stars for lively background if (!game.shootingStars) game.shootingStars = []; // Spawn a shooting star at random intervals if (LK.ticks % 23 === 0 && Math.random() < 0.45) { var star = new ShootingStar(); // Start at random X on left, random Y in upper half star.x = Math.random() * 1200; star.y = 80 + Math.random() * 900; game.shootingStars.push(star); game.addChildAt(star, 1); // Behind main gameplay } // Update and clean up shooting stars for (var s = game.shootingStars.length - 1; s >= 0; s--) { var star = game.shootingStars[s]; if (star.destroyed || star.alpha <= 0.01 || star.x > GAME_RIGHT + 200 || star.y > GAME_BOTTOM + 200) { if (!star.destroyed) star.destroy(); game.shootingStars.splice(s, 1); continue; } star.update(); } // Increase difficulty over time if (LK.ticks % 180 === 0 && speed < maxSpeed) { speed += 1.2; spawnInterval = Math.max(minSpawnInterval, spawnInterval - 4); } // Spawn obstacles if (LK.ticks % spawnInterval === 0) { var obs = new Obstacle(); obs.speed = speed; // Random Y, avoid top 100px var asset = obs.children[0]; var minY = SAFE_TOP + asset.height / 2; var maxY = GAME_BOTTOM - asset.height / 2; obs.x = GAME_RIGHT + asset.width / 2 + 10; obs.y = Math.random() * (maxY - minY) + minY; obstacles.push(obs); game.addChild(obs); } // Spawn treats if (LK.ticks % treatInterval === 0) { var treat = new Treat(); treat.speed = speed * 0.95; var asset = treat.children[0]; var minY = SAFE_TOP + asset.height / 2; var maxY = GAME_BOTTOM - asset.height / 2; treat.x = GAME_RIGHT + asset.width / 2 + 10; treat.y = Math.random() * (maxY - minY) + minY; treats.push(treat); game.addChild(treat); } // Update obstacles for (var i = obstacles.length - 1; i >= 0; i--) { var obs = obstacles[i]; obs.update(); // Twinkle and pulse for obstacles (clouds/stars) if (obs.children && obs.children.length > 1) { var obsSprite = obs.children[1]; obsSprite.rotation = Math.sin(LK.ticks * 0.09 + i) * 0.13; obsSprite.scaleX = 1 + Math.sin(LK.ticks * 0.15 + i) * 0.09; obsSprite.scaleY = 1 + Math.cos(LK.ticks * 0.13 + i) * 0.09; } // Remove if off screen if (obs.x < -300) { obs.destroy(); obstacles.splice(i, 1); continue; } // Collision with Nyan Cat var hit = isColliding(obs, nyanCat); if (hit && !lastHit) { // Flash, play sound, game over nyanCat.flash(); LK.getSound('hit').play(); LK.effects.flashScreen(0xff0000, 800); LK.showGameOver(); lastHit = true; break; // Stop further checks } } // Update treats for (var j = treats.length - 1; j >= 0; j--) { var treat = treats[j]; treat.update(); // Twinkle effect for treats (make them pulse and rotate for more life) if (treat.children && treat.children.length > 1) { var treatSprite = treat.children[1]; treatSprite.rotation = Math.sin(LK.ticks * 0.13 + j) * 0.18; treatSprite.scaleX = 1 + Math.sin(LK.ticks * 0.19 + j) * 0.13; treatSprite.scaleY = 1 + Math.cos(LK.ticks * 0.17 + j) * 0.13; } // Remove if off screen if (treat.x < -200) { treat.destroy(); treats.splice(j, 1); continue; } // Collision with Nyan Cat if (isColliding(treat, nyanCat)) { LK.setScore(LK.getScore() + 1); scoreTxt.setText(LK.getScore()); LK.getSound('collect').play(); // Animate treat tween(treat, { scaleX: 2.1, scaleY: 2.1, alpha: 0 }, { duration: 220, ease: "outBack", onFinish: function onFinish() { treat.destroy(); } }); treats.splice(j, 1); continue; } } // Track Nyan Cat's lastX for parallax if (typeof nyanCat.lastX === "undefined") nyanCat.lastX = nyanCat.x; // Nyan Cat idle bobbing and lively animation if (!dragNode) { nyanCat.y = nyanCatBaseY + Math.sin(LK.ticks * 0.08) * 22; // Subtle rotation and scale for lively effect if (nyanCat.children && nyanCat.children.length > 1) { var catSprite = nyanCat.children[1]; catSprite.rotation = Math.sin(LK.ticks * 0.07) * 0.08; catSprite.scaleX = 1 + Math.sin(LK.ticks * 0.11) * 0.04; catSprite.scaleY = 1 + Math.cos(LK.ticks * 0.13) * 0.04; } // Subtle color pulsing for rainbow trail if (nyanCat.children && nyanCat.children.length > 0) { var rainbowSprite = nyanCat.children[0]; var baseTint = 0xffe0fa; var pulse = Math.floor(0x20 * (1 + Math.sin(LK.ticks * 0.09))); // Animate tint between pink and yellowish rainbowSprite.tint = 0xffe0fa + (pulse << 8); } } // Update lastX for next frame nyanCat.lastX = nyanCat.x; // Reset lastHit if not colliding if (!obstacles.some(function (obs) { return isColliding(obs, nyanCat); })) { lastHit = false; } }; // Reset score and all game state on game start LK.setScore(0); scoreTxt.setText('0'); // Remove all obstacles and treats from game for (var i = 0; i < obstacles.length; i++) { obstacles[i].destroy(); } obstacles = []; for (var j = 0; j < treats.length; j++) { treats[j].destroy(); } treats = []; // Reset Nyan Cat position and base Y nyanCat.x = 3840 * 0.25; nyanCat.y = 2160 * 0.6; nyanCatBaseY = nyanCat.y; // Reset difficulty speed = baseSpeed; spawnInterval = 70; treatInterval = 110; // Reset drag and collision state dragNode = null; lastHit = false;
/****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
/****
* Classes
****/
// Nyan Cat class
var NyanCat = Container.expand(function () {
var self = Container.call(this);
// Rainbow trail (visual only, not collidable)
var rainbow = self.attachAsset('rainbow', {
anchorX: 1,
anchorY: 0.5,
x: -90,
y: 0,
scaleY: 1.2
});
// Add a soft highlight to rainbow for polish
rainbow.alpha = 0.92;
rainbow.tint = 0xffe0fa;
// Add additional rainbow bands for a lively animated effect
self.rainbowBands = [];
var rainbowColors = [0xfe6cd1, 0xf9d423, 0x7ed957, 0x4a90e2, 0x9b59b6, 0xffffff];
for (var i = 0; i < rainbowColors.length; i++) {
var band = self.attachAsset('rainbow', {
anchorX: 1,
anchorY: 0.5,
x: -90,
y: (i - 2.5) * 18,
// stack vertically
scaleY: 0.18,
scaleX: 1.0
});
band.alpha = 0.82;
band.tint = rainbowColors[i];
self.addChildAt(band, i);
self.rainbowBands.push(band);
}
// Nyan Cat sprite
var cat = self.attachAsset('nyanCat', {
anchorX: 0.5,
anchorY: 0.5,
x: 0,
y: 0
});
// Add a soft shadow to Nyan Cat for depth
cat.alpha = 1;
cat.tint = 0xffffff;
self.catShadow = LK.getAsset('nyanCat', {
anchorX: 0.5,
anchorY: 0.5,
x: 8,
y: 18
});
self.catShadow.alpha = 0.22;
self.catShadow.tint = 0x000000;
self.addChildAt(self.catShadow, 0);
// For collision, use the cat's bounds (not rainbow)
self.getCollisionBounds = function () {
return {
x: self.x - cat.width / 2,
y: self.y - cat.height / 2,
width: cat.width,
height: cat.height
};
};
// Flash effect on hit
self.flash = function () {
tween(cat, {
alpha: 0.3
}, {
duration: 80,
onFinish: function onFinish() {
tween(cat, {
alpha: 1
}, {
duration: 120
});
}
});
};
// Rainbow parallax movement for quality polish
self.update = function () {
// Rainbow trail parallax: slight horizontal movement for visual polish
rainbow.x = -90 + Math.sin(LK.ticks * 0.12) * 12;
// Animate rainbow bands for a lively, wavy effect
for (var i = 0; i < self.rainbowBands.length; i++) {
var band = self.rainbowBands[i];
// Wavy movement: each band has a phase offset
band.x = -90 + Math.sin(LK.ticks * 0.12 + i * 0.5) * (12 + i * 2);
band.y = (i - 2.5) * 18 + Math.sin(LK.ticks * 0.18 + i * 0.7) * 8;
// Animate alpha for shimmer
band.alpha = 0.7 + 0.25 * Math.abs(Math.sin(LK.ticks * 0.09 + i));
// Animate scale for a breathing effect
band.scaleX = 1.0 + 0.13 * Math.sin(LK.ticks * 0.11 + i * 0.8);
}
};
return self;
});
// Obstacle class (cloud or star)
var Obstacle = Container.expand(function () {
var self = Container.call(this);
// Randomly choose cloud or star
var isStar = Math.random() < 0.4;
var assetId = isStar ? 'star' : 'cloud';
var asset = self.attachAsset(assetId, {
anchorX: 0.5,
anchorY: 0.5
});
// Add soft shadow for depth
self.shadow = self.attachAsset(assetId, {
anchorX: 0.5,
anchorY: 0.5,
x: 10,
y: 18
});
self.shadow.alpha = 0.18;
self.shadow.tint = 0x000000;
self.addChildAt(self.shadow, 0);
self.isStar = isStar;
// For collision
self.getCollisionBounds = function () {
return {
x: self.x - asset.width / 2,
y: self.y - asset.height / 2,
width: asset.width,
height: asset.height
};
};
// Speed will be set on spawn
self.speed = 0;
self.update = function () {
self.x -= self.speed;
};
return self;
});
// Shooting Star class for lively background
var ShootingStar = Container.expand(function () {
var self = Container.call(this);
// Use the 'star' asset, small and bright
var star = self.attachAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.32,
scaleY: 0.32
});
self.star = star;
// Randomize speed and angle
self.speed = 18 + Math.random() * 10; //{U} // Reduced speed for slower falling stars
self.angle = Math.PI * (0.18 + Math.random() * 0.12); // ~10deg downward
self.alpha = 0.7 + Math.random() * 0.3;
// Trail effect (simple, fade out)
self.update = function () {
self.x += Math.cos(self.angle) * self.speed;
self.y += Math.sin(self.angle) * self.speed;
self.alpha -= 0.018 + Math.random() * 0.008;
if (self.alpha <= 0.01) {
self.destroy();
}
};
return self;
});
// Treat class (collectible)
var Treat = Container.expand(function () {
var self = Container.call(this);
var treat = self.attachAsset('treat', {
anchorX: 0.5,
anchorY: 0.5
});
// Add soft shadow for treat
self.shadow = self.attachAsset('treat', {
anchorX: 0.5,
anchorY: 0.5,
x: 10,
y: 18
});
self.shadow.alpha = 0.18;
self.shadow.tint = 0x000000;
self.addChildAt(self.shadow, 0);
// For collision
self.getCollisionBounds = function () {
return {
x: self.x - treat.width / 2,
y: self.y - treat.height / 2,
width: treat.width,
height: treat.height
};
};
// Speed will be set on spawn
self.speed = 0;
self.update = function () {
self.x -= self.speed;
};
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
// No title, no description
// Always backgroundColor is black
backgroundColor: 0x000000
});
/****
* Game Code
****/
// --- Main Menu Overlay ---
// UFO asset
var mainMenuOverlay = new Container();
mainMenuOverlay.visible = true;
// Hide in-game UI when menu is visible
if (typeof scoreTxt !== "undefined" && scoreTxt !== null) scoreTxt.visible = false;
if (typeof pauseBtnBg !== "undefined" && pauseBtnBg !== null) pauseBtnBg.visible = false;
if (typeof pauseBtnText !== "undefined" && pauseBtnText !== null) pauseBtnText.visible = false;
// Ensure backgroundPlanets is always defined before menu background is created
if (typeof backgroundPlanets === "undefined" || !backgroundPlanets) backgroundPlanets = [];
// Take a screenshot of the game area for menu background (simulate by rendering planets and Nyan Cat in background)
function createMenuBackground() {
// Remove all children from overlay
while (mainMenuOverlay.children.length > 0) mainMenuOverlay.removeChildAt(0);
// Add background planets (simulate by copying their positions)
for (var i = 0; i < backgroundPlanets.length; i++) {
var p = backgroundPlanets[i];
var planet = LK.getAsset(p.assetId || p._assetId || p.id || 'planetBlue', {
anchorX: 0.5,
anchorY: 0.5
});
planet.x = p.x;
planet.y = p.y;
planet.scaleX = planet.scaleY = p.scaleX || 1;
planet.alpha = p.alpha || 0.18;
mainMenuOverlay.addChild(planet);
}
// Add Nyan Cat in the center (large, faded)
var menuCat = LK.getAsset('nyanCat', {
anchorX: 0.5,
anchorY: 0.5
});
menuCat.x = 2048;
menuCat.y = 1200;
menuCat.scaleX = menuCat.scaleY = 2.2;
menuCat.alpha = 0.18;
mainMenuOverlay.addChild(menuCat);
}
// Game Title
var titleText = new Text2('NYAN CAT SPACE RUN', {
size: 220,
fill: "#fff",
font: "Impact, Arial Black, Tahoma"
});
titleText.anchor.set(0.5, 0.5);
titleText.x = 2048;
titleText.y = 420;
mainMenuOverlay.addChild(titleText);
// Play Button
var playBtnBg = LK.getAsset('planetYellow', {
anchorX: 0.5,
anchorY: 0.5
});
playBtnBg.x = 2048;
playBtnBg.y = 1200 + 420;
playBtnBg.scaleX = playBtnBg.scaleY = 2.2;
mainMenuOverlay.addChild(playBtnBg);
var playBtnText = new Text2('OYNA', {
size: 180,
fill: "#222"
});
playBtnText.anchor.set(0.5, 0.5);
playBtnText.x = 2048;
playBtnText.y = 1200 + 420;
mainMenuOverlay.addChild(playBtnText);
// Play button interaction
mainMenuOverlay.down = function (x, y, obj) {
// Check if touch is inside play button
var dx = x - playBtnBg.x;
var dy = y - playBtnBg.y;
var r = playBtnBg.width * playBtnBg.scaleX * 0.5;
if (dx * dx + dy * dy < r * r) {
// Hide menu, start game
mainMenuOverlay.visible = false;
game.paused = false;
// Show in-game UI when menu is hidden
scoreTxt.visible = true;
pauseBtnBg.visible = true;
pauseBtnText.visible = true;
// Make sure in-game UI is visible and up to date
scoreTxt.visible = true;
pauseBtnBg.visible = true;
pauseBtnText.visible = true;
// Reset game state
LK.setScore(0);
scoreTxt.setText('0');
for (var i = 0; i < obstacles.length; i++) obstacles[i].destroy();
obstacles = [];
for (var j = 0; j < treats.length; j++) treats[j].destroy();
treats = [];
nyanCat.x = 3840 * 0.25;
nyanCat.y = 2160 * 0.6;
nyanCatBaseY = nyanCat.y;
speed = baseSpeed;
spawnInterval = 70;
treatInterval = 110;
dragNode = null;
lastHit = false;
// Resume music
LK.playMusic('nyanMusic');
}
};
mainMenuOverlay.move = function (x, y, obj) {};
mainMenuOverlay.up = function (x, y, obj) {};
// Add overlay to GUI (centered, covers all)
LK.gui.center.addChild(mainMenuOverlay);
// Show menu at start
game.paused = true;
createMenuBackground();
// Animate planets in menu
LK.on('tick', function () {
if (mainMenuOverlay.visible) {
// Animate title
titleText.y = 420 + Math.sin(LK.ticks * 0.06) * 24;
titleText.scaleX = titleText.scaleY = 1.0 + Math.sin(LK.ticks * 0.09) * 0.04;
// Animate play button
playBtnBg.scaleX = playBtnBg.scaleY = 2.2 + Math.sin(LK.ticks * 0.13) * 0.13;
playBtnText.scaleX = playBtnText.scaleY = 1.0 + Math.sin(LK.ticks * 0.13) * 0.04;
}
});
// Animate background planets (subtle drifting and glow, and spawn new ones as needed)
var backgroundPlanets = [];
// --- Drifting Planets for Extra Parallax ---
if (!game.backgroundDriftPlanets) game.backgroundDriftPlanets = [];
// Spawn drifting planets if needed
if (game.backgroundDriftPlanets.length < 3 && Math.random() < 0.04) {
var driftPlanetTypes = ['planetBlue', 'planetGreen', 'planetPurple', 'planetRed', 'planetYellow'];
var driftId = driftPlanetTypes[Math.floor(Math.random() * driftPlanetTypes.length)];
var driftScale = 0.7 + Math.random() * 0.7;
var driftAlpha = 0.10 + Math.random() * 0.10;
var driftSpeed = 0.18 + Math.random() * 0.18;
var driftY = 200 + Math.random() * (GAME_BOTTOM - 400);
var driftPlanet = LK.getAsset(driftId, {
anchorX: 0.5,
anchorY: 0.5
});
driftPlanet.x = GAME_RIGHT + 600 + Math.random() * 400;
driftPlanet.y = driftY;
driftPlanet.scaleX = driftPlanet.scaleY = driftScale;
driftPlanet.alpha = driftAlpha;
driftPlanet._speed = driftSpeed;
driftPlanet._drift = 0.03 + Math.random() * 0.07;
driftPlanet._driftPhase = Math.random() * Math.PI * 2;
game.backgroundDriftPlanets.push(driftPlanet);
game.addChildAt(driftPlanet, 0);
}
// Animate drifting planets
for (var dp = game.backgroundDriftPlanets.length - 1; dp >= 0; dp--) {
var driftPlanet = game.backgroundDriftPlanets[dp];
driftPlanet.x -= driftPlanet._speed;
driftPlanet._driftPhase += driftPlanet._drift;
driftPlanet.y += Math.sin(driftPlanet._driftPhase) * 1.2;
// Subtle alpha pulsing
driftPlanet.alpha = Math.abs(Math.sin(LK.ticks * 0.007 + dp)) * 0.06 + 0.10;
// Remove if off screen
if (driftPlanet.x < -600) {
if (driftPlanet.destroy) driftPlanet.destroy();
game.backgroundDriftPlanets.splice(dp, 1);
}
}
// Sparkle and nebula arrays for lively background
if (!game.backgroundSparkles) game.backgroundSparkles = [];
if (!game.backgroundNebulas) game.backgroundNebulas = [];
if (!game.backgroundAuroras) game.backgroundAuroras = [];
// --- Add more planets, flying UFOs, and large moving asteroids to the background ---
if (!game.backgroundUFOs) game.backgroundUFOs = [];
if (!game.backgroundAsteroids) game.backgroundAsteroids = [];
// --- Animate Planets ---
for (var i = backgroundPlanets.length - 1; i >= 0; i--) {
var p = backgroundPlanets[i];
// Parallax horizontal movement for planets (move left, speed up with game speed)
// Make background move faster/slower based on Nyan Cat's movement (if being dragged)
var parallaxSpeed = (0.7 + speed * 0.18) * (1 + p.drift * 2);
if (dragNode === nyanCat && typeof nyanCat.lastX !== "undefined") {
// If Nyan Cat is being dragged, adjust parallax based on delta X
var deltaX = nyanCat.x - nyanCat.lastX;
// Planets move opposite to Nyan Cat's movement for parallax
parallaxSpeed += -deltaX * (0.08 + p.drift * 0.12);
}
p.x -= parallaxSpeed;
// If planet is off screen to the left, remove and spawn a new one at right
if (p.x < -500) {
p.destroy();
backgroundPlanets.splice(i, 1);
// Randomly pick a planet type
var planetTypes = ['planetBlue', 'planetGreen', 'planetPurple', 'planetRed', 'planetYellow'];
var newId = planetTypes[Math.floor(Math.random() * planetTypes.length)];
var newScale = 0.8 + Math.random() * 0.8;
var newAlpha = 0.12 + Math.random() * 0.13;
var newDrift = 0.04 + Math.random() * 0.08;
var newDriftMag = 18 + Math.random() * 30;
var newY = 300 + Math.random() * (GAME_BOTTOM - 600);
var newPlanet = LK.getAsset(newId, {
anchorX: 0.5,
anchorY: 0.5
});
newPlanet.x = GAME_RIGHT + 500 + Math.random() * 400;
newPlanet.y = newY;
newPlanet.scaleX = newPlanet.scaleY = newScale;
newPlanet.alpha = newAlpha;
newPlanet.drift = newDrift;
newPlanet.driftMag = newDriftMag;
backgroundPlanets.push(newPlanet);
game.addChildAt(newPlanet, 0);
continue;
}
// Subtle drifting
p.x += Math.sin(LK.ticks * p.drift + i) * 0.2;
p.y += Math.cos(LK.ticks * p.drift + i) * 0.2;
// Subtle alpha pulsing for glow
p.alpha = Math.abs(Math.sin(LK.ticks * 0.008 + i)) * 0.08 + 0.13 + p.drift * 0.7;
// Twinkle effect: scale planets up/down slightly for more life
var twinkle = 1 + Math.sin(LK.ticks * 0.04 + i * 1.7) * 0.018;
p.scaleX = p.scaleY = (p.scaleX || 1) * twinkle;
}
// --- Flying UFOs (background) ---
if (game.backgroundUFOs.length < 2 && Math.random() < 0.04) {
var ufo = LK.getAsset('ufo', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.7 + Math.random() * 0.5,
scaleY: 0.7 + Math.random() * 0.5
});
ufo.x = GAME_RIGHT + 300 + Math.random() * 400;
ufo.y = 200 + Math.random() * (GAME_BOTTOM - 400);
ufo.alpha = 0.7 + Math.random() * 0.2;
ufo._speed = 9 + Math.random() * 4;
ufo._drift = 0.04 + Math.random() * 0.09;
ufo._driftPhase = Math.random() * Math.PI * 2;
// Add a glow under the UFO for effect
ufo._glow = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.38 + Math.random() * 0.18,
scaleY: 0.18 + Math.random() * 0.12
});
ufo._glow.x = 0;
ufo._glow.y = ufo.height * 0.22;
ufo._glow.alpha = 0.18;
ufo._glow.tint = 0x4a90e2;
ufo.addChildAt(ufo._glow, 0);
game.backgroundUFOs.push(ufo);
game.addChild(ufo);
}
// --- Animated Satellites (background) ---
if (!game.backgroundSatellites) game.backgroundSatellites = [];
if (game.backgroundSatellites.length < 2 && Math.random() < 0.03) {
// Use 'rainbow' asset as a placeholder for a satellite body, with a star as a solar panel
var sat = LK.getAsset('rainbow', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.5 + Math.random() * 0.4,
scaleY: 0.18 + Math.random() * 0.12
});
sat.x = GAME_RIGHT + 200 + Math.random() * 600;
sat.y = 200 + Math.random() * (GAME_BOTTOM - 400);
sat.alpha = 0.19 + Math.random() * 0.13;
sat.tint = 0x4a90e2 + Math.floor(Math.random() * 0x222222); // blueish
sat._speed = 6 + Math.random() * 3;
sat._drift = 0.03 + Math.random() * 0.07;
sat._driftPhase = Math.random() * Math.PI * 2;
sat._rotSpeed = 0.01 + Math.random() * 0.02;
// Add solar panel (star) to each side
var panelL = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.18,
scaleY: 0.18
});
panelL.x = -60;
panelL.y = 0;
panelL.alpha = 0.18;
panelL.tint = 0xf9d423;
var panelR = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.18,
scaleY: 0.18
});
panelR.x = 60;
panelR.y = 0;
panelR.alpha = 0.18;
panelR.tint = 0xf9d423;
sat.addChildAt(panelL, 0);
sat.addChildAt(panelR, 0);
game.backgroundSatellites.push(sat);
game.addChild(sat);
}
// Animate satellites
if (game.backgroundSatellites) {
for (var s = game.backgroundSatellites.length - 1; s >= 0; s--) {
var sat = game.backgroundSatellites[s];
sat.x -= sat._speed;
sat._driftPhase += sat._drift;
sat.y += Math.sin(sat._driftPhase) * 1.2;
sat.rotation = (sat.rotation || 0) + sat._rotSpeed;
// Remove if off screen
if (sat.x < -400) {
if (sat.destroy) sat.destroy();
game.backgroundSatellites.splice(s, 1);
}
}
}
// Animate UFOs
for (var u = game.backgroundUFOs.length - 1; u >= 0; u--) {
var ufo = game.backgroundUFOs[u];
ufo.x -= ufo._speed;
ufo._driftPhase += ufo._drift;
ufo.y += Math.sin(ufo._driftPhase) * 1.2;
ufo._glow.alpha = 0.13 + Math.abs(Math.sin(LK.ticks * 0.09 + u)) * 0.13;
// Remove if off screen
if (ufo.x < -400) {
if (ufo.destroy) ufo.destroy();
game.backgroundUFOs.splice(u, 1);
}
}
// --- Large Asteroids (background) ---
if (game.backgroundAsteroids.length < 2 && Math.random() < 0.03) {
// Use 'planetRed' or 'planetPurple' as a placeholder for big asteroid, squashed and tinted
var asteroidTypes = ['planetRed', 'planetPurple'];
var asteroidId = asteroidTypes[Math.floor(Math.random() * asteroidTypes.length)];
var asteroid = LK.getAsset(asteroidId, {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.7 + Math.random() * 0.7,
scaleY: 0.38 + Math.random() * 0.22
});
asteroid.x = GAME_RIGHT + 600 + Math.random() * 400;
asteroid.y = 200 + Math.random() * (GAME_BOTTOM - 400);
asteroid.alpha = 0.19 + Math.random() * 0.13;
asteroid.tint = 0x888888 + Math.floor(Math.random() * 0x222222); // grayish
asteroid._speed = 10 + Math.random() * 6;
asteroid._drift = 0.03 + Math.random() * 0.07;
asteroid._driftPhase = Math.random() * Math.PI * 2;
asteroid._rotSpeed = 0.01 + Math.random() * 0.02;
game.backgroundAsteroids.push(asteroid);
game.addChild(asteroid);
}
// --- Space Debris (background) ---
if (!game.backgroundDebris) game.backgroundDebris = [];
if (game.backgroundDebris.length < 3 && Math.random() < 0.04) {
// Use 'rainbow' or 'planetYellow' as placeholder for debris
var debrisTypes = ['rainbow', 'planetYellow'];
var debrisId = debrisTypes[Math.floor(Math.random() * debrisTypes.length)];
var debris = LK.getAsset(debrisId, {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.18 + Math.random() * 0.22,
scaleY: 0.18 + Math.random() * 0.22
});
debris.x = GAME_RIGHT + 200 + Math.random() * 800;
debris.y = 200 + Math.random() * (GAME_BOTTOM - 400);
debris.alpha = 0.13 + Math.random() * 0.13;
debris.tint = 0x888888 + Math.floor(Math.random() * 0x222222);
debris._speed = 8 + Math.random() * 4;
debris._drift = 0.04 + Math.random() * 0.09;
debris._driftPhase = Math.random() * Math.PI * 2;
debris._rotSpeed = 0.02 + Math.random() * 0.03;
game.backgroundDebris.push(debris);
game.addChild(debris);
}
// Animate debris
if (game.backgroundDebris) {
for (var d = game.backgroundDebris.length - 1; d >= 0; d--) {
var debris = game.backgroundDebris[d];
debris.x -= debris._speed;
debris._driftPhase += debris._drift;
debris.y += Math.sin(debris._driftPhase) * 1.2;
debris.rotation = (debris.rotation || 0) + debris._rotSpeed;
// Remove if off screen
if (debris.x < -400) {
if (debris.destroy) debris.destroy();
game.backgroundDebris.splice(d, 1);
}
}
}
// Animate asteroids
for (var a = game.backgroundAsteroids.length - 1; a >= 0; a--) {
var asteroid = game.backgroundAsteroids[a];
asteroid.x -= asteroid._speed;
asteroid._driftPhase += asteroid._drift;
asteroid.y += Math.sin(asteroid._driftPhase) * 2.2;
asteroid.rotation = (asteroid.rotation || 0) + asteroid._rotSpeed;
// Remove if off screen
if (asteroid.x < -600) {
if (asteroid.destroy) asteroid.destroy();
game.backgroundAsteroids.splice(a, 1);
}
}
// --- Sparkle background effect ---
if (game.backgroundSparkles.length < 32 && Math.random() < 0.18) {
// Add a new sparkle at random position, random size
var sparkle = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.13 + Math.random() * 0.11,
scaleY: 0.13 + Math.random() * 0.11
});
sparkle.x = Math.random() * (GAME_RIGHT + 400) - 200;
sparkle.y = Math.random() * (GAME_BOTTOM + 400) - 200;
sparkle.alpha = 0.13 + Math.random() * 0.13;
sparkle._twinklePhase = Math.random() * Math.PI * 2;
sparkle._twinkleSpeed = 0.04 + Math.random() * 0.07;
sparkle._baseAlpha = sparkle.alpha;
sparkle._baseScale = sparkle.scaleX;
game.backgroundSparkles.push(sparkle);
game.addChildAt(sparkle, 0);
}
// --- Parallax dust particles for extra movement ---
if (!game.backgroundDust) game.backgroundDust = [];
if (game.backgroundDust.length < 18 && Math.random() < 0.13) {
var dust = LK.getAsset('cloud', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.18 + Math.random() * 0.22,
scaleY: 0.18 + Math.random() * 0.22
});
dust.x = Math.random() * (GAME_RIGHT + 400) - 200;
dust.y = Math.random() * (GAME_BOTTOM + 400) - 200;
dust.alpha = 0.06 + Math.random() * 0.07;
dust._speed = 0.13 + Math.random() * 0.09;
dust._drift = 0.04 + Math.random() * 0.09;
dust._driftPhase = Math.random() * Math.PI * 2;
game.backgroundDust.push(dust);
game.addChildAt(dust, 0);
}
// Animate dust
for (var d = game.backgroundDust.length - 1; d >= 0; d--) {
var dust = game.backgroundDust[d];
dust.x -= dust._speed;
dust._driftPhase += dust._drift;
dust.y += Math.sin(dust._driftPhase) * 0.7;
// Subtle alpha pulsing
dust.alpha = Math.abs(Math.sin(LK.ticks * 0.009 + d)) * 0.03 + 0.06;
// Remove if off screen
if (dust.x < -400 || dust.y < -400 || dust.y > GAME_BOTTOM + 400) {
if (dust.destroy) dust.destroy();
game.backgroundDust.splice(d, 1);
}
}
// Animate sparkles
for (var s = game.backgroundSparkles.length - 1; s >= 0; s--) {
var sparkle = game.backgroundSparkles[s];
// Twinkle alpha and scale
sparkle._twinklePhase += sparkle._twinkleSpeed;
sparkle.alpha = sparkle._baseAlpha * (0.7 + 0.6 * Math.abs(Math.sin(sparkle._twinklePhase)));
sparkle.scaleX = sparkle.scaleY = sparkle._baseScale * (0.9 + 0.2 * Math.abs(Math.cos(sparkle._twinklePhase * 0.7)));
// Slow drift
sparkle.x += Math.sin(sparkle._twinklePhase * 0.5) * 0.13;
sparkle.y += Math.cos(sparkle._twinklePhase * 0.5) * 0.13;
// Remove if off screen
if (sparkle.x < -300 || sparkle.x > GAME_RIGHT + 300 || sparkle.y < -300 || sparkle.y > GAME_BOTTOM + 300) {
if (sparkle.destroy) sparkle.destroy();
game.backgroundSparkles.splice(s, 1);
}
}
// --- Nebula cloud effect (soft colored clouds drifting) ---
if (game.backgroundNebulas.length < 5 && Math.random() < 0.04) {
var nebulaColors = [0xf9d423, 0x9b59b6, 0x4a90e2, 0x7ed957, 0xe94e77];
var color = nebulaColors[Math.floor(Math.random() * nebulaColors.length)];
var nebula = LK.getAsset('cloud', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 1.2 + Math.random() * 1.8,
scaleY: 1.2 + Math.random() * 1.8
});
nebula.x = GAME_RIGHT + 400 + Math.random() * 400;
nebula.y = 200 + Math.random() * (GAME_BOTTOM - 400);
nebula.alpha = 0.08 + Math.random() * 0.08;
nebula.tint = color;
nebula._speed = 0.18 + Math.random() * 0.22;
nebula._drift = 0.12 + Math.random() * 0.13;
nebula._driftPhase = Math.random() * Math.PI * 2;
game.backgroundNebulas.push(nebula);
game.addChildAt(nebula, 0);
}
// Animate nebulas
for (var n = game.backgroundNebulas.length - 1; n >= 0; n--) {
var nebula = game.backgroundNebulas[n];
nebula.x -= nebula._speed;
nebula._driftPhase += nebula._drift;
nebula.y += Math.sin(nebula._driftPhase) * 0.7;
// Subtle alpha pulsing
nebula.alpha = Math.abs(Math.sin(LK.ticks * 0.006 + n)) * 0.04 + 0.08;
// Remove if off screen
if (nebula.x < -600) {
if (nebula.destroy) nebula.destroy();
game.backgroundNebulas.splice(n, 1);
}
}
// --- Aurora band effect (animated colored bands drifting horizontally) ---
if (game.backgroundAuroras.length < 3 && Math.random() < 0.03) {
var auroraColors = [0x7ed957, 0x4a90e2, 0xfe6cd1, 0xf9d423, 0x9b59b6];
var color = auroraColors[Math.floor(Math.random() * auroraColors.length)];
var aurora = LK.getAsset('rainbow', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 18 + Math.random() * 6,
scaleY: 0.7 + Math.random() * 0.5
});
aurora.x = GAME_RIGHT + 800 + Math.random() * 400;
aurora.y = 400 + Math.random() * (GAME_BOTTOM - 800);
aurora.alpha = 0.09 + Math.random() * 0.07;
aurora.tint = color;
aurora._speed = 0.11 + Math.random() * 0.13;
aurora._wavePhase = Math.random() * Math.PI * 2;
aurora._waveSpeed = 0.008 + Math.random() * 0.012;
aurora._baseY = aurora.y;
game.backgroundAuroras.push(aurora);
game.addChildAt(aurora, 0);
}
// Animate auroras
for (var a = game.backgroundAuroras.length - 1; a >= 0; a--) {
var aurora = game.backgroundAuroras[a];
aurora.x -= aurora._speed;
aurora._wavePhase += aurora._waveSpeed;
aurora.y = aurora._baseY + Math.sin(aurora._wavePhase + a) * 38;
// Subtle alpha pulsing
aurora.alpha = Math.abs(Math.sin(LK.ticks * 0.004 + a)) * 0.05 + 0.09;
// Remove if off screen
if (aurora.x < -1200) {
if (aurora.destroy) aurora.destroy();
game.backgroundAuroras.splice(a, 1);
}
}
// --- Comet trail effect (fast-moving, glowing comets with fading tails) ---
if (!game.backgroundComets) game.backgroundComets = [];
if (game.backgroundComets.length < 4 && Math.random() < 0.04) {
var comet = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: 0.22 + Math.random() * 0.18,
scaleY: 0.22 + Math.random() * 0.18
});
comet.x = -200 - Math.random() * 400;
comet.y = 200 + Math.random() * (GAME_BOTTOM - 400);
comet.alpha = 0.19 + Math.random() * 0.13;
comet._speed = 18 + Math.random() * 12;
comet._angle = Math.PI * (0.01 + Math.random() * 0.08); // slight downward
comet._tail = [];
comet._tailColor = [0xf9d423, 0x9b59b6, 0x4a90e2, 0x7ed957, 0xe94e77][Math.floor(Math.random() * 5)];
// Add a glow for more dynamic effect
comet._glow = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: comet.scaleX * 2.2,
scaleY: comet.scaleY * 2.2
});
comet._glow.x = 0;
comet._glow.y = 0;
comet._glow.alpha = 0.13;
comet._glow.tint = comet._tailColor;
comet.addChildAt(comet._glow, 0);
game.backgroundComets.push(comet);
game.addChildAt(comet, 1);
}
// Animate comets and their tails
for (var c = game.backgroundComets.length - 1; c >= 0; c--) {
var comet = game.backgroundComets[c];
// Move comet
comet.x += Math.cos(comet._angle) * comet._speed;
comet.y += Math.sin(comet._angle) * comet._speed;
// Fade out slightly
comet.alpha -= 0.002 + Math.random() * 0.002;
if (comet._glow) {
comet._glow.alpha = comet.alpha * 0.5;
comet._glow.scaleX = comet._glow.scaleY = comet.scaleX * (2.1 + Math.sin(LK.ticks * 0.13 + c) * 0.2);
}
// Store tail positions
if (!comet._tail) comet._tail = [];
comet._tail.unshift({
x: comet.x,
y: comet.y,
alpha: comet.alpha,
scale: comet.scaleX
});
if (comet._tail.length > 14) comet._tail.pop();
// Draw tail as faded stars
for (var t = 1; t < comet._tail.length; t += 2) {
var tail = comet._tail[t];
if (!tail._sprite) {
tail._sprite = LK.getAsset('star', {
anchorX: 0.5,
anchorY: 0.5,
scaleX: comet.scaleX * (1 - t * 0.06),
scaleY: comet.scaleY * (1 - t * 0.06)
});
tail._sprite.x = tail.x;
tail._sprite.y = tail.y;
tail._sprite.alpha = comet.alpha * (0.5 - t * 0.04);
tail._sprite.tint = comet._tailColor;
game.addChildAt(tail._sprite, 0);
} else {
tail._sprite.x = tail.x;
tail._sprite.y = tail.y;
tail._sprite.alpha = comet.alpha * (0.5 - t * 0.04);
tail._sprite.scaleX = tail._sprite.scaleY = comet.scaleX * (1 - t * 0.06);
}
}
// Remove if off screen
if (comet.x > GAME_RIGHT + 400 || comet.y > GAME_BOTTOM + 400 || comet.alpha < 0.01) {
// Remove tail sprites
for (var t = 1; t < comet._tail.length; t += 2) {
var tail = comet._tail[t];
if (tail._sprite && tail._sprite.destroy) tail._sprite.destroy();
}
if (comet._glow && comet._glow.destroy) comet._glow.destroy();
if (comet.destroy) comet.destroy();
game.backgroundComets.splice(c, 1);
}
}
function spawnBackgroundPlanets() {
// Remove any existing
for (var i = 0; i < backgroundPlanets.length; i++) {
backgroundPlanets[i].destroy();
}
backgroundPlanets = [];
// Place a few planets at random positions, different depths/colors
var planetDefs = [{
id: 'planetBlue',
x: 900,
y: 400,
scale: 1.2,
alpha: 0.22,
drift: 0.08,
driftMag: 40
}, {
id: 'planetGreen',
x: 3200,
y: 600,
scale: 1.1,
alpha: 0.18,
drift: 0.06,
driftMag: 30
}, {
id: 'planetPurple',
x: 2600,
y: 1700,
scale: 1.4,
alpha: 0.16,
drift: 0.07,
driftMag: 36
}, {
id: 'planetRed',
x: 1800,
y: 1400,
scale: 1.0,
alpha: 0.19,
drift: 0.09,
driftMag: 28
}, {
id: 'planetYellow',
x: 3400,
y: 1800,
scale: 0.9,
alpha: 0.13,
drift: 0.05,
driftMag: 22
}];
for (var i = 0; i < planetDefs.length; i++) {
var def = planetDefs[i];
var planet = LK.getAsset(def.id, {
anchorX: 0.5,
anchorY: 0.5
});
planet.x = def.x;
planet.y = def.y;
planet.scaleX = planet.scaleY = def.scale;
planet.alpha = def.alpha;
planet.drift = def.drift;
planet.driftMag = def.driftMag;
backgroundPlanets.push(planet);
game.addChildAt(planet, 0); // Always behind everything
}
}
spawnBackgroundPlanets();
// Music
// Sound effects
// Rainbow trail
// Treat (pop tart)
// Obstacle (star)
// Obstacle (cloud)
// Nyan Cat (main character)
// Game area margins
var GAME_TOP = 0;
var GAME_BOTTOM = 2160;
var GAME_LEFT = 0;
var GAME_RIGHT = 3840;
// Avoid top left 100x100 for menu
var SAFE_TOP = 120;
// Main character
var nyanCat = new NyanCat();
game.addChild(nyanCat);
// Center Nyan Cat horizontally, place at 60% height
nyanCat.x = 3840 * 0.25;
nyanCat.y = 2160 * 0.6;
var nyanCatBaseY = nyanCat.y;
// --- In-Game UI Overlay ---
// Score display (smaller, always visible at top center)
var scoreTxt = new Text2('0', {
size: 120,
fill: "#fff"
});
scoreTxt.anchor.set(0.5, 0);
scoreTxt.x = 2048;
scoreTxt.y = 20;
LK.gui.top.addChild(scoreTxt);
// Pause button (top right, avoid top left 100x100)
var pauseBtnBg = LK.getAsset('planetPurple', {
anchorX: 0.5,
anchorY: 0.5
});
pauseBtnBg.x = 2048 * 2 - 180;
pauseBtnBg.y = 100;
pauseBtnBg.scaleX = pauseBtnBg.scaleY = 0.7;
pauseBtnBg.alpha = 0.85;
LK.gui.top.addChild(pauseBtnBg);
var pauseBtnText = new Text2('II', {
size: 90,
fill: "#fff"
});
pauseBtnText.anchor.set(0.5, 0.5);
pauseBtnText.x = pauseBtnBg.x;
pauseBtnText.y = pauseBtnBg.y;
LK.gui.top.addChild(pauseBtnText);
// Pause button interaction
pauseBtnBg.down = function (x, y, obj) {
// Pause the game and show the menu overlay
if (!mainMenuOverlay.visible) {
mainMenuOverlay.visible = true;
game.paused = true;
createMenuBackground();
LK.stopMusic();
}
};
pauseBtnText.down = pauseBtnBg.down;
// Arrays for obstacles and treats
var obstacles = [];
var treats = [];
// Difficulty parameters
var baseSpeed = 12;
var speed = baseSpeed;
var spawnInterval = 70; // ticks between spawns
var treatInterval = 110; // ticks between treat spawns
var minSpawnInterval = 30;
var maxSpeed = 32;
// Dragging
var dragNode = null;
// Last collision state
var lastHit = false;
// Play music
LK.playMusic('nyanMusic');
// Helper: collision check (AABB)
function isColliding(a, b) {
var ab = a.getCollisionBounds();
var bb = b.getCollisionBounds();
return ab.x < bb.x + bb.width && ab.x + ab.width > bb.x && ab.y < bb.y + bb.height && ab.y + ab.height > bb.y;
}
// Move handler (drag Nyan Cat)
function handleMove(x, y, obj) {
if (dragNode) {
// Clamp to game area, avoid top left 100x100
var cat = dragNode;
var bounds = cat.getCollisionBounds();
var halfW = bounds.width / 2;
var halfH = bounds.height / 2;
var minX = GAME_LEFT + halfW;
var maxX = GAME_RIGHT - halfW;
var minY = Math.max(GAME_TOP + halfH, SAFE_TOP + halfH);
var maxY = GAME_BOTTOM - halfH;
cat.x = Math.max(minX, Math.min(maxX, x));
cat.y = Math.max(minY, Math.min(maxY, y));
}
}
game.move = handleMove;
game.down = function (x, y, obj) {
// Only allow drag if touch is on Nyan Cat
var bounds = nyanCat.getCollisionBounds();
if (x >= bounds.x && x <= bounds.x + bounds.width && y >= bounds.y && y <= bounds.y + bounds.height) {
dragNode = nyanCat;
handleMove(x, y, obj);
}
};
game.up = function (x, y, obj) {
dragNode = null;
};
// Game update loop
game.update = function () {
// Only planets are used for the space background; no starfield, clouds, or other backgrounds
// Animate shooting stars for lively background
if (!game.shootingStars) game.shootingStars = [];
// Spawn a shooting star at random intervals
if (LK.ticks % 23 === 0 && Math.random() < 0.45) {
var star = new ShootingStar();
// Start at random X on left, random Y in upper half
star.x = Math.random() * 1200;
star.y = 80 + Math.random() * 900;
game.shootingStars.push(star);
game.addChildAt(star, 1); // Behind main gameplay
}
// Update and clean up shooting stars
for (var s = game.shootingStars.length - 1; s >= 0; s--) {
var star = game.shootingStars[s];
if (star.destroyed || star.alpha <= 0.01 || star.x > GAME_RIGHT + 200 || star.y > GAME_BOTTOM + 200) {
if (!star.destroyed) star.destroy();
game.shootingStars.splice(s, 1);
continue;
}
star.update();
}
// Increase difficulty over time
if (LK.ticks % 180 === 0 && speed < maxSpeed) {
speed += 1.2;
spawnInterval = Math.max(minSpawnInterval, spawnInterval - 4);
}
// Spawn obstacles
if (LK.ticks % spawnInterval === 0) {
var obs = new Obstacle();
obs.speed = speed;
// Random Y, avoid top 100px
var asset = obs.children[0];
var minY = SAFE_TOP + asset.height / 2;
var maxY = GAME_BOTTOM - asset.height / 2;
obs.x = GAME_RIGHT + asset.width / 2 + 10;
obs.y = Math.random() * (maxY - minY) + minY;
obstacles.push(obs);
game.addChild(obs);
}
// Spawn treats
if (LK.ticks % treatInterval === 0) {
var treat = new Treat();
treat.speed = speed * 0.95;
var asset = treat.children[0];
var minY = SAFE_TOP + asset.height / 2;
var maxY = GAME_BOTTOM - asset.height / 2;
treat.x = GAME_RIGHT + asset.width / 2 + 10;
treat.y = Math.random() * (maxY - minY) + minY;
treats.push(treat);
game.addChild(treat);
}
// Update obstacles
for (var i = obstacles.length - 1; i >= 0; i--) {
var obs = obstacles[i];
obs.update();
// Twinkle and pulse for obstacles (clouds/stars)
if (obs.children && obs.children.length > 1) {
var obsSprite = obs.children[1];
obsSprite.rotation = Math.sin(LK.ticks * 0.09 + i) * 0.13;
obsSprite.scaleX = 1 + Math.sin(LK.ticks * 0.15 + i) * 0.09;
obsSprite.scaleY = 1 + Math.cos(LK.ticks * 0.13 + i) * 0.09;
}
// Remove if off screen
if (obs.x < -300) {
obs.destroy();
obstacles.splice(i, 1);
continue;
}
// Collision with Nyan Cat
var hit = isColliding(obs, nyanCat);
if (hit && !lastHit) {
// Flash, play sound, game over
nyanCat.flash();
LK.getSound('hit').play();
LK.effects.flashScreen(0xff0000, 800);
LK.showGameOver();
lastHit = true;
break; // Stop further checks
}
}
// Update treats
for (var j = treats.length - 1; j >= 0; j--) {
var treat = treats[j];
treat.update();
// Twinkle effect for treats (make them pulse and rotate for more life)
if (treat.children && treat.children.length > 1) {
var treatSprite = treat.children[1];
treatSprite.rotation = Math.sin(LK.ticks * 0.13 + j) * 0.18;
treatSprite.scaleX = 1 + Math.sin(LK.ticks * 0.19 + j) * 0.13;
treatSprite.scaleY = 1 + Math.cos(LK.ticks * 0.17 + j) * 0.13;
}
// Remove if off screen
if (treat.x < -200) {
treat.destroy();
treats.splice(j, 1);
continue;
}
// Collision with Nyan Cat
if (isColliding(treat, nyanCat)) {
LK.setScore(LK.getScore() + 1);
scoreTxt.setText(LK.getScore());
LK.getSound('collect').play();
// Animate treat
tween(treat, {
scaleX: 2.1,
scaleY: 2.1,
alpha: 0
}, {
duration: 220,
ease: "outBack",
onFinish: function onFinish() {
treat.destroy();
}
});
treats.splice(j, 1);
continue;
}
}
// Track Nyan Cat's lastX for parallax
if (typeof nyanCat.lastX === "undefined") nyanCat.lastX = nyanCat.x;
// Nyan Cat idle bobbing and lively animation
if (!dragNode) {
nyanCat.y = nyanCatBaseY + Math.sin(LK.ticks * 0.08) * 22;
// Subtle rotation and scale for lively effect
if (nyanCat.children && nyanCat.children.length > 1) {
var catSprite = nyanCat.children[1];
catSprite.rotation = Math.sin(LK.ticks * 0.07) * 0.08;
catSprite.scaleX = 1 + Math.sin(LK.ticks * 0.11) * 0.04;
catSprite.scaleY = 1 + Math.cos(LK.ticks * 0.13) * 0.04;
}
// Subtle color pulsing for rainbow trail
if (nyanCat.children && nyanCat.children.length > 0) {
var rainbowSprite = nyanCat.children[0];
var baseTint = 0xffe0fa;
var pulse = Math.floor(0x20 * (1 + Math.sin(LK.ticks * 0.09)));
// Animate tint between pink and yellowish
rainbowSprite.tint = 0xffe0fa + (pulse << 8);
}
}
// Update lastX for next frame
nyanCat.lastX = nyanCat.x;
// Reset lastHit if not colliding
if (!obstacles.some(function (obs) {
return isColliding(obs, nyanCat);
})) {
lastHit = false;
}
};
// Reset score and all game state on game start
LK.setScore(0);
scoreTxt.setText('0');
// Remove all obstacles and treats from game
for (var i = 0; i < obstacles.length; i++) {
obstacles[i].destroy();
}
obstacles = [];
for (var j = 0; j < treats.length; j++) {
treats[j].destroy();
}
treats = [];
// Reset Nyan Cat position and base Y
nyanCat.x = 3840 * 0.25;
nyanCat.y = 2160 * 0.6;
nyanCatBaseY = nyanCat.y;
// Reset difficulty
speed = baseSpeed;
spawnInterval = 70;
treatInterval = 110;
// Reset drag and collision state
dragNode = null;
lastHit = false;
NYAN CAT. In-Game asset. 2d. High contrast. No shadows
DİKENLİ TOP. In-Game asset. 2d. High contrast. No shadows
TAŞ. In-Game asset. 2d. High contrast. No shadows
kurabiye. In-Game asset. 2d. High contrast. No shadows
satürn. In-Game asset. 2d. High contrast. No shadows
neptün. In-Game asset. 2d. High contrast. No shadows