/****
* Plugins
****/
var tween = LK.import("@upit/tween.v1");
/****
* Classes
****/
var Candy = Container.expand(function (type) {
var self = Container.call(this);
self.type = type;
self.gridX = 0;
self.gridY = 0;
self.isAnimating = false;
var candyGraphics = self.attachAsset('candy_' + type, {
anchorX: 0.5,
anchorY: 0.5
});
self.setGridPosition = function (gridX, gridY) {
self.gridX = gridX;
self.gridY = gridY;
var targetX = gridStartX + gridX * cellSize + cellSize / 2;
var targetY = gridStartY + gridY * cellSize + cellSize / 2;
self.x = targetX;
self.y = targetY;
};
self.animateToPosition = function (targetX, targetY, duration, onComplete) {
self.isAnimating = true;
tween(self, {
x: targetX,
y: targetY
}, {
duration: duration || 300,
easing: tween.easeOut,
onFinish: function onFinish() {
self.isAnimating = false;
if (onComplete) onComplete();
}
});
};
self.animateToGridPosition = function (gridX, gridY, duration, onComplete) {
self.gridX = gridX;
self.gridY = gridY;
var targetX = gridStartX + gridX * cellSize + cellSize / 2;
var targetY = gridStartY + gridY * cellSize + cellSize / 2;
self.animateToPosition(targetX, targetY, duration, onComplete);
};
return self;
});
/****
* Initialize Game
****/
var game = new LK.Game({
backgroundColor: 0x2E8B57
});
/****
* Game Code
****/
var GRID_SIZE = 8;
var candyTypes = ['red', 'blue', 'green', 'yellow', 'purple', 'orange'];
var cellSize = 90;
var gridStartX = (2048 - GRID_SIZE * cellSize) / 2;
var gridStartY = (2732 - GRID_SIZE * cellSize) / 2;
var grid = [];
var selectedCandy = null;
var isProcessing = false;
var movesLeft = 30;
var targetScore = 1000;
var animatingCandies = 0;
// Initialize grid array
for (var i = 0; i < GRID_SIZE; i++) {
grid[i] = [];
for (var j = 0; j < GRID_SIZE; j++) {
grid[i][j] = null;
}
}
// UI Elements
var scoreText = new Text2('Score: 0', {
size: 60,
fill: 0xFFFFFF
});
scoreText.anchor.set(0.5, 0);
scoreText.x = 0;
scoreText.y = 100;
LK.gui.top.addChild(scoreText);
var movesText = new Text2('Moves: ' + movesLeft, {
size: 60,
fill: 0xFFFFFF
});
movesText.anchor.set(0.5, 0);
movesText.x = 0;
movesText.y = 200;
LK.gui.top.addChild(movesText);
var targetText = new Text2('Target: ' + targetScore, {
size: 50,
fill: 0xFFFF00
});
targetText.anchor.set(0.5, 0);
targetText.x = 0;
targetText.y = 300;
LK.gui.top.addChild(targetText);
// Create grid background
var gridBg = game.attachAsset('grid_bg', {
anchorX: 0.5,
anchorY: 0.5,
x: 2048 / 2,
y: 2732 / 2
});
// Create cell backgrounds
for (var i = 0; i < GRID_SIZE; i++) {
for (var j = 0; j < GRID_SIZE; j++) {
var cellBg = game.attachAsset('cell_bg', {
anchorX: 0.5,
anchorY: 0.5,
x: gridStartX + i * cellSize + cellSize / 2,
y: gridStartY + j * cellSize + cellSize / 2
});
}
}
function getRandomCandyType() {
return candyTypes[Math.floor(Math.random() * candyTypes.length)];
}
function createCandy(type, gridX, gridY) {
var candy = new Candy(type);
candy.setGridPosition(gridX, gridY);
game.addChild(candy);
return candy;
}
function fillGrid() {
for (var x = 0; x < GRID_SIZE; x++) {
for (var y = 0; y < GRID_SIZE; y++) {
if (!grid[x][y]) {
var type = getRandomCandyType();
grid[x][y] = createCandy(type, x, y);
}
}
}
}
function isValidPosition(x, y) {
return x >= 0 && x < GRID_SIZE && y >= 0 && y < GRID_SIZE;
}
function areAdjacent(x1, y1, x2, y2) {
var dx = Math.abs(x1 - x2);
var dy = Math.abs(y1 - y2);
return dx === 1 && dy === 0 || dx === 0 && dy === 1;
}
function swapCandies(x1, y1, x2, y2) {
var candy1 = grid[x1][y1];
var candy2 = grid[x2][y2];
grid[x1][y1] = candy2;
grid[x2][y2] = candy1;
animatingCandies += 2;
candy1.animateToGridPosition(x2, y2, 200, function () {
animatingCandies--;
});
candy2.animateToGridPosition(x1, y1, 200, function () {
animatingCandies--;
});
}
function findMatches() {
var matches = [];
var visited = [];
for (var i = 0; i < GRID_SIZE; i++) {
visited[i] = [];
for (var j = 0; j < GRID_SIZE; j++) {
visited[i][j] = false;
}
}
// Check horizontal matches
for (var y = 0; y < GRID_SIZE; y++) {
for (var x = 0; x < GRID_SIZE - 2; x++) {
if (grid[x][y] && grid[x + 1][y] && grid[x + 2][y] && grid[x][y].type === grid[x + 1][y].type && grid[x][y].type === grid[x + 2][y].type) {
var match = [];
var type = grid[x][y].type;
var startX = x;
while (x < GRID_SIZE && grid[x][y] && grid[x][y].type === type) {
if (!visited[x][y]) {
match.push({
x: x,
y: y
});
visited[x][y] = true;
}
x++;
}
x--;
if (match.length >= 3) {
matches.push(match);
}
}
}
}
// Check vertical matches
for (var x = 0; x < GRID_SIZE; x++) {
for (var y = 0; y < GRID_SIZE - 2; y++) {
if (grid[x][y] && grid[x][y + 1] && grid[x][y + 2] && grid[x][y].type === grid[x][y + 1].type && grid[x][y].type === grid[x][y + 2].type) {
var match = [];
var type = grid[x][y].type;
var startY = y;
while (y < GRID_SIZE && grid[x][y] && grid[x][y].type === type) {
if (!visited[x][y]) {
match.push({
x: x,
y: y
});
visited[x][y] = true;
}
y++;
}
y--;
if (match.length >= 3) {
matches.push(match);
}
}
}
}
return matches;
}
function clearMatches(matches) {
var totalCleared = 0;
for (var i = 0; i < matches.length; i++) {
var match = matches[i];
for (var j = 0; j < match.length; j++) {
var pos = match[j];
if (grid[pos.x][pos.y]) {
grid[pos.x][pos.y].destroy();
grid[pos.x][pos.y] = null;
totalCleared++;
}
}
}
if (totalCleared > 0) {
LK.getSound('match').play();
LK.setScore(LK.getScore() + totalCleared * 10);
scoreText.setText('Score: ' + LK.getScore());
}
return totalCleared;
}
function applyGravity() {
var moved = false;
for (var x = 0; x < GRID_SIZE; x++) {
for (var y = GRID_SIZE - 1; y >= 0; y--) {
if (!grid[x][y]) {
// Find candy above to fall down
for (var above = y - 1; above >= 0; above--) {
if (grid[x][above]) {
grid[x][y] = grid[x][above];
grid[x][above] = null;
animatingCandies++;
grid[x][y].animateToGridPosition(x, y, 300, function () {
animatingCandies--;
});
moved = true;
break;
}
}
}
}
}
return moved;
}
function fillEmptySpaces() {
for (var x = 0; x < GRID_SIZE; x++) {
for (var y = 0; y < GRID_SIZE; y++) {
if (!grid[x][y]) {
var type = getRandomCandyType();
grid[x][y] = createCandy(type, x, y - GRID_SIZE);
animatingCandies++;
grid[x][y].animateToGridPosition(x, y, 400, function () {
animatingCandies--;
});
}
}
}
}
function processMatches() {
if (isProcessing || animatingCandies > 0) return;
var matches = findMatches();
if (matches.length > 0) {
isProcessing = true;
clearMatches(matches);
LK.setTimeout(function () {
applyGravity();
LK.setTimeout(function () {
fillEmptySpaces();
LK.setTimeout(function () {
isProcessing = false;
}, 500);
}, 400);
}, 200);
}
}
function getCandyAtPosition(x, y) {
var localX = x - gridStartX;
var localY = y - gridStartY;
if (localX < 0 || localY < 0 || localX >= GRID_SIZE * cellSize || localY >= GRID_SIZE * cellSize) {
return null;
}
var gridX = Math.floor(localX / cellSize);
var gridY = Math.floor(localY / cellSize);
return grid[gridX][gridY];
}
function getGridPosition(x, y) {
var localX = x - gridStartX;
var localY = y - gridStartY;
if (localX < 0 || localY < 0 || localX >= GRID_SIZE * cellSize || localY >= GRID_SIZE * cellSize) {
return null;
}
var gridX = Math.floor(localX / cellSize);
var gridY = Math.floor(localY / cellSize);
return {
x: gridX,
y: gridY
};
}
function checkWinCondition() {
if (LK.getScore() >= targetScore) {
LK.showYouWin();
} else if (movesLeft <= 0) {
LK.showGameOver();
}
}
game.down = function (x, y, obj) {
if (isProcessing || animatingCandies > 0) return;
var candy = getCandyAtPosition(x, y);
if (candy) {
if (selectedCandy) {
selectedCandy.alpha = 1.0;
}
selectedCandy = candy;
selectedCandy.alpha = 0.7;
LK.getSound('swap').play();
}
};
game.up = function (x, y, obj) {
if (isProcessing || animatingCandies > 0) return;
var candy = getCandyAtPosition(x, y);
if (selectedCandy && candy && selectedCandy !== candy) {
var pos1 = {
x: selectedCandy.gridX,
y: selectedCandy.gridY
};
var pos2 = {
x: candy.gridX,
y: candy.gridY
};
if (areAdjacent(pos1.x, pos1.y, pos2.x, pos2.y)) {
// Test swap
var temp = grid[pos1.x][pos1.y];
grid[pos1.x][pos1.y] = grid[pos2.x][pos2.y];
grid[pos2.x][pos2.y] = temp;
var matches = findMatches();
// Revert test swap
grid[pos2.x][pos2.y] = grid[pos1.x][pos1.y];
grid[pos1.x][pos1.y] = temp;
if (matches.length > 0) {
swapCandies(pos1.x, pos1.y, pos2.x, pos2.y);
movesLeft--;
movesText.setText('Moves: ' + movesLeft);
LK.setTimeout(function () {
processMatches();
}, 250);
}
}
selectedCandy.alpha = 1.0;
selectedCandy = null;
} else if (selectedCandy) {
selectedCandy.alpha = 1.0;
selectedCandy = null;
}
};
game.update = function () {
if (animatingCandies === 0 && !isProcessing) {
processMatches();
checkWinCondition();
}
};
// Initialize the game
fillGrid(); ===================================================================
--- original.js
+++ change.js
@@ -1,6 +1,381 @@
-/****
+/****
+* Plugins
+****/
+var tween = LK.import("@upit/tween.v1");
+
+/****
+* Classes
+****/
+var Candy = Container.expand(function (type) {
+ var self = Container.call(this);
+ self.type = type;
+ self.gridX = 0;
+ self.gridY = 0;
+ self.isAnimating = false;
+ var candyGraphics = self.attachAsset('candy_' + type, {
+ anchorX: 0.5,
+ anchorY: 0.5
+ });
+ self.setGridPosition = function (gridX, gridY) {
+ self.gridX = gridX;
+ self.gridY = gridY;
+ var targetX = gridStartX + gridX * cellSize + cellSize / 2;
+ var targetY = gridStartY + gridY * cellSize + cellSize / 2;
+ self.x = targetX;
+ self.y = targetY;
+ };
+ self.animateToPosition = function (targetX, targetY, duration, onComplete) {
+ self.isAnimating = true;
+ tween(self, {
+ x: targetX,
+ y: targetY
+ }, {
+ duration: duration || 300,
+ easing: tween.easeOut,
+ onFinish: function onFinish() {
+ self.isAnimating = false;
+ if (onComplete) onComplete();
+ }
+ });
+ };
+ self.animateToGridPosition = function (gridX, gridY, duration, onComplete) {
+ self.gridX = gridX;
+ self.gridY = gridY;
+ var targetX = gridStartX + gridX * cellSize + cellSize / 2;
+ var targetY = gridStartY + gridY * cellSize + cellSize / 2;
+ self.animateToPosition(targetX, targetY, duration, onComplete);
+ };
+ return self;
+});
+
+/****
* Initialize Game
-****/
+****/
var game = new LK.Game({
- backgroundColor: 0x000000
-});
\ No newline at end of file
+ backgroundColor: 0x2E8B57
+});
+
+/****
+* Game Code
+****/
+var GRID_SIZE = 8;
+var candyTypes = ['red', 'blue', 'green', 'yellow', 'purple', 'orange'];
+var cellSize = 90;
+var gridStartX = (2048 - GRID_SIZE * cellSize) / 2;
+var gridStartY = (2732 - GRID_SIZE * cellSize) / 2;
+var grid = [];
+var selectedCandy = null;
+var isProcessing = false;
+var movesLeft = 30;
+var targetScore = 1000;
+var animatingCandies = 0;
+// Initialize grid array
+for (var i = 0; i < GRID_SIZE; i++) {
+ grid[i] = [];
+ for (var j = 0; j < GRID_SIZE; j++) {
+ grid[i][j] = null;
+ }
+}
+// UI Elements
+var scoreText = new Text2('Score: 0', {
+ size: 60,
+ fill: 0xFFFFFF
+});
+scoreText.anchor.set(0.5, 0);
+scoreText.x = 0;
+scoreText.y = 100;
+LK.gui.top.addChild(scoreText);
+var movesText = new Text2('Moves: ' + movesLeft, {
+ size: 60,
+ fill: 0xFFFFFF
+});
+movesText.anchor.set(0.5, 0);
+movesText.x = 0;
+movesText.y = 200;
+LK.gui.top.addChild(movesText);
+var targetText = new Text2('Target: ' + targetScore, {
+ size: 50,
+ fill: 0xFFFF00
+});
+targetText.anchor.set(0.5, 0);
+targetText.x = 0;
+targetText.y = 300;
+LK.gui.top.addChild(targetText);
+// Create grid background
+var gridBg = game.attachAsset('grid_bg', {
+ anchorX: 0.5,
+ anchorY: 0.5,
+ x: 2048 / 2,
+ y: 2732 / 2
+});
+// Create cell backgrounds
+for (var i = 0; i < GRID_SIZE; i++) {
+ for (var j = 0; j < GRID_SIZE; j++) {
+ var cellBg = game.attachAsset('cell_bg', {
+ anchorX: 0.5,
+ anchorY: 0.5,
+ x: gridStartX + i * cellSize + cellSize / 2,
+ y: gridStartY + j * cellSize + cellSize / 2
+ });
+ }
+}
+function getRandomCandyType() {
+ return candyTypes[Math.floor(Math.random() * candyTypes.length)];
+}
+function createCandy(type, gridX, gridY) {
+ var candy = new Candy(type);
+ candy.setGridPosition(gridX, gridY);
+ game.addChild(candy);
+ return candy;
+}
+function fillGrid() {
+ for (var x = 0; x < GRID_SIZE; x++) {
+ for (var y = 0; y < GRID_SIZE; y++) {
+ if (!grid[x][y]) {
+ var type = getRandomCandyType();
+ grid[x][y] = createCandy(type, x, y);
+ }
+ }
+ }
+}
+function isValidPosition(x, y) {
+ return x >= 0 && x < GRID_SIZE && y >= 0 && y < GRID_SIZE;
+}
+function areAdjacent(x1, y1, x2, y2) {
+ var dx = Math.abs(x1 - x2);
+ var dy = Math.abs(y1 - y2);
+ return dx === 1 && dy === 0 || dx === 0 && dy === 1;
+}
+function swapCandies(x1, y1, x2, y2) {
+ var candy1 = grid[x1][y1];
+ var candy2 = grid[x2][y2];
+ grid[x1][y1] = candy2;
+ grid[x2][y2] = candy1;
+ animatingCandies += 2;
+ candy1.animateToGridPosition(x2, y2, 200, function () {
+ animatingCandies--;
+ });
+ candy2.animateToGridPosition(x1, y1, 200, function () {
+ animatingCandies--;
+ });
+}
+function findMatches() {
+ var matches = [];
+ var visited = [];
+ for (var i = 0; i < GRID_SIZE; i++) {
+ visited[i] = [];
+ for (var j = 0; j < GRID_SIZE; j++) {
+ visited[i][j] = false;
+ }
+ }
+ // Check horizontal matches
+ for (var y = 0; y < GRID_SIZE; y++) {
+ for (var x = 0; x < GRID_SIZE - 2; x++) {
+ if (grid[x][y] && grid[x + 1][y] && grid[x + 2][y] && grid[x][y].type === grid[x + 1][y].type && grid[x][y].type === grid[x + 2][y].type) {
+ var match = [];
+ var type = grid[x][y].type;
+ var startX = x;
+ while (x < GRID_SIZE && grid[x][y] && grid[x][y].type === type) {
+ if (!visited[x][y]) {
+ match.push({
+ x: x,
+ y: y
+ });
+ visited[x][y] = true;
+ }
+ x++;
+ }
+ x--;
+ if (match.length >= 3) {
+ matches.push(match);
+ }
+ }
+ }
+ }
+ // Check vertical matches
+ for (var x = 0; x < GRID_SIZE; x++) {
+ for (var y = 0; y < GRID_SIZE - 2; y++) {
+ if (grid[x][y] && grid[x][y + 1] && grid[x][y + 2] && grid[x][y].type === grid[x][y + 1].type && grid[x][y].type === grid[x][y + 2].type) {
+ var match = [];
+ var type = grid[x][y].type;
+ var startY = y;
+ while (y < GRID_SIZE && grid[x][y] && grid[x][y].type === type) {
+ if (!visited[x][y]) {
+ match.push({
+ x: x,
+ y: y
+ });
+ visited[x][y] = true;
+ }
+ y++;
+ }
+ y--;
+ if (match.length >= 3) {
+ matches.push(match);
+ }
+ }
+ }
+ }
+ return matches;
+}
+function clearMatches(matches) {
+ var totalCleared = 0;
+ for (var i = 0; i < matches.length; i++) {
+ var match = matches[i];
+ for (var j = 0; j < match.length; j++) {
+ var pos = match[j];
+ if (grid[pos.x][pos.y]) {
+ grid[pos.x][pos.y].destroy();
+ grid[pos.x][pos.y] = null;
+ totalCleared++;
+ }
+ }
+ }
+ if (totalCleared > 0) {
+ LK.getSound('match').play();
+ LK.setScore(LK.getScore() + totalCleared * 10);
+ scoreText.setText('Score: ' + LK.getScore());
+ }
+ return totalCleared;
+}
+function applyGravity() {
+ var moved = false;
+ for (var x = 0; x < GRID_SIZE; x++) {
+ for (var y = GRID_SIZE - 1; y >= 0; y--) {
+ if (!grid[x][y]) {
+ // Find candy above to fall down
+ for (var above = y - 1; above >= 0; above--) {
+ if (grid[x][above]) {
+ grid[x][y] = grid[x][above];
+ grid[x][above] = null;
+ animatingCandies++;
+ grid[x][y].animateToGridPosition(x, y, 300, function () {
+ animatingCandies--;
+ });
+ moved = true;
+ break;
+ }
+ }
+ }
+ }
+ }
+ return moved;
+}
+function fillEmptySpaces() {
+ for (var x = 0; x < GRID_SIZE; x++) {
+ for (var y = 0; y < GRID_SIZE; y++) {
+ if (!grid[x][y]) {
+ var type = getRandomCandyType();
+ grid[x][y] = createCandy(type, x, y - GRID_SIZE);
+ animatingCandies++;
+ grid[x][y].animateToGridPosition(x, y, 400, function () {
+ animatingCandies--;
+ });
+ }
+ }
+ }
+}
+function processMatches() {
+ if (isProcessing || animatingCandies > 0) return;
+ var matches = findMatches();
+ if (matches.length > 0) {
+ isProcessing = true;
+ clearMatches(matches);
+ LK.setTimeout(function () {
+ applyGravity();
+ LK.setTimeout(function () {
+ fillEmptySpaces();
+ LK.setTimeout(function () {
+ isProcessing = false;
+ }, 500);
+ }, 400);
+ }, 200);
+ }
+}
+function getCandyAtPosition(x, y) {
+ var localX = x - gridStartX;
+ var localY = y - gridStartY;
+ if (localX < 0 || localY < 0 || localX >= GRID_SIZE * cellSize || localY >= GRID_SIZE * cellSize) {
+ return null;
+ }
+ var gridX = Math.floor(localX / cellSize);
+ var gridY = Math.floor(localY / cellSize);
+ return grid[gridX][gridY];
+}
+function getGridPosition(x, y) {
+ var localX = x - gridStartX;
+ var localY = y - gridStartY;
+ if (localX < 0 || localY < 0 || localX >= GRID_SIZE * cellSize || localY >= GRID_SIZE * cellSize) {
+ return null;
+ }
+ var gridX = Math.floor(localX / cellSize);
+ var gridY = Math.floor(localY / cellSize);
+ return {
+ x: gridX,
+ y: gridY
+ };
+}
+function checkWinCondition() {
+ if (LK.getScore() >= targetScore) {
+ LK.showYouWin();
+ } else if (movesLeft <= 0) {
+ LK.showGameOver();
+ }
+}
+game.down = function (x, y, obj) {
+ if (isProcessing || animatingCandies > 0) return;
+ var candy = getCandyAtPosition(x, y);
+ if (candy) {
+ if (selectedCandy) {
+ selectedCandy.alpha = 1.0;
+ }
+ selectedCandy = candy;
+ selectedCandy.alpha = 0.7;
+ LK.getSound('swap').play();
+ }
+};
+game.up = function (x, y, obj) {
+ if (isProcessing || animatingCandies > 0) return;
+ var candy = getCandyAtPosition(x, y);
+ if (selectedCandy && candy && selectedCandy !== candy) {
+ var pos1 = {
+ x: selectedCandy.gridX,
+ y: selectedCandy.gridY
+ };
+ var pos2 = {
+ x: candy.gridX,
+ y: candy.gridY
+ };
+ if (areAdjacent(pos1.x, pos1.y, pos2.x, pos2.y)) {
+ // Test swap
+ var temp = grid[pos1.x][pos1.y];
+ grid[pos1.x][pos1.y] = grid[pos2.x][pos2.y];
+ grid[pos2.x][pos2.y] = temp;
+ var matches = findMatches();
+ // Revert test swap
+ grid[pos2.x][pos2.y] = grid[pos1.x][pos1.y];
+ grid[pos1.x][pos1.y] = temp;
+ if (matches.length > 0) {
+ swapCandies(pos1.x, pos1.y, pos2.x, pos2.y);
+ movesLeft--;
+ movesText.setText('Moves: ' + movesLeft);
+ LK.setTimeout(function () {
+ processMatches();
+ }, 250);
+ }
+ }
+ selectedCandy.alpha = 1.0;
+ selectedCandy = null;
+ } else if (selectedCandy) {
+ selectedCandy.alpha = 1.0;
+ selectedCandy = null;
+ }
+};
+game.update = function () {
+ if (animatingCandies === 0 && !isProcessing) {
+ processMatches();
+ checkWinCondition();
+ }
+};
+// Initialize the game
+fillGrid();
\ No newline at end of file