User prompt
make the tutorial more understable
User prompt
fix the all assets hitbox
User prompt
In some levels, when we select one of the particles in dimension 0, the particle in dimension 2 moves with it. fix this error
User prompt
in someIn some levels, when we select one of the particles in dimension 0, the particle in dimension 2 moves with it.
User prompt
particle hit box not working probly
User prompt
tutorial not working probly
User prompt
fix the levels after level 5
User prompt
fix the levels particle errors
User prompt
tutorial not working probly
User prompt
make the game little bit easyer
User prompt
make the interference Field assets brighter
User prompt
make the assets more visibly
User prompt
tutorial not working probly
User prompt
make the tutorial more educational
User prompt
i want a add a tutorial level at the start
User prompt
powerups not working probly
User prompt
fix the powerups spawn time
User prompt
when choosing particle in the dimension other dimensions particle following it too
User prompt
dimensions not workin
User prompt
when the pick up powerups tell the specs
User prompt
cant use powerups
User prompt
add more level
User prompt
fix the all hitbox
User prompt
fix the particle hit box
User prompt
some time interferencefield not working correctly
/****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
/****
* Classes
****/
var BackgroundStar = Container.expand(function () {
var self = Container.call(this);
var starGraphics = self.attachAsset('star', {
anchorX: 0.5,
anchorY: 0.5
});
self.twinkleSpeed = 0.02 + Math.random() * 0.03;
self.twinkleOffset = Math.random() * Math.PI * 2;
self.baseAlpha = 0.3 + Math.random() * 0.7;
self.update = function () {
// Direct property updates instead of creating tweens every frame
var twinkle = Math.sin(LK.ticks * self.twinkleSpeed + self.twinkleOffset) * 0.3 + 0.7;
self.alpha = self.baseAlpha * twinkle;
// Direct position updates for smooth movement
self.x += Math.sin(LK.ticks * 0.01 + self.twinkleOffset) * 0.02;
self.y += Math.cos(LK.ticks * 0.008 + self.twinkleOffset) * 0.015;
};
return self;
});
var InterferenceField = Container.expand(function () {
var self = Container.call(this);
var fieldGraphics = self.attachAsset('interferenceField', {
anchorX: 0.5,
anchorY: 0.5,
tint: 0xff4444
});
self.dimension = 0;
self.pulseDirection = 1;
self.setDimension = function (dim) {
self.dimension = dim;
self.alpha = 0.8;
};
self.update = function () {
// Direct rotation update
fieldGraphics.rotation += 0.015;
// Direct alpha updates instead of creating tweens every frame
if (self.dimension === currentDimension) {
self.alpha = 0.9 + Math.sin(LK.ticks * 0.05) * 0.3;
// Add bright glow effect with color cycling
var glowIntensity = Math.sin(LK.ticks * 0.08) * 0.5 + 0.5;
fieldGraphics.tint = 0xff0000 + Math.floor(glowIntensity * 0x4444);
} else {
self.alpha = 0.4;
fieldGraphics.tint = 0xff4444;
}
// Direct position updates for moving fields - reduced speeds for easier gameplay
if (self.moveDirection !== undefined) {
var moveSpeed = 2.5; // Reduced from 4 to 2.5
// Increase speed for level 8+
if (level >= 8) {
moveSpeed = 3.5; // Reduced from 6 to 3.5
}
// Ultra-fast speed for level 16+
if (level >= 16) {
moveSpeed = 5; // Reduced from 9 to 5
}
// Extreme speed for level 11+
if (level >= 11) {
moveSpeed = 4; // Reduced from 7 to 4
}
self.x += self.moveDirection * moveSpeed;
if (self.x <= self.minX || self.x >= self.maxX) {
self.moveDirection *= -1;
}
}
};
return self;
});
var Particle = Container.expand(function () {
var self = Container.call(this);
var particleGraphics = self.attachAsset('particle', {
anchorX: 0.5,
anchorY: 0.5
});
self.dimension = 0;
self.originalPosition = {
x: 0,
y: 0
};
self.isBeingDragged = false;
self.isCollected = false;
self.entangledWith = null;
self.setDimension = function (dim) {
self.dimension = dim;
self.alpha = 1.0;
};
self.startDrag = function () {
self.isBeingDragged = true;
tween(particleGraphics, {
scaleX: 1.2,
scaleY: 1.2
}, {
duration: 200
});
};
self.stopDrag = function () {
self.isBeingDragged = false;
tween(particleGraphics, {
scaleX: 1.0,
scaleY: 1.0
}, {
duration: 200
});
};
self.collect = function () {
self.isCollected = true;
// Enhanced collection animation with bounce effect
tween(self, {
scaleX: 1.5,
scaleY: 1.5
}, {
duration: 150,
easing: tween.easeOut,
onFinish: function onFinish() {
tween(self, {
alpha: 0,
scaleX: 0.1,
scaleY: 0.1
}, {
duration: 200,
easing: tween.easeIn,
onFinish: function onFinish() {
self.visible = false;
}
});
}
});
// Tutorial step progression for particle collection
if (isTutorial) {
if (tutorialStep === 1 || tutorialStep === 2) {
tutorialStep = 2;
LK.setTimeout(function () {
updateTutorialStep();
}, 1000);
} else if (tutorialStep === 5) {
tutorialStep = 6;
LK.setTimeout(function () {
updateTutorialStep();
}, 1000);
}
}
};
self.update = function () {
if (self.isCollected) return;
// Initialize collision tracking
if (self.lastCoreIntersecting === undefined) {
self.lastCoreIntersecting = false;
}
// Check collision with quantum core - only trigger on first contact
var currentCoreIntersecting = false;
if (self.dimension === currentDimension && quantumCore) {
// Use actual asset dimensions for accurate collision detection
var particleHalfWidth = particleGraphics.width / 2; // Use actual particle asset width
var particleHalfHeight = particleGraphics.height / 2; // Use actual particle asset height
var coreHalfWidth = quantumCore.width / 2; // Use actual quantum core asset width
var coreHalfHeight = quantumCore.height / 2; // Use actual quantum core asset height
currentCoreIntersecting = Math.abs(self.x - quantumCore.x) < particleHalfWidth + coreHalfWidth && Math.abs(self.y - quantumCore.y) < particleHalfHeight + coreHalfHeight;
}
if (!self.lastCoreIntersecting && currentCoreIntersecting) {
self.collect();
LK.getSound('collectSound').play();
particlesCollected++;
checkWinCondition();
}
self.lastCoreIntersecting = currentCoreIntersecting;
// Check collision with interference fields
for (var i = 0; i < interferenceFields.length; i++) {
var field = interferenceFields[i];
if (field.dimension === self.dimension) {
// Use actual asset dimensions for accurate collision detection
var particleHalfWidth = particleGraphics.width / 2; // Use actual particle asset width
var particleHalfHeight = particleGraphics.height / 2; // Use actual particle asset height
var fieldHalfWidth = field.children[0].width / 2; // Use actual interference field asset width
var fieldHalfHeight = field.children[0].height / 2; // Use actual interference field asset height
var isColliding = Math.abs(self.x - field.x) < particleHalfWidth + fieldHalfWidth && Math.abs(self.y - field.y) < particleHalfHeight + fieldHalfHeight;
if (isColliding) {
if (isTutorial) {
// In tutorial, just show educational message instead of resetting
if (tutorialStep >= 7) {
tutorialText.setText('You touched an interference field!\nIn real levels, this would reset the level.');
LK.effects.flashObject(self, 0xff0000, 500);
}
} else {
resetLevel();
return;
}
}
}
}
// Handle entanglement
if (self.entangledWith && !self.isBeingDragged && self.entangledWith.isBeingDragged) {
self.x = self.entangledWith.x + 150;
self.y = self.entangledWith.y;
// Maintain proper alpha based on current dimension
var targetAlpha = self.dimension === currentDimension ? 1.0 : 0.15;
self.alpha = targetAlpha;
}
};
self.down = function (x, y, obj) {
// Drag handling is now managed by game.down event handler
};
return self;
});
var Portal = Container.expand(function () {
var self = Container.call(this);
var portalGraphics = self.attachAsset('portal', {
anchorX: 0.5,
anchorY: 0.5
});
self.dimension = 0;
self.targetDimension = 1;
self.setDimension = function (dim) {
self.dimension = dim;
self.alpha = 1.0;
};
self.update = function () {
// Direct rotation update
portalGraphics.rotation += 0.02;
// Check if particles are transported through portal
for (var i = 0; i < particles.length; i++) {
var particle = particles[i];
if (particle.dimension === self.dimension && !particle.isBeingDragged) {
// Use actual asset dimensions for accurate collision detection
var portalHalfWidth = portalGraphics.width / 2; // Use actual portal asset width
var portalHalfHeight = portalGraphics.height / 2; // Use actual portal asset height
var particleHalfWidth = particle.children[0].width / 2; // Use actual particle asset width
var particleHalfHeight = particle.children[0].height / 2; // Use actual particle asset height
var isColliding = Math.abs(self.x - particle.x) < portalHalfWidth + particleHalfWidth && Math.abs(self.y - particle.y) < portalHalfHeight + particleHalfHeight;
if (isColliding) {
particle.setDimension(self.targetDimension);
LK.getSound('portalSound').play();
LK.effects.flashObject(self, 0xffffff, 300);
}
}
}
};
return self;
});
var PowerUp = Container.expand(function () {
var self = Container.call(this);
self.type = 'timeBoost'; // Default type
self.dimension = 0;
self.isCollected = false;
self.powerUpGraphics = null;
self.floatOffset = Math.random() * Math.PI * 2;
self.floatSpeed = 0.02 + Math.random() * 0.01;
self.glowDirection = 1;
self.glowIntensity = 1.0;
self.setType = function (type) {
self.type = type;
if (self.powerUpGraphics) {
self.powerUpGraphics.destroy();
}
var assetName = type === 'timeBoost' ? 'timeBoost' : type === 'shield' ? 'shieldPower' : 'slowMotion';
self.powerUpGraphics = self.attachAsset(assetName, {
anchorX: 0.5,
anchorY: 0.5
});
};
self.setDimension = function (dim) {
self.dimension = dim;
self.alpha = 1.0;
};
self.collect = function () {
self.isCollected = true;
LK.getSound('powerUpSound').play();
// Collect animation with burst effect
tween(self, {
scaleX: 2.0,
scaleY: 2.0,
alpha: 0
}, {
duration: 400,
easing: tween.easeOut,
onFinish: function onFinish() {
self.visible = false;
}
});
// Apply power-up effect
self.applyEffect();
};
self.applyEffect = function () {
if (self.type === 'timeBoost') {
timeRemaining += 15000; // Add 15 seconds (increased from 10)
LK.effects.flashScreen(0x00ff00, 300);
showPowerUpSpec('TIME BOOST', '+15 seconds', 0x00ff00);
} else if (self.type === 'shield') {
shieldActive = true;
shieldTimeRemaining = 12000; // 12 seconds of shield (increased from 8)
LK.effects.flashScreen(0x0088ff, 300);
showPowerUpSpec('SHIELD', '12 seconds protection', 0x0088ff);
} else if (self.type === 'slowMotion') {
slowMotionActive = true;
slowMotionTimeRemaining = 10000; // 10 seconds of slow motion (increased from 6)
LK.effects.flashScreen(0xff8800, 300);
showPowerUpSpec('SLOW MOTION', '10 seconds effect', 0xff8800);
}
};
self.update = function () {
if (self.isCollected) return;
// Initialize collision tracking
if (self.lastPlayerIntersecting === undefined) {
self.lastPlayerIntersecting = false;
}
// Floating animation
self.y += Math.sin(LK.ticks * self.floatSpeed + self.floatOffset) * 0.5;
// Glow effect
self.glowIntensity += self.glowDirection * 0.02;
if (self.glowIntensity > 1.3) {
self.glowIntensity = 1.3;
self.glowDirection = -1;
} else if (self.glowIntensity < 0.7) {
self.glowIntensity = 0.7;
self.glowDirection = 1;
}
self.scaleX = self.glowIntensity;
self.scaleY = self.glowIntensity;
// Rotation for visual appeal
if (self.powerUpGraphics) {
self.powerUpGraphics.rotation += 0.03;
}
// Update visibility based on current dimension
var targetAlpha = self.dimension === currentDimension ? self.glowIntensity : 0.15;
if (Math.abs(self.alpha - targetAlpha) > 0.05) {
self.alpha = targetAlpha;
}
// Check collision with all particles in current dimension
var currentPlayerIntersecting = false;
for (var p = 0; p < particles.length; p++) {
var particle = particles[p];
if (particle.dimension === self.dimension && particle.dimension === currentDimension && !particle.isCollected) {
// Use actual asset dimensions for accurate collision detection
var powerUpHalfWidth = self.powerUpGraphics.width / 2; // Use actual power-up asset width
var powerUpHalfHeight = self.powerUpGraphics.height / 2; // Use actual power-up asset height
var particleHalfWidth = particle.children[0].width / 2; // Use actual particle asset width
var particleHalfHeight = particle.children[0].height / 2; // Use actual particle asset height
var isColliding = Math.abs(self.x - particle.x) < powerUpHalfWidth + particleHalfWidth && Math.abs(self.y - particle.y) < powerUpHalfHeight + particleHalfHeight;
if (isColliding) {
currentPlayerIntersecting = true;
break;
}
}
}
if (!self.lastPlayerIntersecting && currentPlayerIntersecting) {
self.collect();
}
self.lastPlayerIntersecting = currentPlayerIntersecting;
};
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x000033
});
/****
* Game Code
****/
var currentDimension = 0;
var totalDimensions = 2;
var particles = [];
var portals = [];
var interferenceFields = [];
var quantumCore;
var draggedParticle = null;
var dragOffset = {
x: 0,
y: 0
};
var particlesCollected = 0;
var totalParticles = 0;
var level = 0; // Start with tutorial level (level 0)
var timeLimit = 25000; // 25 seconds in milliseconds
var timeRemaining = timeLimit;
var timerActive = false;
var dimensionSwitches = 0;
var maxDimensionSwitches = 5;
var backgroundStars = [];
var powerUps = [];
var shieldActive = false;
var shieldTimeRemaining = 0;
var slowMotionActive = false;
var slowMotionTimeRemaining = 0;
var powerUpSpawnTimer = 0;
var powerUpSpawnInterval = 8000; // Spawn power-up every 8 seconds
var isTutorial = true;
var tutorialStep = 0;
var tutorialComplete = false;
var tutorialText = null;
// UI Elements
var dimensionText = new Text2('Dimension: 0', {
size: 60,
fill: 0xFFFFFF
});
dimensionText.anchor.set(0.5, 0);
LK.gui.top.addChild(dimensionText);
var levelText = new Text2('Level: 1', {
size: 50,
fill: 0xFFFFFF
});
levelText.anchor.set(0.5, 0);
levelText.y = 100;
LK.gui.top.addChild(levelText);
var instructionText = new Text2('Tap to switch dimensions', {
size: 40,
fill: 0xCCCCCC
});
instructionText.anchor.set(0.5, 1);
LK.gui.bottom.addChild(instructionText);
var timerText = new Text2('Time: 25s', {
size: 50,
fill: 0xFFFFFF
});
timerText.anchor.set(0.5, 0);
timerText.y = 160;
LK.gui.top.addChild(timerText);
var shieldText = new Text2('SHIELD ACTIVE', {
size: 45,
fill: 0x0088ff
});
shieldText.anchor.set(0.5, 0);
shieldText.y = 220;
shieldText.visible = false;
LK.gui.top.addChild(shieldText);
var slowMotionText = new Text2('SLOW MOTION', {
size: 45,
fill: 0xff8800
});
slowMotionText.anchor.set(0.5, 0);
slowMotionText.y = 280;
slowMotionText.visible = false;
LK.gui.top.addChild(slowMotionText);
// Tutorial text
tutorialText = new Text2('Welcome to Quantum Dimensions!', {
size: 50,
fill: 0x00ff88
});
tutorialText.anchor.set(0.5, 0.5);
tutorialText.x = 1024;
tutorialText.y = 400;
tutorialText.visible = false;
game.addChild(tutorialText);
// Create dimension indicators
var dimensionIndicators = [];
for (var d = 0; d < totalDimensions; d++) {
var indicator = LK.getAsset('dimensionIndicator', {
anchorX: 0.5,
anchorY: 0.5,
x: 1024 + d * 60,
y: 150
});
dimensionIndicators.push(indicator);
LK.gui.addChild(indicator);
}
function initializeLevel() {
// Clear existing elements
for (var i = 0; i < particles.length; i++) {
particles[i].destroy();
}
for (var i = 0; i < portals.length; i++) {
portals[i].destroy();
}
for (var i = 0; i < interferenceFields.length; i++) {
interferenceFields[i].destroy();
}
for (var i = 0; i < backgroundStars.length; i++) {
backgroundStars[i].destroy();
}
for (var i = 0; i < powerUps.length; i++) {
powerUps[i].destroy();
}
backgroundStars = [];
particles = [];
portals = [];
interferenceFields = [];
powerUps = [];
particlesCollected = 0;
currentDimension = 0;
// Reset and start timer - reduced time penalty for easier gameplay
var timeReduction = (level - 1) * 800; // Reduced from 1500 to 800
// Extra time reduction for extreme levels - less harsh
if (level >= 11) {
timeReduction += (level - 10) * 200; // Reduced from 500 to 200
}
if (level >= 16) {
timeReduction += (level - 15) * 100; // Reduced from 300 to 100
}
timeRemaining = Math.max(12000, timeLimit - timeReduction); // Increased minimum from 6 to 12 seconds
timerActive = true;
dimensionSwitches = 0;
maxDimensionSwitches = Math.max(12, 18 - Math.min(level, 4)); // More switches allowed, minimum 12 (increased from 8)
// Reset power-up system
shieldActive = false;
shieldTimeRemaining = 0;
slowMotionActive = false;
slowMotionTimeRemaining = 0;
powerUpSpawnTimer = 0;
shieldText.visible = false;
slowMotionText.visible = false;
// Create quantum core
if (quantumCore) {
quantumCore.destroy();
}
quantumCore = game.addChild(LK.getAsset('quantumCore', {
anchorX: 0.5,
anchorY: 0.5,
x: 1024,
y: 800
}));
// Create background star field
var numStars = 80 + level * 15;
for (var i = 0; i < numStars; i++) {
var star = game.addChild(new BackgroundStar());
star.x = Math.random() * 2048;
star.y = Math.random() * 2732;
star.scaleX = 0.5 + Math.random() * 1.5;
star.scaleY = star.scaleX;
backgroundStars.push(star);
}
// Create orbital particles around quantum core
for (var i = 0; i < 8; i++) {
var orbitalStar = game.addChild(new BackgroundStar());
var angle = i / 8 * Math.PI * 2;
var radius = 200 + Math.random() * 100;
orbitalStar.x = quantumCore.x + Math.cos(angle) * radius;
orbitalStar.y = quantumCore.y + Math.sin(angle) * radius;
orbitalStar.scaleX = 1.5;
orbitalStar.scaleY = 1.5;
orbitalStar.orbitalAngle = angle;
orbitalStar.orbitalRadius = radius;
orbitalStar.orbitalSpeed = 0.01 + Math.random() * 0.02;
backgroundStars.push(orbitalStar);
}
// Tutorial level setup (Level 0)
if (level === 0) {
isTutorial = true;
tutorialStep = 0;
tutorialComplete = false;
timerActive = false; // No timer pressure in tutorial
maxDimensionSwitches = 999; // Unlimited switches for tutorial
tutorialText.visible = true;
tutorialText.setText('Welcome to Quantum Dimensions!');
// Single particle in dimension 0 for simple drag tutorial
var tutorialParticle = game.addChild(new Particle());
tutorialParticle.x = 300;
tutorialParticle.y = 1800;
tutorialParticle.setDimension(0);
tutorialParticle.lastCoreIntersecting = false;
tutorialParticle.isBeingDragged = false;
tutorialParticle.isCollected = false;
tutorialParticle.dimension = 0; // Ensure dimension is properly set
particles.push(tutorialParticle);
// Add a second particle in dimension 1 to demonstrate dimension switching
var tutorialParticle2 = game.addChild(new Particle());
tutorialParticle2.x = 1700;
tutorialParticle2.y = 1800;
tutorialParticle2.setDimension(1);
tutorialParticle2.lastCoreIntersecting = false;
tutorialParticle2.isBeingDragged = false;
tutorialParticle2.isCollected = false;
tutorialParticle2.dimension = 1; // Ensure dimension is properly set
particles.push(tutorialParticle2);
// Add a safe interference field for demonstration (not dangerous in tutorial)
var demoField = game.addChild(new InterferenceField());
demoField.x = 1024;
demoField.y = 2200;
demoField.setDimension(0);
demoField.alpha = 0.3; // Make it less threatening
interferenceFields.push(demoField);
// Add a portal for demonstration
var demoPortal = game.addChild(new Portal());
demoPortal.x = 1024;
demoPortal.y = 1400;
demoPortal.dimension = 0;
demoPortal.targetDimension = 1;
demoPortal.setDimension(0);
demoPortal.alpha = 0.5; // Make it visible but not distracting
portals.push(demoPortal);
totalParticles = 2; // Count both particles for tutorial completion
// Show tutorial instructions immediately
LK.setTimeout(function () {
updateTutorialStep();
}, 500);
} else if (level === 1) {
// Reset tutorial flags for actual gameplay
isTutorial = false;
tutorialText.visible = false;
timerActive = true;
// Simple particles in different dimensions
var particle1 = game.addChild(new Particle());
particle1.x = 300;
particle1.y = 1600;
particle1.setDimension(0);
particle1.lastCoreIntersecting = false;
particle1.isBeingDragged = false;
particle1.isCollected = false;
particles.push(particle1);
var particle2 = game.addChild(new Particle());
particle2.x = 1700;
particle2.y = 1600;
particle2.setDimension(1);
particle2.lastCoreIntersecting = false;
particle2.isBeingDragged = false;
particle2.isCollected = false;
particles.push(particle2);
// Portal to connect dimensions
var portal1 = game.addChild(new Portal());
portal1.x = 1024;
portal1.y = 1600;
portal1.dimension = 0;
portal1.targetDimension = 1;
portal1.setDimension(0);
portals.push(portal1);
totalParticles = 2;
} else {
// Progressive levels with more complexity - reduced interference fields
var numParticles = Math.min(level + 1, 4);
var numFields = Math.min(Math.max(0, level - 1), 4); // Fewer interference fields, starting from level 2
for (var i = 0; i < numParticles; i++) {
var particle = game.addChild(new Particle());
particle.x = 200 + i * 400;
particle.y = 1800 + i % 2 * 400;
particle.setDimension(i % totalDimensions);
particle.lastCoreIntersecting = false;
particle.isBeingDragged = false;
particle.isCollected = false;
particles.push(particle);
}
// Create entangled pairs for higher levels
if (level >= 3 && particles.length >= 2) {
particles[0].entangledWith = particles[1];
particles[1].entangledWith = particles[0];
}
// Create portals
for (var i = 0; i < 2; i++) {
var portal = game.addChild(new Portal());
portal.x = 400 + i * 1200;
portal.y = 1200;
portal.dimension = i;
portal.targetDimension = (i + 1) % totalDimensions;
portal.setDimension(i);
portals.push(portal);
}
// Create interference fields
for (var i = 0; i < numFields; i++) {
var field = game.addChild(new InterferenceField());
field.x = 300 + i * 600;
field.y = 1000 + i % 2 * 400;
field.setDimension(i % totalDimensions);
// Add movement to interference fields for higher levels
if (level >= 2) {
field.moveDirection = i % 2 === 0 ? 1 : -1;
field.minX = 100;
field.maxX = 1948;
}
interferenceFields.push(field);
}
// Add additional moving barriers for higher levels
if (level >= 2) {
var movingField = game.addChild(new InterferenceField());
movingField.x = 1024;
movingField.y = 1400;
movingField.setDimension(0);
movingField.moveDirection = 1;
movingField.minX = 200;
movingField.maxX = 1848;
interferenceFields.push(movingField);
}
// Add second moving barrier for level 3+
if (level >= 3) {
var movingField2 = game.addChild(new InterferenceField());
movingField2.x = 500;
movingField2.y = 2000;
movingField2.setDimension(1);
movingField2.moveDirection = -1;
movingField2.minX = 100;
movingField2.maxX = 1948;
interferenceFields.push(movingField2);
}
// Add third moving barrier for level 4+
if (level >= 4) {
var movingField3 = game.addChild(new InterferenceField());
movingField3.x = 1500;
movingField3.y = 1600;
movingField3.setDimension(0);
movingField3.moveDirection = 1;
movingField3.minX = 300;
movingField3.maxX = 1700;
interferenceFields.push(movingField3);
}
// Add fourth moving barrier for level 5+
if (level >= 5) {
var movingField4 = game.addChild(new InterferenceField());
movingField4.x = 800;
movingField4.y = 1800;
movingField4.setDimension(1);
movingField4.moveDirection = -1;
movingField4.minX = 200;
movingField4.maxX = 1800;
interferenceFields.push(movingField4);
}
// Advanced levels 6-10 with additional challenges
if (level >= 6) {
// Add more particles for higher levels
var extraParticles = Math.min(level - 5, 3);
for (var j = 0; j < extraParticles; j++) {
var extraParticle = game.addChild(new Particle());
extraParticle.x = 400 + j * 300;
extraParticle.y = 2200 + j % 2 * 200;
extraParticle.setDimension(j % totalDimensions);
extraParticle.lastCoreIntersecting = false;
extraParticle.isBeingDragged = false;
extraParticle.isCollected = false;
particles.push(extraParticle);
}
totalParticles += extraParticles;
// Add additional moving barriers
var numExtraFields = Math.min(level - 5, 4);
for (var k = 0; k < numExtraFields; k++) {
var extraField = game.addChild(new InterferenceField());
extraField.x = 200 + k * 400;
extraField.y = 1300 + k % 2 * 300;
extraField.setDimension(k % totalDimensions);
extraField.moveDirection = k % 2 === 0 ? 1 : -1;
extraField.minX = 100;
extraField.maxX = 1948;
interferenceFields.push(extraField);
}
}
// Level 8+ speed increase is now handled in the InterferenceField update method
// Level 10 gets entangled triplets
if (level >= 10 && particles.length >= 3) {
particles[0].entangledWith = particles[1];
particles[1].entangledWith = particles[2];
particles[2].entangledWith = particles[0];
}
// Advanced levels 11-15 with extreme challenges
if (level >= 11) {
// Add even more particles for extreme levels
var extremeParticles = Math.min(level - 10, 5);
for (var m = 0; m < extremeParticles; m++) {
var extremeParticle = game.addChild(new Particle());
extremeParticle.x = 150 + m * 250;
extremeParticle.y = 2400 + m % 2 * 150;
extremeParticle.setDimension(m % totalDimensions);
extremeParticle.lastCoreIntersecting = false;
extremeParticle.isBeingDragged = false;
extremeParticle.isCollected = false;
particles.push(extremeParticle);
}
totalParticles += extremeParticles;
// Add maze-like interference field patterns
var mazeFields = Math.min(level - 10, 6);
for (var n = 0; n < mazeFields; n++) {
var mazeField = game.addChild(new InterferenceField());
mazeField.x = 300 + n * 200;
mazeField.y = 1100 + n % 3 * 200;
mazeField.setDimension(n % totalDimensions);
mazeField.moveDirection = n % 2 === 0 ? 1 : -1;
mazeField.minX = 50;
mazeField.maxX = 1998;
interferenceFields.push(mazeField);
}
}
// Master levels 16-20 with ultimate difficulty
if (level >= 16) {
// Add master-level particles
var masterParticles = Math.min(level - 15, 4);
for (var p = 0; p < masterParticles; p++) {
var masterParticle = game.addChild(new Particle());
masterParticle.x = 200 + p * 400;
masterParticle.y = 2500 + p % 2 * 100;
masterParticle.setDimension(p % totalDimensions);
masterParticle.lastCoreIntersecting = false;
masterParticle.isBeingDragged = false;
masterParticle.isCollected = false;
particles.push(masterParticle);
}
totalParticles += masterParticles;
// Create complex entanglement networks
if (particles.length >= 4) {
for (var q = 0; q < Math.min(particles.length - 1, 6); q++) {
if (q + 1 < particles.length) {
particles[q].entangledWith = particles[q + 1];
}
}
}
// Add ultra-fast moving barriers
var ultraFields = Math.min(level - 15, 8);
for (var r = 0; r < ultraFields; r++) {
var ultraField = game.addChild(new InterferenceField());
ultraField.x = 100 + r * 180;
ultraField.y = 1200 + r % 4 * 150;
ultraField.setDimension(r % totalDimensions);
ultraField.moveDirection = r % 2 === 0 ? 1 : -1;
ultraField.minX = 50;
ultraField.maxX = 1998;
interferenceFields.push(ultraField);
}
}
// Calculate total particles correctly for all levels
totalParticles = particles.length;
}
updateDimensionDisplay();
if (level === 0) {
levelText.setText('Tutorial');
} else {
levelText.setText('Level: ' + level);
}
}
function updateDimensionDisplay() {
dimensionText.setText('Dimension: ' + currentDimension);
instructionText.setText('Switches: ' + dimensionSwitches + '/' + maxDimensionSwitches + ' - Tap to switch');
for (var i = 0; i < dimensionIndicators.length; i++) {
var indicator = dimensionIndicators[i];
tween(indicator, {
alpha: i === currentDimension ? 1.0 : 0.3,
scaleX: i === currentDimension ? 1.5 : 1.0,
scaleY: i === currentDimension ? 1.5 : 1.0
}, {
duration: 300,
easing: tween.easeOut
});
}
// Update all objects for dimension visibility
for (var i = 0; i < particles.length; i++) {
var targetAlpha = particles[i].dimension === currentDimension ? 1.0 : 0.15;
tween(particles[i], {
alpha: targetAlpha
}, {
duration: 200,
easing: tween.easeInOut
});
}
for (var i = 0; i < portals.length; i++) {
var targetAlpha = portals[i].dimension === currentDimension ? 1.0 : 0.1;
tween(portals[i], {
alpha: targetAlpha
}, {
duration: 200,
easing: tween.easeInOut
});
}
for (var i = 0; i < interferenceFields.length; i++) {
var targetAlpha = interferenceFields[i].dimension === currentDimension ? 0.8 : 0.1;
tween(interferenceFields[i], {
alpha: targetAlpha
}, {
duration: 200,
easing: tween.easeInOut
});
}
for (var i = 0; i < powerUps.length; i++) {
var targetAlpha = powerUps[i].dimension === currentDimension ? 1.0 : 0.15;
tween(powerUps[i], {
alpha: targetAlpha
}, {
duration: 200,
easing: tween.easeInOut
});
}
}
function switchDimension() {
if (dimensionSwitches >= maxDimensionSwitches && !isTutorial) {
LK.effects.flashScreen(0xFF0000, 200);
return; // No more switches allowed (except in tutorial)
}
dimensionSwitches++;
// Remove time penalty to make dimension switching more accessible
currentDimension = (currentDimension + 1) % totalDimensions;
updateDimensionDisplay();
LK.getSound('dimensionShift').play();
LK.effects.flashScreen(0x440088, 200);
// Tutorial progress tracking
if (isTutorial) {
if (tutorialStep === 3) {
tutorialStep = 4;
LK.setTimeout(function () {
updateTutorialStep();
}, 500);
} else if (tutorialStep === 4 && currentDimension === 1) {
// Player successfully switched to dimension 1
tutorialStep = 5;
LK.setTimeout(function () {
updateTutorialStep();
}, 1000);
}
}
}
function checkWinCondition() {
if (particlesCollected >= totalParticles) {
timerActive = false; // Stop timer when level complete
if (isTutorial) {
if (particlesCollected === 1 && tutorialStep <= 3) {
// First particle collected, advance tutorial
tutorialStep = 3;
updateTutorialStep();
return;
} else if (particlesCollected >= 2) {
// All particles collected in tutorial, complete it
if (tutorialStep < 6) {
tutorialStep = 6;
updateTutorialStep();
} else if (tutorialComplete || tutorialStep >= 10) {
// Tutorial is complete, move to level 1
level = 1;
isTutorial = false;
tutorialText.visible = false;
initializeLevel();
}
return;
}
}
level++;
LK.setTimeout(function () {
if (level > 20) {
LK.showYouWin();
} else {
initializeLevel();
}
}, 1000);
}
}
function resetLevel() {
// Check if shield is active to prevent death
if (shieldActive) {
shieldActive = false;
shieldTimeRemaining = 0;
shieldText.visible = false;
LK.effects.flashScreen(0x0088ff, 300);
return; // Shield absorbed the hit
}
LK.effects.flashScreen(0xff0000, 500);
LK.setTimeout(function () {
initializeLevel();
}, 600);
}
function spawnPowerUp() {
if (powerUps.length >= 2) return; // Maximum 2 power-ups on screen
var powerUp = game.addChild(new PowerUp());
// Ensure power-ups spawn in safe areas away from interference fields
var safePosition = false;
var attempts = 0;
var spawnX, spawnY;
while (!safePosition && attempts < 10) {
spawnX = 300 + Math.random() * 1448;
spawnY = 600 + Math.random() * 800;
// Check distance from interference fields
safePosition = true;
for (var f = 0; f < interferenceFields.length; f++) {
var field = interferenceFields[f];
var distance = Math.sqrt((spawnX - field.x) * (spawnX - field.x) + (spawnY - field.y) * (spawnY - field.y));
if (distance < 200) {
safePosition = false;
break;
}
}
attempts++;
}
powerUp.x = spawnX || 300 + Math.random() * 1448;
powerUp.y = spawnY || 600 + Math.random() * 800;
powerUp.setDimension(currentDimension); // Always spawn in current dimension for better accessibility
// Random power-up type
var types = ['timeBoost', 'shield', 'slowMotion'];
var randomType = types[Math.floor(Math.random() * types.length)];
powerUp.setType(randomType);
powerUp.lastPlayerIntersecting = false;
powerUps.push(powerUp);
}
// Event handlers
game.down = function (x, y, obj) {
var hitParticle = false;
for (var i = 0; i < particles.length; i++) {
var particle = particles[i];
if (particle.dimension === currentDimension && !particle.isCollected && particle.alpha > 0.5) {
// Use actual asset dimensions for accurate touch detection
var halfWidth = particle.children[0].width / 2; // Use actual particle asset width
var halfHeight = particle.children[0].height / 2; // Use actual particle asset height
// Check if touch point is within particle bounds
if (x >= particle.x - halfWidth && x <= particle.x + halfWidth && y >= particle.y - halfHeight && y <= particle.y + halfHeight) {
draggedParticle = particle;
particle.startDrag();
dragOffset.x = x - particle.x;
dragOffset.y = y - particle.y;
hitParticle = true;
break;
}
}
}
if (!hitParticle) {
switchDimension();
}
};
game.move = function (x, y, obj) {
if (draggedParticle && !draggedParticle.isCollected) {
var targetX = x - dragOffset.x;
var targetY = y - dragOffset.y;
// Keep particle within bounds
targetX = Math.max(80, Math.min(1968, targetX));
targetY = Math.max(80, Math.min(2652, targetY));
// Direct position update for responsive dragging
draggedParticle.x = targetX;
draggedParticle.y = targetY;
// Reduce trail effect frequency to improve performance
if (LK.ticks % 10 === 0) {
var trailStar = game.addChild(new BackgroundStar());
trailStar.x = draggedParticle.x + (Math.random() - 0.5) * 20;
trailStar.y = draggedParticle.y + (Math.random() - 0.5) * 20;
trailStar.scaleX = 0.8;
trailStar.scaleY = 0.8;
trailStar.alpha = 0.8;
// Fade out trail particle
tween(trailStar, {
alpha: 0,
scaleX: 0.1,
scaleY: 0.1
}, {
duration: 1000,
easing: tween.easeOut,
onFinish: function onFinish() {
trailStar.destroy();
}
});
}
// Handle entangled particle movement with direct updates
if (draggedParticle.entangledWith) {
// Only move entangled particles when BOTH the dragged particle AND the entangled particle are in the current dimension
// This prevents cross-dimensional interference where particles in other dimensions move unexpectedly
if (draggedParticle.dimension === currentDimension && draggedParticle.entangledWith.dimension === currentDimension) {
draggedParticle.entangledWith.x = targetX + 150;
draggedParticle.entangledWith.y = targetY;
}
// Ensure entangled particles maintain proper alpha based on current dimension
var entangledTargetAlpha = draggedParticle.entangledWith.dimension === currentDimension ? 1.0 : 0.15;
draggedParticle.entangledWith.alpha = entangledTargetAlpha;
}
}
};
game.up = function (x, y, obj) {
if (draggedParticle) {
draggedParticle.stopDrag();
draggedParticle = null;
}
};
game.update = function () {
// Handle timer countdown
if (timerActive) {
var timeDecrement = slowMotionActive ? 8.33 : 16.67; // Slow motion halves time consumption
timeRemaining -= timeDecrement;
if (timeRemaining <= 0) {
resetLevel();
return;
}
var seconds = Math.ceil(timeRemaining / 1000);
timerText.setText('Time: ' + seconds + 's');
// Smooth color transitions when time is running out
if (seconds <= 5) {
tween(timerText, {
tint: 0xFF0000
}, {
duration: 200,
easing: tween.easeOut
});
} else if (seconds <= 10) {
tween(timerText, {
tint: 0xFFFF00
}, {
duration: 200,
easing: tween.easeOut
});
} else {
tween(timerText, {
tint: 0xFFFFFF
}, {
duration: 200,
easing: tween.easeOut
});
}
}
// Animate quantum core with direct property updates
if (quantumCore) {
// Direct rotation update
quantumCore.rotation += 0.02;
// Direct pulsing animation
var pulse = Math.sin(LK.ticks * 0.08) * 0.15 + 1.0;
quantumCore.scaleX = pulse;
quantumCore.scaleY = pulse;
// Reduced frequency color cycling
if (LK.ticks % 60 === 0) {
var colorPhase = LK.ticks * 0.015;
var r = Math.sin(colorPhase) * 0.4 + 0.6;
var g = Math.sin(colorPhase + 2) * 0.4 + 0.6;
var b = Math.sin(colorPhase + 4) * 0.4 + 0.6;
var color = Math.floor(r * 255) << 16 | Math.floor(g * 255) << 8 | Math.floor(b * 255);
quantumCore.tint = color;
}
}
// Update all particles
for (var i = 0; i < particles.length; i++) {
if (particles[i].update) {
particles[i].update();
}
}
// Update all portals
for (var i = 0; i < portals.length; i++) {
if (portals[i].update) {
portals[i].update();
}
}
// Update all interference fields
for (var i = 0; i < interferenceFields.length; i++) {
if (interferenceFields[i].update) {
interferenceFields[i].update();
}
}
// Handle power-up spawning
if (timerActive) {
powerUpSpawnTimer += 16.67;
// Calculate dynamic spawn interval based on level - more frequent power-ups
var dynamicSpawnInterval = powerUpSpawnInterval;
if (level >= 5) {
dynamicSpawnInterval = Math.max(3000, powerUpSpawnInterval - (level - 4) * 300); // Faster spawning for higher levels, minimum 3 seconds (reduced from 4)
}
if (powerUpSpawnTimer >= dynamicSpawnInterval) {
spawnPowerUp();
powerUpSpawnTimer = 0;
}
}
// Handle shield duration
if (shieldActive) {
shieldTimeRemaining -= 16.67;
if (shieldTimeRemaining <= 0) {
shieldActive = false;
shieldText.visible = false;
} else {
shieldText.visible = true;
shieldText.setText('SHIELD: ' + Math.ceil(shieldTimeRemaining / 1000) + 's');
}
}
// Handle slow motion duration
if (slowMotionActive) {
slowMotionTimeRemaining -= 16.67;
if (slowMotionTimeRemaining <= 0) {
slowMotionActive = false;
slowMotionText.visible = false;
} else {
slowMotionText.visible = true;
slowMotionText.setText('SLOW MOTION: ' + Math.ceil(slowMotionTimeRemaining / 1000) + 's');
}
}
// Update power-ups
for (var i = powerUps.length - 1; i >= 0; i--) {
if (powerUps[i].update) {
powerUps[i].update();
}
// Remove collected power-ups
if (powerUps[i].isCollected && !powerUps[i].visible) {
powerUps[i].destroy();
powerUps.splice(i, 1);
}
}
// Update background stars
for (var i = 0; i < backgroundStars.length; i++) {
var star = backgroundStars[i];
if (star.update) {
star.update();
}
// Handle orbital motion for core particles
if (star.orbitalAngle !== undefined && quantumCore) {
star.orbitalAngle += star.orbitalSpeed;
star.x = quantumCore.x + Math.cos(star.orbitalAngle) * star.orbitalRadius;
star.y = quantumCore.y + Math.sin(star.orbitalAngle) * star.orbitalRadius;
}
}
};
function updateTutorialStep() {
if (!isTutorial) return;
// Ensure tutorial text is visible and properly positioned
tutorialText.visible = true;
tutorialText.alpha = 1.0;
// Position tutorial text in center-upper area for better visibility
tutorialText.x = 1024;
tutorialText.y = 600;
// Ensure text is on top and visible
game.removeChild(tutorialText);
game.addChild(tutorialText);
switch (tutorialStep) {
case 0:
tutorialText.setText('Welcome to Quantum Dimensions!\nYou control particles across multiple dimensions.');
LK.setTimeout(function () {
tutorialStep = 1;
updateTutorialStep();
}, 3000);
break;
case 1:
tutorialText.setText('See the glowing particle? Touch and drag it.\nThis is how you move particles in the quantum field.');
// Add visual hint by pulsing the particle
if (particles.length > 0 && particles[0].dimension === currentDimension) {
LK.effects.flashObject(particles[0], 0x00ff00, 1000);
}
break;
case 2:
tutorialText.setText('Excellent! Now drag it to the quantum core (center).\nParticles must reach the core to be collected.');
// Add visual hint by flashing the quantum core
if (quantumCore) {
LK.effects.flashObject(quantumCore, 0x00ffff, 1500);
}
break;
case 3:
tutorialText.setText('Perfect! You collected your first particle!\nNow tap anywhere (empty space) to switch dimensions.');
break;
case 4:
tutorialText.setText('Great! Notice how the view changed?\nYou just switched to Dimension 1. See the second particle?');
if (particles.length > 1 && particles[1].dimension === currentDimension) {
LK.effects.flashObject(particles[1], 0x00ff00, 1000);
}
LK.setTimeout(function () {
tutorialStep = 5;
updateTutorialStep();
}, 3000);
break;
case 5:
tutorialText.setText('Now collect this second particle!\nDrag it to the quantum core too.');
if (particles.length > 1 && particles[1].dimension === currentDimension) {
LK.effects.flashObject(particles[1], 0x00ff00, 1000);
}
break;
case 6:
tutorialText.setText('Excellent! You have learned the basics.\nIn real levels, you have limited dimension switches!');
LK.setTimeout(function () {
tutorialStep = 7;
updateTutorialStep();
}, 3000);
break;
case 7:
tutorialText.setText('Watch out for red interference fields - they reset the level!\nAvoid them while moving particles.');
LK.setTimeout(function () {
tutorialStep = 8;
updateTutorialStep();
}, 3000);
break;
case 8:
tutorialText.setText('Blue portals transport particles between dimensions.\nUse them strategically!');
LK.setTimeout(function () {
tutorialStep = 9;
updateTutorialStep();
}, 3000);
break;
case 9:
tutorialText.setText('Power-ups help you: Time Boost (+15s), Shield (protection),\nand Slow Motion (easier movement).');
LK.setTimeout(function () {
tutorialStep = 10;
updateTutorialStep();
}, 4000);
break;
case 10:
tutorialText.setText('Tutorial Complete! Ready for the challenge?\nStarting Level 1...');
LK.setTimeout(function () {
tutorialComplete = true;
checkWinCondition(); // Use existing function to transition properly
}, 3000);
break;
}
}
function showPowerUpSpec(title, description, color) {
// Create power-up specification display
var specContainer = new Container();
// Title text
var titleText = new Text2(title, {
size: 60,
fill: color
});
titleText.anchor.set(0.5, 0.5);
titleText.x = 1024;
titleText.y = 1300;
specContainer.addChild(titleText);
// Description text
var descText = new Text2(description, {
size: 45,
fill: 0xFFFFFF
});
descText.anchor.set(0.5, 0.5);
descText.x = 1024;
descText.y = 1380;
specContainer.addChild(descText);
// Add to game
game.addChild(specContainer);
// Initial state
specContainer.alpha = 0;
specContainer.scaleX = 0.3;
specContainer.scaleY = 0.3;
// Animation: fade in and scale up
tween(specContainer, {
alpha: 1.0,
scaleX: 1.0,
scaleY: 1.0
}, {
duration: 300,
easing: tween.easeOut,
onFinish: function onFinish() {
// Hold for a moment then fade out
LK.setTimeout(function () {
tween(specContainer, {
alpha: 0,
scaleX: 0.8,
scaleY: 0.8
}, {
duration: 400,
easing: tween.easeIn,
onFinish: function onFinish() {
specContainer.destroy();
}
});
}, 2000);
}
});
}
// Initialize first level
initializeLevel(); ===================================================================
--- original.js
+++ change.js
@@ -156,13 +156,13 @@
}
// Check collision with quantum core - only trigger on first contact
var currentCoreIntersecting = false;
if (self.dimension === currentDimension && quantumCore) {
- // Use proper bounds checking for accurate collision detection
- var particleHalfWidth = 70; // Half of particle asset width (140/2)
- var particleHalfHeight = 70; // Half of particle asset height (140/2)
- var coreHalfWidth = 125; // Half of quantum core asset width (250/2)
- var coreHalfHeight = 125; // Half of quantum core asset height (250/2)
+ // Use actual asset dimensions for accurate collision detection
+ var particleHalfWidth = particleGraphics.width / 2; // Use actual particle asset width
+ var particleHalfHeight = particleGraphics.height / 2; // Use actual particle asset height
+ var coreHalfWidth = quantumCore.width / 2; // Use actual quantum core asset width
+ var coreHalfHeight = quantumCore.height / 2; // Use actual quantum core asset height
currentCoreIntersecting = Math.abs(self.x - quantumCore.x) < particleHalfWidth + coreHalfWidth && Math.abs(self.y - quantumCore.y) < particleHalfHeight + coreHalfHeight;
}
if (!self.lastCoreIntersecting && currentCoreIntersecting) {
self.collect();
@@ -174,13 +174,13 @@
// Check collision with interference fields
for (var i = 0; i < interferenceFields.length; i++) {
var field = interferenceFields[i];
if (field.dimension === self.dimension) {
- // Use proper bounds checking for accurate collision detection
- var particleHalfWidth = 70; // Half of particle asset width (140/2)
- var particleHalfHeight = 70; // Half of particle asset height (140/2)
- var fieldHalfWidth = 75; // Half of interference field asset width (150/2)
- var fieldHalfHeight = 75; // Half of interference field asset height (150/2)
+ // Use actual asset dimensions for accurate collision detection
+ var particleHalfWidth = particleGraphics.width / 2; // Use actual particle asset width
+ var particleHalfHeight = particleGraphics.height / 2; // Use actual particle asset height
+ var fieldHalfWidth = field.children[0].width / 2; // Use actual interference field asset width
+ var fieldHalfHeight = field.children[0].height / 2; // Use actual interference field asset height
var isColliding = Math.abs(self.x - field.x) < particleHalfWidth + fieldHalfWidth && Math.abs(self.y - field.y) < particleHalfHeight + fieldHalfHeight;
if (isColliding) {
if (isTutorial) {
// In tutorial, just show educational message instead of resetting
@@ -227,13 +227,13 @@
// Check if particles are transported through portal
for (var i = 0; i < particles.length; i++) {
var particle = particles[i];
if (particle.dimension === self.dimension && !particle.isBeingDragged) {
- // Use proper bounds checking for accurate collision detection
- var portalHalfWidth = 100; // Half of portal asset width (200/2)
- var portalHalfHeight = 100; // Half of portal asset height (200/2)
- var particleHalfWidth = 70; // Half of particle asset width (140/2)
- var particleHalfHeight = 70; // Half of particle asset height (140/2)
+ // Use actual asset dimensions for accurate collision detection
+ var portalHalfWidth = portalGraphics.width / 2; // Use actual portal asset width
+ var portalHalfHeight = portalGraphics.height / 2; // Use actual portal asset height
+ var particleHalfWidth = particle.children[0].width / 2; // Use actual particle asset width
+ var particleHalfHeight = particle.children[0].height / 2; // Use actual particle asset height
var isColliding = Math.abs(self.x - particle.x) < portalHalfWidth + particleHalfWidth && Math.abs(self.y - particle.y) < portalHalfHeight + particleHalfHeight;
if (isColliding) {
particle.setDimension(self.targetDimension);
LK.getSound('portalSound').play();
@@ -336,13 +336,13 @@
var currentPlayerIntersecting = false;
for (var p = 0; p < particles.length; p++) {
var particle = particles[p];
if (particle.dimension === self.dimension && particle.dimension === currentDimension && !particle.isCollected) {
- // Use proper bounds checking for more accurate collision detection
- var powerUpHalfWidth = 45; // Half of power-up asset width (90/2 average)
- var powerUpHalfHeight = 45; // Half of power-up asset height (90/2 average)
- var particleHalfWidth = 70; // Half of particle asset width (140/2)
- var particleHalfHeight = 70; // Half of particle asset height (140/2)
+ // Use actual asset dimensions for accurate collision detection
+ var powerUpHalfWidth = self.powerUpGraphics.width / 2; // Use actual power-up asset width
+ var powerUpHalfHeight = self.powerUpGraphics.height / 2; // Use actual power-up asset height
+ var particleHalfWidth = particle.children[0].width / 2; // Use actual particle asset width
+ var particleHalfHeight = particle.children[0].height / 2; // Use actual particle asset height
var isColliding = Math.abs(self.x - particle.x) < powerUpHalfWidth + particleHalfWidth && Math.abs(self.y - particle.y) < powerUpHalfHeight + particleHalfHeight;
if (isColliding) {
currentPlayerIntersecting = true;
break;
@@ -983,11 +983,11 @@
var hitParticle = false;
for (var i = 0; i < particles.length; i++) {
var particle = particles[i];
if (particle.dimension === currentDimension && !particle.isCollected && particle.alpha > 0.5) {
- // Use proper bounds checking based on particle's actual asset dimensions
- var halfWidth = 70; // Half of particle asset width (140/2)
- var halfHeight = 70; // Half of particle asset height (140/2)
+ // Use actual asset dimensions for accurate touch detection
+ var halfWidth = particle.children[0].width / 2; // Use actual particle asset width
+ var halfHeight = particle.children[0].height / 2; // Use actual particle asset height
// Check if touch point is within particle bounds
if (x >= particle.x - halfWidth && x <= particle.x + halfWidth && y >= particle.y - halfHeight && y <= particle.y + halfHeight) {
draggedParticle = particle;
particle.startDrag();