/**** 
* Plugins
****/ 
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1", {
	highScore: 0,
	currentLevel: 1
});
/**** 
* Classes
****/ 
var Flower = Container.expand(function (type) {
	var self = Container.call(this);
	self.type = type;
	self.isMatched = false;
	self.isMoving = false;
	// Create flower asset based on type
	var flowerGraphics = self.attachAsset(type, {
		anchorX: 0.5,
		anchorY: 0.5,
		scaleX: 0.9,
		scaleY: 0.9
	});
	// Method to handle selection/deselection visual effect
	self.setSelected = function (selected) {
		if (selected) {
			tween(flowerGraphics, {
				scaleX: 1.1,
				scaleY: 1.1
			}, {
				duration: 200,
				easing: tween.easeOut
			});
		} else {
			tween(flowerGraphics, {
				scaleX: 0.9,
				scaleY: 0.9
			}, {
				duration: 200,
				easing: tween.easeOut
			});
		}
	};
	// Method to handle match animation
	self.animateMatch = function (callback) {
		self.isMatched = true;
		tween(flowerGraphics, {
			alpha: 0,
			scaleX: 0.2,
			scaleY: 0.2
		}, {
			duration: 300,
			easing: tween.easeOut,
			onFinish: function onFinish() {
				if (callback) {
					callback();
				}
			}
		});
	};
	// Method to move flower to a new position
	self.moveTo = function (newX, newY, duration, callback) {
		self.isMoving = true;
		tween(self, {
			x: newX,
			y: newY
		}, {
			duration: duration || 300,
			easing: tween.easeOut,
			onFinish: function onFinish() {
				self.isMoving = false;
				if (callback) {
					callback();
				}
			}
		});
	};
	// Event handlers
	self.down = function (x, y, obj) {
		// Handle touch/click in game logic
		if (!self.isMatched && !self.isMoving && !gameOver) {
			selectFlower(self);
		}
	};
	return self;
});
var GameBoard = Container.expand(function (rows, cols, cellSize) {
	var self = Container.call(this);
	self.rows = rows;
	self.cols = cols;
	self.cellSize = cellSize;
	self.boardWidth = cols * cellSize;
	self.boardHeight = rows * cellSize;
	self.grid = [];
	// Create board background
	var boardBackground = self.attachAsset('board', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: self.boardWidth,
		height: self.boardHeight
	});
	// Initialize grid with cells
	self.initializeGrid = function () {
		// Create grid cells
		for (var row = 0; row < rows; row++) {
			self.grid[row] = [];
			for (var col = 0; col < cols; col++) {
				// Create cell background
				var cell = LK.getAsset('cell', {
					anchorX: 0.5,
					anchorY: 0.5,
					width: cellSize - 10,
					height: cellSize - 10
				});
				// Position cell
				cell.x = col * cellSize - self.boardWidth / 2 + cellSize / 2;
				cell.y = row * cellSize - self.boardHeight / 2 + cellSize / 2;
				self.addChild(cell);
				self.grid[row][col] = null; // Will hold flower references
			}
		}
	};
	// Add a flower to the grid at specified position
	self.addFlower = function (flower, row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			self.grid[row][col] = flower;
			flower.row = row;
			flower.col = col;
			// Position flower in grid
			flower.x = col * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower.y = row * cellSize - self.boardHeight / 2 + cellSize / 2;
			self.addChild(flower);
			return true;
		}
		return false;
	};
	// Remove a flower from the grid
	self.removeFlower = function (row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			var flower = self.grid[row][col];
			if (flower) {
				self.grid[row][col] = null;
				return flower;
			}
		}
		return null;
	};
	// Swap two flowers in the grid
	self.swapFlowers = function (row1, col1, row2, col2, animate, callback) {
		if (row1 < 0 || row1 >= rows || col1 < 0 || col1 >= cols || row2 < 0 || row2 >= rows || col2 < 0 || col2 >= cols) {
			return false;
		}
		var flower1 = self.grid[row1][col1];
		var flower2 = self.grid[row2][col2];
		if (!flower1 || !flower2) {
			return false;
		}
		// Update grid references
		self.grid[row1][col1] = flower2;
		self.grid[row2][col2] = flower1;
		// Update flower position properties
		flower1.row = row2;
		flower1.col = col2;
		flower2.row = row1;
		flower2.col = col1;
		if (animate) {
			// Calculate target positions
			var pos1 = {
				x: col2 * cellSize - self.boardWidth / 2 + cellSize / 2,
				y: row2 * cellSize - self.boardHeight / 2 + cellSize / 2
			};
			var pos2 = {
				x: col1 * cellSize - self.boardWidth / 2 + cellSize / 2,
				y: row1 * cellSize - self.boardHeight / 2 + cellSize / 2
			};
			// Animate the swap
			flower1.moveTo(pos1.x, pos1.y, 200);
			flower2.moveTo(pos2.x, pos2.y, 200, callback);
		} else {
			// Instantly swap positions
			flower1.x = col2 * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower1.y = row2 * cellSize - self.boardHeight / 2 + cellSize / 2;
			flower2.x = col1 * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower2.y = row1 * cellSize - self.boardHeight / 2 + cellSize / 2;
			if (callback) {
				callback();
			}
		}
		return true;
	};
	// Get flower at specific grid position
	self.getFlower = function (row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			return self.grid[row][col];
		}
		return null;
	};
	// Check if coordinates are adjacent
	self.areAdjacent = function (row1, col1, row2, col2) {
		var rowDiff = Math.abs(row1 - row2);
		var colDiff = Math.abs(col1 - col2);
		// Adjacent if exactly one coordinate differs by 1 and the other is the same
		return rowDiff === 1 && colDiff === 0 || rowDiff === 0 && colDiff === 1;
	};
	return self;
});
// LicoriceBall class for combo feature
var LicoriceBall = Container.expand(function (row, col) {
	var self = Container.call(this);
	self.row = row;
	self.col = col;
	self.isExploded = false;
	// Attach a licorice ball asset (use a unique color/shape for now)
	var licoriceGraphics = self.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 90,
		height: 90,
		color: 0x222222,
		tint: 0x222222
	});
	// Add a visual cue (e.g. a white "O" text)
	var licoriceText = new Text2('🍬', {
		size: 60,
		fill: 0xffffff
	});
	licoriceText.anchor.set(0.5, 0.5);
	self.addChild(licoriceText);
	// Animate appearance
	licoriceGraphics.scaleX = 0.2;
	licoriceGraphics.scaleY = 0.2;
	tween(licoriceGraphics, {
		scaleX: 1,
		scaleY: 1
	}, {
		duration: 300,
		easing: tween.bounceOut
	});
	// Handle explosion on tap
	self.down = function (x, y, obj) {
		if (!self.isExploded && !isProcessingMatches && !gameOver) {
			self.isExploded = true;
			triggerLicoriceExplosion(self.row, self.col);
		}
	};
	return self;
});
/**** 
* Initialize Game
****/ 
var game = new LK.Game({
	backgroundColor: 0x4CAF50
});
/**** 
* Game Code
****/ 
// Add custom background
var customBackground = LK.getAsset('customBackground', {
	anchorX: 0.5,
	anchorY: 0.5,
	width: 2048,
	height: 2732
});
customBackground.x = 2048 / 2;
customBackground.y = 2732 / 2;
game.addChild(customBackground);
// Language system
var SUPPORTED_LANGUAGES = [{
	code: 'fr',
	name: 'Français'
}, {
	code: 'en',
	name: 'English'
}, {
	code: 'de',
	name: 'Deutsch'
}, {
	code: 'ja',
	name: '日本語'
}, {
	code: 'it',
	name: 'Italiano'
}, {
	code: 'es',
	name: 'Español'
}, {
	code: 'zh',
	name: '中文'
}, {
	code: 'el',
	name: 'Ελληνικά'
}, {
	code: 'ro',
	name: 'Română'
}, {
	code: 'pl',
	name: 'Polski'
}];
var TRANSLATIONS = {
	fr: {
		score: 'Score: ',
		moves: 'Mouvements: ',
		level: 'Niveau: ',
		reset: 'RESET',
		changeLanguage: 'Changer la langue',
		chooseLanguage: 'Choisissez votre langue',
		choice: 'Choisir',
		back: 'Retour'
	},
	en: {
		score: 'Score: ',
		moves: 'Moves: ',
		level: 'Level: ',
		reset: 'RESET',
		changeLanguage: 'Change the Game Language',
		chooseLanguage: 'Choose your language',
		choice: 'Choice',
		back: 'Back'
	},
	de: {
		score: 'Punkte: ',
		moves: 'Züge: ',
		level: 'Level: ',
		reset: 'RESET',
		changeLanguage: 'Spielsprache ändern',
		chooseLanguage: 'Wählen Sie Ihre Sprache',
		choice: 'Wählen',
		back: 'Zurück'
	},
	ja: {
		score: 'スコア: ',
		moves: '手数: ',
		level: 'レベル: ',
		reset: 'リセット',
		changeLanguage: 'ゲーム言語を変更',
		chooseLanguage: '言語を選択してください',
		choice: '選択',
		back: '戻る'
	},
	it: {
		score: 'Punteggio: ',
		moves: 'Mosse: ',
		level: 'Livello: ',
		reset: 'RESET',
		changeLanguage: 'Cambia lingua del gioco',
		chooseLanguage: 'Scegli la tua lingua',
		choice: 'Scegli',
		back: 'Indietro'
	},
	es: {
		score: 'Puntuación: ',
		moves: 'Movimientos: ',
		level: 'Nivel: ',
		reset: 'RESET',
		changeLanguage: 'Cambiar idioma del juego',
		chooseLanguage: 'Elige tu idioma',
		choice: 'Elegir',
		back: 'Volver'
	},
	zh: {
		score: '分数: ',
		moves: '步数: ',
		level: '等级: ',
		reset: '重置',
		changeLanguage: '更改游戏语言',
		chooseLanguage: '选择您的语言',
		choice: '选择',
		back: '返回'
	},
	el: {
		score: 'Σκορ: ',
		moves: 'Κινήσεις: ',
		level: 'Επίπεδο: ',
		reset: 'ΕΠΑΝΑΦΟΡΑ',
		changeLanguage: 'Αλλαγή γλώσσας παιχνιδιού',
		chooseLanguage: 'Επιλέξτε τη γλώσσα σας',
		choice: 'Επιλογή',
		back: 'Πίσω'
	},
	ro: {
		score: 'Scor: ',
		moves: 'Mișcări: ',
		level: 'Nivel: ',
		reset: 'RESET',
		changeLanguage: 'Schimbă limba jocului',
		chooseLanguage: 'Alege limba ta',
		choice: 'Alege',
		back: 'Înapoi'
	},
	pl: {
		score: 'Wynik: ',
		moves: 'Ruchy: ',
		level: 'Poziom: ',
		reset: 'RESET',
		changeLanguage: 'Zmień język gry',
		chooseLanguage: 'Wybierz swój język',
		choice: 'Wybierz',
		back: 'Wstecz'
	}
};
var currentLanguage = storage.language || 'fr';
var languageMenuOpen = false;
var languageMenuContainer = null;
function getText(key) {
	return TRANSLATIONS[currentLanguage][key] || TRANSLATIONS['fr'][key] || key;
}
// Game constants
var ROWS = 7;
var COLS = 7;
var CELL_SIZE = 100;
var FLOWER_TYPES = ['tulip', 'poppy', 'rose', 'violet', 'lily', 'jasmine', 'lilac'];
var MAX_MOVES = 50;
// Game state variables
var gameBoard;
var selectedFlower = null;
var movesLeft = MAX_MOVES;
var currentScore = 0;
var currentLevel = storage.currentLevel || 1;
var highScore = storage.highScore || 0;
var remainingFlowers = ROWS * COLS;
var isProcessingMatches = false;
var gameOver = false;
var matchCounter = 0;
var matchesRequiredForNextLevel = 5;
// UI elements
var scoreText;
var movesText;
var levelText;
// Initialize game
function initGame() {
	// Create game board
	gameBoard = new GameBoard(ROWS, COLS, CELL_SIZE);
	gameBoard.x = 2048 / 2;
	gameBoard.y = 2732 / 2;
	game.addChild(gameBoard);
	// Initialize the grid cells
	gameBoard.initializeGrid();
	// Populate the board with flowers
	populateBoard();
	// Create UI
	createUI();
	// Set initial game state
	movesLeft = MAX_MOVES;
	currentScore = 0;
	remainingFlowers = ROWS * COLS;
	gameOver = false;
	matchCounter = 0;
	matchesRequiredForNextLevel = 5 + (currentLevel - 1) * 3; // 5 for level 1, +3 for each level
	// Update UI
	updateUI();
	// Play background music
	LK.playMusic('bgmusic');
	// Play background music
	LK.playMusic('bgmusic');
}
// Create UI elements
function createUI() {
	// Create score text
	scoreText = new Text2(getText('score') + '0', {
		size: 60,
		fill: 0xFFFFFF
	});
	scoreText.anchor.set(1, 0); // Anchored to top-right
	LK.gui.topRight.addChild(scoreText);
	// Create moves text
	movesText = new Text2(getText('moves') + movesLeft, {
		size: 60,
		fill: 0xFFFFFF
	});
	movesText.anchor.set(0, 0); // Anchored to top-left
	// Don't place in top-left corner due to platform menu icon
	movesText.x = 120;
	LK.gui.topLeft.addChild(movesText);
	// Create level text
	levelText = new Text2(getText('level') + currentLevel + ' (' + matchCounter + '/' + matchesRequiredForNextLevel + ')', {
		size: 60,
		fill: 0xFFFFFF
	});
	levelText.anchor.set(0.5, 0);
	LK.gui.top.addChild(levelText);
	// Create language button
	var languageButton = new Container();
	var languageBackground = languageButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 300,
		height: 60,
		tint: 0xFF0000
	});
	var languageText = new Text2(getText('changeLanguage'), {
		size: 35,
		fill: 0xFFFFFF
	});
	languageText.anchor.set(0.5, 0.5);
	languageButton.addChild(languageText);
	languageButton.x = 0;
	languageButton.y = 120;
	LK.gui.top.addChild(languageButton);
	// Add event handler to language button
	languageButton.down = function (x, y, obj) {
		if (!languageMenuOpen) {
			showLanguageMenu();
		}
	};
	// Store reference for updates
	languageButton.textElement = languageText;
	// Create reset button
	var resetButton = new Container();
	var resetBackground = resetButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 120,
		height: 60,
		tint: 0xFF0000
	});
	var resetText = new Text2(getText('reset'), {
		size: 40,
		fill: 0xFFFFFF
	});
	resetText.anchor.set(0.5, 0.5);
	resetButton.addChild(resetText);
	resetButton.x = -150;
	resetButton.y = 50;
	LK.gui.topRight.addChild(resetButton);
	// Store reference for updates
	resetButton.textElement = resetText;
	// Add event handler to reset button
	resetButton.down = function (x, y, obj) {
		// Reset level to 1
		currentLevel = 1;
		storage.currentLevel = 1;
		// Reset match counter and requirements
		matchCounter = 0;
		matchesRequiredForNextLevel = 5;
		// Reset game state and board
		gameOver = true; // To stop game processing temporarily
		// Clear the board
		for (var row = 0; row < ROWS; row++) {
			for (var col = 0; col < COLS; col++) {
				var flower = gameBoard.removeFlower(row, col);
				if (flower) {
					flower.destroy();
				}
			}
		}
		// Reset and restart the game
		initGame();
	};
}
// Update UI elements
function updateUI() {
	scoreText.setText(getText('score') + currentScore);
	movesText.setText(getText('moves') + movesLeft);
	levelText.setText(getText('level') + currentLevel + ' (' + matchCounter + '/' + matchesRequiredForNextLevel + ')');
	LK.setScore(currentScore);
}
// Populate the board with flowers
function populateBoard() {
	// Create flowers and ensure no initial matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS; col++) {
			addNewFlower(row, col);
		}
	}
	// Check and resolve any initial matches
	var initialMatches = findAllMatches();
	while (initialMatches.length > 0) {
		// If we have initial matches, regenerate those flowers
		for (var i = 0; i < initialMatches.length; i++) {
			var matchedFlower = gameBoard.removeFlower(initialMatches[i].row, initialMatches[i].col);
			if (matchedFlower) {
				matchedFlower.destroy();
				addNewFlower(initialMatches[i].row, initialMatches[i].col);
			}
		}
		initialMatches = findAllMatches();
	}
}
// Add a new flower at the specified position
function addNewFlower(row, col) {
	// Choose a random flower type that doesn't create a match
	var validTypes = getValidFlowerTypes(row, col);
	var randomType = validTypes[Math.floor(Math.random() * validTypes.length)];
	// Create a new flower and add it to the board
	var flower = new Flower(randomType);
	gameBoard.addFlower(flower, row, col);
	return flower;
}
// Get valid flower types that don't create a match at position
function getValidFlowerTypes(row, col) {
	var invalidTypes = {}; // Use a regular object instead of Set
	// Check horizontal matches to avoid
	if (col >= 2) {
		var flower1 = gameBoard.getFlower(row, col - 1);
		var flower2 = gameBoard.getFlower(row, col - 2);
		if (flower1 && flower2 && flower1.type === flower2.type) {
			invalidTypes[flower1.type] = true; // Mark type as invalid
		}
	}
	// Check vertical matches to avoid
	if (row >= 2) {
		var flower1 = gameBoard.getFlower(row - 1, col);
		var flower2 = gameBoard.getFlower(row - 2, col);
		if (flower1 && flower2 && flower1.type === flower2.type) {
			invalidTypes[flower1.type] = true; // Mark type as invalid
		}
	}
	// Return valid types (all types minus invalid ones)
	return FLOWER_TYPES.filter(function (type) {
		return !invalidTypes[type]; // Check if type is in invalidTypes object
	});
}
// Handle flower selection
function selectFlower(flower) {
	if (isProcessingMatches || gameOver) {
		return;
	}
	if (selectedFlower === null) {
		// First selection
		selectedFlower = flower;
		selectedFlower.setSelected(true);
		LK.getSound('swap').play();
	} else if (selectedFlower === flower) {
		// Deselect
		selectedFlower.setSelected(false);
		selectedFlower = null;
	} else {
		// Second selection - check if adjacent
		if (gameBoard.areAdjacent(selectedFlower.row, selectedFlower.col, flower.row, flower.col)) {
			// Try to swap
			trySwapFlowers(selectedFlower, flower);
		} else {
			// Not adjacent, switch selection
			selectedFlower.setSelected(false);
			selectedFlower = flower;
			selectedFlower.setSelected(true);
			LK.getSound('swap').play();
		}
	}
}
// Try to swap flowers and check for matches
function trySwapFlowers(flower1, flower2) {
	// Swap flowers
	var row1 = flower1.row;
	var col1 = flower1.col;
	var row2 = flower2.row;
	var col2 = flower2.col;
	// Deselect first flower
	flower1.setSelected(false);
	selectedFlower = null;
	// Swap to check for matches
	gameBoard.swapFlowers(row1, col1, row2, col2, true, function () {
		// Check for matches after swap
		var matches = findAllMatches();
		if (matches.length > 0) {
			// Valid move - process matches
			decreaseMoves();
			processMatches(matches);
		} else {
			// Invalid move - swap back
			LK.getSound('invalid').play();
			gameBoard.swapFlowers(row2, col2, row1, col1, true);
		}
	});
}
// Decrease moves and check game over
function decreaseMoves() {
	movesLeft--;
	updateUI();
	// Check if game is over
	if (movesLeft <= 0 && remainingFlowers > 0) {
		endGame(false);
	}
}
// Process all matches
function processMatches(matches) {
	if (matches.length === 0) {
		return;
	}
	isProcessingMatches = true;
	// Calculate score based on match length
	var matchScore = 0;
	var matchCounts = {};
	// Group matches by type
	matches.forEach(function (match) {
		var flower = gameBoard.getFlower(match.row, match.col);
		if (flower) {
			if (!matchCounts[flower.type]) {
				matchCounts[flower.type] = 0;
			}
			matchCounts[flower.type]++;
		}
	});
	// Calculate score based on matches
	// Track licorice ball spawn positions
	var licoriceToSpawn = [];
	Object.keys(matchCounts).forEach(function (type) {
		var count = matchCounts[type];
		if (count >= 5) {
			matchScore += count * 15;
			LK.getSound('match5').play();
		} else if (count === 4) {
			matchScore += count * 10;
			LK.getSound('match4').play();
			// Find the 4-in-a-row and mark for licorice ball spawn
			// Horizontal
			for (var row = 0; row < ROWS; row++) {
				for (var col = 0; col < COLS - 3; col++) {
					var f1 = gameBoard.getFlower(row, col);
					var f2 = gameBoard.getFlower(row, col + 1);
					var f3 = gameBoard.getFlower(row, col + 2);
					var f4 = gameBoard.getFlower(row, col + 3);
					if (f1 && f2 && f3 && f4 && f1.type === type && f2.type === type && f3.type === type && f4.type === type) {
						// Place licorice ball at the second or third flower (centered)
						licoriceToSpawn.push({
							row: row,
							col: col + 1
						});
					}
				}
			}
			// Vertical
			for (var col = 0; col < COLS; col++) {
				for (var row = 0; row < ROWS - 3; row++) {
					var f1 = gameBoard.getFlower(row, col);
					var f2 = gameBoard.getFlower(row + 1, col);
					var f3 = gameBoard.getFlower(row + 2, col);
					var f4 = gameBoard.getFlower(row + 3, col);
					if (f1 && f2 && f3 && f4 && f1.type === type && f2.type === type && f3.type === type && f4.type === type) {
						licoriceToSpawn.push({
							row: row + 1,
							col: col
						});
					}
				}
			}
		} else {
			matchScore += count * 5;
			LK.getSound('match3').play();
		}
		// Count this as a successful match for level progression
		matchCounter++;
	});
	// Update score
	currentScore += matchScore;
	remainingFlowers -= matches.length;
	// Animate matches and remove flowers
	var animationsCompleted = 0;
	matches.forEach(function (match) {
		var flower = gameBoard.getFlower(match.row, match.col);
		if (flower) {
			gameBoard.removeFlower(match.row, match.col);
			flower.animateMatch(function () {
				flower.destroy();
				animationsCompleted++;
				// When all animations complete, make flowers fall and check for new matches
				if (animationsCompleted === matches.length) {
					// Spawn licorice balls if needed
					if (typeof licoriceToSpawn !== "undefined" && licoriceToSpawn.length > 0) {
						for (var i = 0; i < licoriceToSpawn.length; i++) {
							var pos = licoriceToSpawn[i];
							// Only spawn if cell is empty (flower was matched)
							if (!gameBoard.getFlower(pos.row, pos.col)) {
								var licorice = new LicoriceBall(pos.row, pos.col);
								// Place licorice ball in grid (so it can be found for explosion)
								gameBoard.grid[pos.row][pos.col] = licorice;
								// Position licorice ball
								licorice.x = pos.col * CELL_SIZE - gameBoard.boardWidth / 2 + CELL_SIZE / 2;
								licorice.y = pos.row * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
								gameBoard.addChild(licorice);
							}
						}
					}
					updateUI();
					makeFlowersFall(function () {
						fillEmptySpaces(function () {
							// Check for new matches after filling
							var newMatches = findAllMatches();
							if (newMatches.length > 0) {
								processMatches(newMatches);
							} else {
								isProcessingMatches = false;
								// Check if player reached required match count
								if (matchCounter >= matchesRequiredForNextLevel) {
									// Level completed
									endGame(true);
								} else if (remainingFlowers <= 0) {
									// All flowers cleared (alternative win condition)
									endGame(true);
								}
							}
						});
					});
				}
			});
		}
	});
}
// Make flowers fall to fill empty spaces
function makeFlowersFall(callback) {
	var animationsInProgress = 0;
	// Process columns bottom to top
	for (var col = 0; col < COLS; col++) {
		var emptySpaces = 0;
		// Process rows bottom to top
		for (var row = ROWS - 1; row >= 0; row--) {
			var flower = gameBoard.getFlower(row, col);
			if (!flower) {
				emptySpaces++;
			} else if (emptySpaces > 0) {
				// Move flower down by the number of empty spaces
				var newRow = row + emptySpaces;
				animationsInProgress++;
				// Update grid reference
				gameBoard.grid[row][col] = null;
				gameBoard.grid[newRow][col] = flower;
				// Update flower position properties
				flower.row = newRow;
				// Animate the fall
				var targetY = newRow * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
				if (typeof flower.moveTo === "function") {
					flower.moveTo(flower.x, targetY, 300, function () {
						animationsInProgress--;
						if (animationsInProgress === 0 && callback) {
							callback();
						}
					});
				} else {
					// Fallback for objects without moveTo (e.g. LicoriceBall)
					flower.y = targetY;
					animationsInProgress--;
					if (animationsInProgress === 0 && callback) {
						callback();
					}
				}
			}
		}
	}
	if (animationsInProgress === 0 && callback) {
		callback();
	}
}
// Fill empty spaces at the top with new flowers
function fillEmptySpaces(callback) {
	var animationsInProgress = 0;
	for (var col = 0; col < COLS; col++) {
		// Find empty spaces at the top
		for (var row = 0; row < ROWS; row++) {
			if (!gameBoard.getFlower(row, col)) {
				// Create a new flower above the board
				var flower = new Flower(FLOWER_TYPES[Math.floor(Math.random() * FLOWER_TYPES.length)]);
				gameBoard.addFlower(flower, row, col);
				// Position it above the board
				flower.y -= (row + 1) * CELL_SIZE;
				// Animate it falling down
				animationsInProgress++;
				remainingFlowers++;
				var targetY = row * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
				flower.moveTo(flower.x, targetY, 300, function () {
					animationsInProgress--;
					if (animationsInProgress === 0 && callback) {
						callback();
					}
				});
			}
		}
	}
	if (animationsInProgress === 0 && callback) {
		callback();
	}
}
// Find all matching flowers on the board
function findAllMatches() {
	var matches = [];
	var visited = {};
	// Check horizontal matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS - 2; col++) {
			var flower1 = gameBoard.getFlower(row, col);
			var flower2 = gameBoard.getFlower(row, col + 1);
			var flower3 = gameBoard.getFlower(row, col + 2);
			if (flower1 && flower2 && flower3 && flower1.type === flower2.type && flower2.type === flower3.type) {
				// Add match if not already added
				var key1 = row + "," + col;
				var key2 = row + "," + (col + 1);
				var key3 = row + "," + (col + 2);
				if (!visited[key1]) {
					matches.push({
						row: row,
						col: col
					});
					visited[key1] = true;
				}
				if (!visited[key2]) {
					matches.push({
						row: row,
						col: col + 1
					});
					visited[key2] = true;
				}
				if (!visited[key3]) {
					matches.push({
						row: row,
						col: col + 2
					});
					visited[key3] = true;
				}
			}
		}
	}
	// Check vertical matches
	for (var row = 0; row < ROWS - 2; row++) {
		for (var col = 0; col < COLS; col++) {
			var flower1 = gameBoard.getFlower(row, col);
			var flower2 = gameBoard.getFlower(row + 1, col);
			var flower3 = gameBoard.getFlower(row + 2, col);
			if (flower1 && flower2 && flower3 && flower1.type === flower2.type && flower2.type === flower3.type) {
				// Add match if not already added
				var key1 = row + "," + col;
				var key2 = row + 1 + "," + col;
				var key3 = row + 2 + "," + col;
				if (!visited[key1]) {
					matches.push({
						row: row,
						col: col
					});
					visited[key1] = true;
				}
				if (!visited[key2]) {
					matches.push({
						row: row + 1,
						col: col
					});
					visited[key2] = true;
				}
				if (!visited[key3]) {
					matches.push({
						row: row + 2,
						col: col
					});
					visited[key3] = true;
				}
			}
		}
	}
	return matches;
}
// Check if any valid moves exist
function hasValidMoves() {
	// Check each position for potential swaps that create matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS; col++) {
			// Check right swap
			if (col < COLS - 1) {
				// Simulate swap right
				var flower1 = gameBoard.getFlower(row, col);
				var flower2 = gameBoard.getFlower(row, col + 1);
				if (flower1 && flower2) {
					// Swap
					gameBoard.swapFlowers(row, col, row, col + 1, false);
					// Check for matches
					var matches = findAllMatches();
					// Swap back
					gameBoard.swapFlowers(row, col + 1, row, col, false);
					if (matches.length > 0) {
						return true;
					}
				}
			}
			// Check down swap
			if (row < ROWS - 1) {
				// Simulate swap down
				var flower1 = gameBoard.getFlower(row, col);
				var flower2 = gameBoard.getFlower(row + 1, col);
				if (flower1 && flower2) {
					// Swap
					gameBoard.swapFlowers(row, col, row + 1, col, false);
					// Check for matches
					var matches = findAllMatches();
					// Swap back
					gameBoard.swapFlowers(row + 1, col, row, col, false);
					if (matches.length > 0) {
						return true;
					}
				}
			}
		}
	}
	return false;
}
// End the game
function endGame(success) {
	gameOver = true;
	if (success) {
		// Level completed
		currentLevel++;
		storage.currentLevel = currentLevel;
		// Reset match counter and increase requirements for next level
		matchCounter = 0;
		matchesRequiredForNextLevel = 5 + (currentLevel - 1) * 3; // 5 for level 1, +3 for each level
		// Update high score
		if (currentScore > highScore) {
			highScore = currentScore;
			storage.highScore = highScore;
		}
		// Show you win screen
		LK.getSound('levelup').play();
		LK.showYouWin();
	} else {
		// Game over - ran out of moves
		currentLevel = 1;
		storage.currentLevel = currentLevel;
		// Update high score
		if (currentScore > highScore) {
			highScore = currentScore;
			storage.highScore = highScore;
		}
		// Show game over screen
		LK.showGameOver();
	}
}
// Initialize the game
initGame();
// Main game update loop
game.update = function () {
	// If no valid moves exist, shuffle the board
	if (!isProcessingMatches && !gameOver && !hasValidMoves()) {
		// Shuffle the board
		var allFlowers = [];
		// Collect all flowers
		for (var row = 0; row < ROWS; row++) {
			for (var col = 0; col < COLS; col++) {
				var flower = gameBoard.removeFlower(row, col);
				if (flower) {
					flower.destroy();
				}
			}
		}
		// Repopulate the board
		populateBoard();
	}
};
// Handle touch/mouse input on game board
game.down = function (x, y, obj) {
	// This is handled in the Flower class
};
game.move = function (x, y, obj) {
	// Handle dragging of selected flower
	if (selectedFlower && !isProcessingMatches && !gameOver) {
		// Get position in gameBoard coordinates
		var localPos = gameBoard.toLocal({
			x: x,
			y: y
		});
		// Calculate which cell the player is hovering over
		var hoverCol = Math.floor((localPos.x + gameBoard.boardWidth / 2) / CELL_SIZE);
		var hoverRow = Math.floor((localPos.y + gameBoard.boardHeight / 2) / CELL_SIZE);
		// Check if it's a valid cell and adjacent to the original position
		if (hoverRow >= 0 && hoverRow < ROWS && hoverCol >= 0 && hoverCol < COLS && gameBoard.areAdjacent(selectedFlower.row, selectedFlower.col, hoverRow, hoverCol)) {
			// Get the flower at the hover position
			var targetFlower = gameBoard.getFlower(hoverRow, hoverCol);
			if (targetFlower && targetFlower !== selectedFlower) {
				// Try to swap the flowers
				trySwapFlowers(selectedFlower, targetFlower);
			}
		}
	}
};
game.up = function (x, y, obj) {
	// No global up handling needed
};
// Show language selection menu
function showLanguageMenu() {
	if (languageMenuOpen) return;
	languageMenuOpen = true;
	// Create language menu container
	languageMenuContainer = new Container();
	// Create background overlay
	var overlay = languageMenuContainer.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 2048,
		height: 2732,
		tint: 0x000000,
		alpha: 0.8
	});
	// Create menu background
	var menuBackground = languageMenuContainer.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 1200,
		height: 1800,
		tint: 0xFFFFFF
	});
	// Create title
	var titleText = new Text2(getText('chooseLanguage'), {
		size: 80,
		fill: 0x000000
	});
	titleText.anchor.set(0.5, 0.5);
	titleText.y = -700;
	languageMenuContainer.addChild(titleText);
	// Create language buttons
	var buttonStartY = -500;
	var buttonSpacing = 120;
	for (var i = 0; i < SUPPORTED_LANGUAGES.length; i++) {
		var lang = SUPPORTED_LANGUAGES[i];
		var langButton = new Container();
		// Button background
		var buttonBg = langButton.attachAsset('cell', {
			anchorX: 0.5,
			anchorY: 0.5,
			width: 800,
			height: 100,
			tint: currentLanguage === lang.code ? 0x00FF00 : 0x808080
		});
		// Language name
		var langName = new Text2(lang.name, {
			size: 50,
			fill: 0x000000
		});
		langName.anchor.set(0, 0.5);
		langName.x = -300;
		langButton.addChild(langName);
		// Choice button
		var choiceButton = new Container();
		var choiceBg = choiceButton.attachAsset('cell', {
			anchorX: 0.5,
			anchorY: 0.5,
			width: 200,
			height: 80,
			tint: 0x0066CC
		});
		var choiceText = new Text2(getText('choice'), {
			size: 40,
			fill: 0xFFFFFF
		});
		choiceText.anchor.set(0.5, 0.5);
		choiceButton.addChild(choiceText);
		choiceButton.x = 250;
		// Add choice button event
		choiceButton.languageCode = lang.code;
		choiceButton.down = function (x, y, obj) {
			selectLanguage(this.languageCode);
		};
		langButton.addChild(choiceButton);
		langButton.y = buttonStartY + i * buttonSpacing;
		languageMenuContainer.addChild(langButton);
	}
	// Create back button
	var backButton = new Container();
	var backBg = backButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 300,
		height: 100,
		tint: 0xFF0000
	});
	var backText = new Text2(getText('back'), {
		size: 50,
		fill: 0xFFFFFF
	});
	backText.anchor.set(0.5, 0.5);
	backButton.addChild(backText);
	backButton.y = 700;
	backButton.down = function (x, y, obj) {
		hideLanguageMenu();
	};
	languageMenuContainer.addChild(backButton);
	// Position and add to game
	languageMenuContainer.x = 2048 / 2;
	languageMenuContainer.y = 2732 / 2;
	game.addChild(languageMenuContainer);
}
// Hide language menu
function hideLanguageMenu() {
	if (languageMenuContainer) {
		languageMenuContainer.destroy();
		languageMenuContainer = null;
	}
	languageMenuOpen = false;
}
// Select a language
function selectLanguage(languageCode) {
	currentLanguage = languageCode;
	storage.language = languageCode;
	// Update all UI text
	updateAllUIText();
	// Hide language menu
	hideLanguageMenu();
}
// Update all UI text with current language
function updateAllUIText() {
	// Update main UI
	updateUI();
	// Update button texts
	var topContainer = LK.gui.top;
	for (var i = 0; i < topContainer.children.length; i++) {
		var child = topContainer.children[i];
		if (child.textElement && child.textElement.text) {
			if (child.textElement.text.indexOf('Change') >= 0 || child.textElement.text.indexOf('Changer') >= 0 || child.textElement.text.indexOf('Cambiar') >= 0 || child.textElement.text.indexOf('Cambia') >= 0 || child.textElement.text.indexOf('Schimbă') >= 0 || child.textElement.text.indexOf('Zmień') >= 0 || child.textElement.text.indexOf('Αλλαγή') >= 0 || child.textElement.text.indexOf('Spielsprache') >= 0 || child.textElement.text.indexOf('更改') >= 0 || child.textElement.text.indexOf('ゲーム言語') >= 0) {
				child.textElement.setText(getText('changeLanguage'));
			}
		}
	}
	var topRightContainer = LK.gui.topRight;
	for (var i = 0; i < topRightContainer.children.length; i++) {
		var child = topRightContainer.children[i];
		if (child.textElement && child.textElement.text) {
			if (child.textElement.text === 'RESET' || child.textElement.text === 'リセット' || child.textElement.text === 'ΕΠΑΝΑΦΟΡΑ' || child.textElement.text === '重置') {
				child.textElement.setText(getText('reset'));
			}
		}
	}
}
// Trigger the licorice explosion: remove all flowers in the column, trigger combo mode for 8 seconds
function triggerLicoriceExplosion(row, col) {
	if (gameOver || isProcessingMatches) return;
	isProcessingMatches = true;
	// Remove all flowers in the column (except LicoriceBall itself)
	for (var r = 0; r < ROWS; r++) {
		var obj = gameBoard.getFlower(r, col);
		if (obj && !(obj instanceof LicoriceBall)) {
			gameBoard.removeFlower(r, col);
			if (typeof obj.animateMatch === "function") {
				obj.animateMatch(function () {
					obj.destroy();
				});
			} else {
				obj.destroy();
			}
			remainingFlowers--;
		}
	}
	// Remove the LicoriceBall itself
	var licorice = gameBoard.getFlower(row, col);
	if (licorice && licorice instanceof LicoriceBall) {
		gameBoard.removeFlower(row, col);
		licorice.destroy();
	}
	// Combo mode: for 8 seconds, after each match, auto-match adjacent flowers
	var comboEndTime = Date.now() + 8000;
	var originalProcessMatches = processMatches;
	var comboActive = true;
	// Helper to auto-match adjacent flowers after each match
	function comboProcessMatches(matches) {
		originalProcessMatches(matches);
		// After normal match processing, auto-match adjacent flowers if combo is still active
		if (comboActive && !gameOver) {
			LK.setTimeout(function () {
				var newMatches = [];
				// Find all adjacent pairs and add to matches
				for (var row = 0; row < ROWS; row++) {
					for (var col = 0; col < COLS; col++) {
						var f = gameBoard.getFlower(row, col);
						if (!f || f instanceof LicoriceBall) continue;
						// Check right
						var fRight = gameBoard.getFlower(row, col + 1);
						if (fRight && fRight.type === f.type && !(fRight instanceof LicoriceBall)) {
							newMatches.push({
								row: row,
								col: col
							});
							newMatches.push({
								row: row,
								col: col + 1
							});
						}
						// Check down
						var fDown = gameBoard.getFlower(row + 1, col);
						if (fDown && fDown.type === f.type && !(fDown instanceof LicoriceBall)) {
							newMatches.push({
								row: row,
								col: col
							});
							newMatches.push({
								row: row + 1,
								col: col
							});
						}
					}
				}
				// Remove duplicates
				var seen = {};
				var uniqueMatches = [];
				for (var i = 0; i < newMatches.length; i++) {
					var key = newMatches[i].row + "," + newMatches[i].col;
					if (!seen[key]) {
						uniqueMatches.push(newMatches[i]);
						seen[key] = true;
					}
				}
				if (uniqueMatches.length > 0 && comboActive) {
					comboProcessMatches(uniqueMatches);
				} else {
					isProcessingMatches = false;
				}
			}, 350); // Wait for match animation
		} else {
			isProcessingMatches = false;
		}
	}
	// Override processMatches for combo mode
	processMatches = comboProcessMatches;
	// End combo mode after 8 seconds
	LK.setTimeout(function () {
		comboActive = false;
		processMatches = originalProcessMatches;
		isProcessingMatches = false;
	}, 8000);
	// After explosion, let flowers fall and fill, then check for matches
	makeFlowersFall(function () {
		fillEmptySpaces(function () {
			var matches = findAllMatches();
			if (matches.length > 0) {
				processMatches(matches);
			} else {
				isProcessingMatches = false;
			}
		});
	});
} /**** 
* Plugins
****/ 
var tween = LK.import("@upit/tween.v1");
var storage = LK.import("@upit/storage.v1", {
	highScore: 0,
	currentLevel: 1
});
/**** 
* Classes
****/ 
var Flower = Container.expand(function (type) {
	var self = Container.call(this);
	self.type = type;
	self.isMatched = false;
	self.isMoving = false;
	// Create flower asset based on type
	var flowerGraphics = self.attachAsset(type, {
		anchorX: 0.5,
		anchorY: 0.5,
		scaleX: 0.9,
		scaleY: 0.9
	});
	// Method to handle selection/deselection visual effect
	self.setSelected = function (selected) {
		if (selected) {
			tween(flowerGraphics, {
				scaleX: 1.1,
				scaleY: 1.1
			}, {
				duration: 200,
				easing: tween.easeOut
			});
		} else {
			tween(flowerGraphics, {
				scaleX: 0.9,
				scaleY: 0.9
			}, {
				duration: 200,
				easing: tween.easeOut
			});
		}
	};
	// Method to handle match animation
	self.animateMatch = function (callback) {
		self.isMatched = true;
		tween(flowerGraphics, {
			alpha: 0,
			scaleX: 0.2,
			scaleY: 0.2
		}, {
			duration: 300,
			easing: tween.easeOut,
			onFinish: function onFinish() {
				if (callback) {
					callback();
				}
			}
		});
	};
	// Method to move flower to a new position
	self.moveTo = function (newX, newY, duration, callback) {
		self.isMoving = true;
		tween(self, {
			x: newX,
			y: newY
		}, {
			duration: duration || 300,
			easing: tween.easeOut,
			onFinish: function onFinish() {
				self.isMoving = false;
				if (callback) {
					callback();
				}
			}
		});
	};
	// Event handlers
	self.down = function (x, y, obj) {
		// Handle touch/click in game logic
		if (!self.isMatched && !self.isMoving && !gameOver) {
			selectFlower(self);
		}
	};
	return self;
});
var GameBoard = Container.expand(function (rows, cols, cellSize) {
	var self = Container.call(this);
	self.rows = rows;
	self.cols = cols;
	self.cellSize = cellSize;
	self.boardWidth = cols * cellSize;
	self.boardHeight = rows * cellSize;
	self.grid = [];
	// Create board background
	var boardBackground = self.attachAsset('board', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: self.boardWidth,
		height: self.boardHeight
	});
	// Initialize grid with cells
	self.initializeGrid = function () {
		// Create grid cells
		for (var row = 0; row < rows; row++) {
			self.grid[row] = [];
			for (var col = 0; col < cols; col++) {
				// Create cell background
				var cell = LK.getAsset('cell', {
					anchorX: 0.5,
					anchorY: 0.5,
					width: cellSize - 10,
					height: cellSize - 10
				});
				// Position cell
				cell.x = col * cellSize - self.boardWidth / 2 + cellSize / 2;
				cell.y = row * cellSize - self.boardHeight / 2 + cellSize / 2;
				self.addChild(cell);
				self.grid[row][col] = null; // Will hold flower references
			}
		}
	};
	// Add a flower to the grid at specified position
	self.addFlower = function (flower, row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			self.grid[row][col] = flower;
			flower.row = row;
			flower.col = col;
			// Position flower in grid
			flower.x = col * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower.y = row * cellSize - self.boardHeight / 2 + cellSize / 2;
			self.addChild(flower);
			return true;
		}
		return false;
	};
	// Remove a flower from the grid
	self.removeFlower = function (row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			var flower = self.grid[row][col];
			if (flower) {
				self.grid[row][col] = null;
				return flower;
			}
		}
		return null;
	};
	// Swap two flowers in the grid
	self.swapFlowers = function (row1, col1, row2, col2, animate, callback) {
		if (row1 < 0 || row1 >= rows || col1 < 0 || col1 >= cols || row2 < 0 || row2 >= rows || col2 < 0 || col2 >= cols) {
			return false;
		}
		var flower1 = self.grid[row1][col1];
		var flower2 = self.grid[row2][col2];
		if (!flower1 || !flower2) {
			return false;
		}
		// Update grid references
		self.grid[row1][col1] = flower2;
		self.grid[row2][col2] = flower1;
		// Update flower position properties
		flower1.row = row2;
		flower1.col = col2;
		flower2.row = row1;
		flower2.col = col1;
		if (animate) {
			// Calculate target positions
			var pos1 = {
				x: col2 * cellSize - self.boardWidth / 2 + cellSize / 2,
				y: row2 * cellSize - self.boardHeight / 2 + cellSize / 2
			};
			var pos2 = {
				x: col1 * cellSize - self.boardWidth / 2 + cellSize / 2,
				y: row1 * cellSize - self.boardHeight / 2 + cellSize / 2
			};
			// Animate the swap
			flower1.moveTo(pos1.x, pos1.y, 200);
			flower2.moveTo(pos2.x, pos2.y, 200, callback);
		} else {
			// Instantly swap positions
			flower1.x = col2 * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower1.y = row2 * cellSize - self.boardHeight / 2 + cellSize / 2;
			flower2.x = col1 * cellSize - self.boardWidth / 2 + cellSize / 2;
			flower2.y = row1 * cellSize - self.boardHeight / 2 + cellSize / 2;
			if (callback) {
				callback();
			}
		}
		return true;
	};
	// Get flower at specific grid position
	self.getFlower = function (row, col) {
		if (row >= 0 && row < rows && col >= 0 && col < cols) {
			return self.grid[row][col];
		}
		return null;
	};
	// Check if coordinates are adjacent
	self.areAdjacent = function (row1, col1, row2, col2) {
		var rowDiff = Math.abs(row1 - row2);
		var colDiff = Math.abs(col1 - col2);
		// Adjacent if exactly one coordinate differs by 1 and the other is the same
		return rowDiff === 1 && colDiff === 0 || rowDiff === 0 && colDiff === 1;
	};
	return self;
});
// LicoriceBall class for combo feature
var LicoriceBall = Container.expand(function (row, col) {
	var self = Container.call(this);
	self.row = row;
	self.col = col;
	self.isExploded = false;
	// Attach a licorice ball asset (use a unique color/shape for now)
	var licoriceGraphics = self.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 90,
		height: 90,
		color: 0x222222,
		tint: 0x222222
	});
	// Add a visual cue (e.g. a white "O" text)
	var licoriceText = new Text2('🍬', {
		size: 60,
		fill: 0xffffff
	});
	licoriceText.anchor.set(0.5, 0.5);
	self.addChild(licoriceText);
	// Animate appearance
	licoriceGraphics.scaleX = 0.2;
	licoriceGraphics.scaleY = 0.2;
	tween(licoriceGraphics, {
		scaleX: 1,
		scaleY: 1
	}, {
		duration: 300,
		easing: tween.bounceOut
	});
	// Handle explosion on tap
	self.down = function (x, y, obj) {
		if (!self.isExploded && !isProcessingMatches && !gameOver) {
			self.isExploded = true;
			triggerLicoriceExplosion(self.row, self.col);
		}
	};
	return self;
});
/**** 
* Initialize Game
****/ 
var game = new LK.Game({
	backgroundColor: 0x4CAF50
});
/**** 
* Game Code
****/ 
// Add custom background
var customBackground = LK.getAsset('customBackground', {
	anchorX: 0.5,
	anchorY: 0.5,
	width: 2048,
	height: 2732
});
customBackground.x = 2048 / 2;
customBackground.y = 2732 / 2;
game.addChild(customBackground);
// Language system
var SUPPORTED_LANGUAGES = [{
	code: 'fr',
	name: 'Français'
}, {
	code: 'en',
	name: 'English'
}, {
	code: 'de',
	name: 'Deutsch'
}, {
	code: 'ja',
	name: '日本語'
}, {
	code: 'it',
	name: 'Italiano'
}, {
	code: 'es',
	name: 'Español'
}, {
	code: 'zh',
	name: '中文'
}, {
	code: 'el',
	name: 'Ελληνικά'
}, {
	code: 'ro',
	name: 'Română'
}, {
	code: 'pl',
	name: 'Polski'
}];
var TRANSLATIONS = {
	fr: {
		score: 'Score: ',
		moves: 'Mouvements: ',
		level: 'Niveau: ',
		reset: 'RESET',
		changeLanguage: 'Changer la langue',
		chooseLanguage: 'Choisissez votre langue',
		choice: 'Choisir',
		back: 'Retour'
	},
	en: {
		score: 'Score: ',
		moves: 'Moves: ',
		level: 'Level: ',
		reset: 'RESET',
		changeLanguage: 'Change the Game Language',
		chooseLanguage: 'Choose your language',
		choice: 'Choice',
		back: 'Back'
	},
	de: {
		score: 'Punkte: ',
		moves: 'Züge: ',
		level: 'Level: ',
		reset: 'RESET',
		changeLanguage: 'Spielsprache ändern',
		chooseLanguage: 'Wählen Sie Ihre Sprache',
		choice: 'Wählen',
		back: 'Zurück'
	},
	ja: {
		score: 'スコア: ',
		moves: '手数: ',
		level: 'レベル: ',
		reset: 'リセット',
		changeLanguage: 'ゲーム言語を変更',
		chooseLanguage: '言語を選択してください',
		choice: '選択',
		back: '戻る'
	},
	it: {
		score: 'Punteggio: ',
		moves: 'Mosse: ',
		level: 'Livello: ',
		reset: 'RESET',
		changeLanguage: 'Cambia lingua del gioco',
		chooseLanguage: 'Scegli la tua lingua',
		choice: 'Scegli',
		back: 'Indietro'
	},
	es: {
		score: 'Puntuación: ',
		moves: 'Movimientos: ',
		level: 'Nivel: ',
		reset: 'RESET',
		changeLanguage: 'Cambiar idioma del juego',
		chooseLanguage: 'Elige tu idioma',
		choice: 'Elegir',
		back: 'Volver'
	},
	zh: {
		score: '分数: ',
		moves: '步数: ',
		level: '等级: ',
		reset: '重置',
		changeLanguage: '更改游戏语言',
		chooseLanguage: '选择您的语言',
		choice: '选择',
		back: '返回'
	},
	el: {
		score: 'Σκορ: ',
		moves: 'Κινήσεις: ',
		level: 'Επίπεδο: ',
		reset: 'ΕΠΑΝΑΦΟΡΑ',
		changeLanguage: 'Αλλαγή γλώσσας παιχνιδιού',
		chooseLanguage: 'Επιλέξτε τη γλώσσα σας',
		choice: 'Επιλογή',
		back: 'Πίσω'
	},
	ro: {
		score: 'Scor: ',
		moves: 'Mișcări: ',
		level: 'Nivel: ',
		reset: 'RESET',
		changeLanguage: 'Schimbă limba jocului',
		chooseLanguage: 'Alege limba ta',
		choice: 'Alege',
		back: 'Înapoi'
	},
	pl: {
		score: 'Wynik: ',
		moves: 'Ruchy: ',
		level: 'Poziom: ',
		reset: 'RESET',
		changeLanguage: 'Zmień język gry',
		chooseLanguage: 'Wybierz swój język',
		choice: 'Wybierz',
		back: 'Wstecz'
	}
};
var currentLanguage = storage.language || 'fr';
var languageMenuOpen = false;
var languageMenuContainer = null;
function getText(key) {
	return TRANSLATIONS[currentLanguage][key] || TRANSLATIONS['fr'][key] || key;
}
// Game constants
var ROWS = 7;
var COLS = 7;
var CELL_SIZE = 100;
var FLOWER_TYPES = ['tulip', 'poppy', 'rose', 'violet', 'lily', 'jasmine', 'lilac'];
var MAX_MOVES = 50;
// Game state variables
var gameBoard;
var selectedFlower = null;
var movesLeft = MAX_MOVES;
var currentScore = 0;
var currentLevel = storage.currentLevel || 1;
var highScore = storage.highScore || 0;
var remainingFlowers = ROWS * COLS;
var isProcessingMatches = false;
var gameOver = false;
var matchCounter = 0;
var matchesRequiredForNextLevel = 5;
// UI elements
var scoreText;
var movesText;
var levelText;
// Initialize game
function initGame() {
	// Create game board
	gameBoard = new GameBoard(ROWS, COLS, CELL_SIZE);
	gameBoard.x = 2048 / 2;
	gameBoard.y = 2732 / 2;
	game.addChild(gameBoard);
	// Initialize the grid cells
	gameBoard.initializeGrid();
	// Populate the board with flowers
	populateBoard();
	// Create UI
	createUI();
	// Set initial game state
	movesLeft = MAX_MOVES;
	currentScore = 0;
	remainingFlowers = ROWS * COLS;
	gameOver = false;
	matchCounter = 0;
	matchesRequiredForNextLevel = 5 + (currentLevel - 1) * 3; // 5 for level 1, +3 for each level
	// Update UI
	updateUI();
	// Play background music
	LK.playMusic('bgmusic');
	// Play background music
	LK.playMusic('bgmusic');
}
// Create UI elements
function createUI() {
	// Create score text
	scoreText = new Text2(getText('score') + '0', {
		size: 60,
		fill: 0xFFFFFF
	});
	scoreText.anchor.set(1, 0); // Anchored to top-right
	LK.gui.topRight.addChild(scoreText);
	// Create moves text
	movesText = new Text2(getText('moves') + movesLeft, {
		size: 60,
		fill: 0xFFFFFF
	});
	movesText.anchor.set(0, 0); // Anchored to top-left
	// Don't place in top-left corner due to platform menu icon
	movesText.x = 120;
	LK.gui.topLeft.addChild(movesText);
	// Create level text
	levelText = new Text2(getText('level') + currentLevel + ' (' + matchCounter + '/' + matchesRequiredForNextLevel + ')', {
		size: 60,
		fill: 0xFFFFFF
	});
	levelText.anchor.set(0.5, 0);
	LK.gui.top.addChild(levelText);
	// Create language button
	var languageButton = new Container();
	var languageBackground = languageButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 300,
		height: 60,
		tint: 0xFF0000
	});
	var languageText = new Text2(getText('changeLanguage'), {
		size: 35,
		fill: 0xFFFFFF
	});
	languageText.anchor.set(0.5, 0.5);
	languageButton.addChild(languageText);
	languageButton.x = 0;
	languageButton.y = 120;
	LK.gui.top.addChild(languageButton);
	// Add event handler to language button
	languageButton.down = function (x, y, obj) {
		if (!languageMenuOpen) {
			showLanguageMenu();
		}
	};
	// Store reference for updates
	languageButton.textElement = languageText;
	// Create reset button
	var resetButton = new Container();
	var resetBackground = resetButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 120,
		height: 60,
		tint: 0xFF0000
	});
	var resetText = new Text2(getText('reset'), {
		size: 40,
		fill: 0xFFFFFF
	});
	resetText.anchor.set(0.5, 0.5);
	resetButton.addChild(resetText);
	resetButton.x = -150;
	resetButton.y = 50;
	LK.gui.topRight.addChild(resetButton);
	// Store reference for updates
	resetButton.textElement = resetText;
	// Add event handler to reset button
	resetButton.down = function (x, y, obj) {
		// Reset level to 1
		currentLevel = 1;
		storage.currentLevel = 1;
		// Reset match counter and requirements
		matchCounter = 0;
		matchesRequiredForNextLevel = 5;
		// Reset game state and board
		gameOver = true; // To stop game processing temporarily
		// Clear the board
		for (var row = 0; row < ROWS; row++) {
			for (var col = 0; col < COLS; col++) {
				var flower = gameBoard.removeFlower(row, col);
				if (flower) {
					flower.destroy();
				}
			}
		}
		// Reset and restart the game
		initGame();
	};
}
// Update UI elements
function updateUI() {
	scoreText.setText(getText('score') + currentScore);
	movesText.setText(getText('moves') + movesLeft);
	levelText.setText(getText('level') + currentLevel + ' (' + matchCounter + '/' + matchesRequiredForNextLevel + ')');
	LK.setScore(currentScore);
}
// Populate the board with flowers
function populateBoard() {
	// Create flowers and ensure no initial matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS; col++) {
			addNewFlower(row, col);
		}
	}
	// Check and resolve any initial matches
	var initialMatches = findAllMatches();
	while (initialMatches.length > 0) {
		// If we have initial matches, regenerate those flowers
		for (var i = 0; i < initialMatches.length; i++) {
			var matchedFlower = gameBoard.removeFlower(initialMatches[i].row, initialMatches[i].col);
			if (matchedFlower) {
				matchedFlower.destroy();
				addNewFlower(initialMatches[i].row, initialMatches[i].col);
			}
		}
		initialMatches = findAllMatches();
	}
}
// Add a new flower at the specified position
function addNewFlower(row, col) {
	// Choose a random flower type that doesn't create a match
	var validTypes = getValidFlowerTypes(row, col);
	var randomType = validTypes[Math.floor(Math.random() * validTypes.length)];
	// Create a new flower and add it to the board
	var flower = new Flower(randomType);
	gameBoard.addFlower(flower, row, col);
	return flower;
}
// Get valid flower types that don't create a match at position
function getValidFlowerTypes(row, col) {
	var invalidTypes = {}; // Use a regular object instead of Set
	// Check horizontal matches to avoid
	if (col >= 2) {
		var flower1 = gameBoard.getFlower(row, col - 1);
		var flower2 = gameBoard.getFlower(row, col - 2);
		if (flower1 && flower2 && flower1.type === flower2.type) {
			invalidTypes[flower1.type] = true; // Mark type as invalid
		}
	}
	// Check vertical matches to avoid
	if (row >= 2) {
		var flower1 = gameBoard.getFlower(row - 1, col);
		var flower2 = gameBoard.getFlower(row - 2, col);
		if (flower1 && flower2 && flower1.type === flower2.type) {
			invalidTypes[flower1.type] = true; // Mark type as invalid
		}
	}
	// Return valid types (all types minus invalid ones)
	return FLOWER_TYPES.filter(function (type) {
		return !invalidTypes[type]; // Check if type is in invalidTypes object
	});
}
// Handle flower selection
function selectFlower(flower) {
	if (isProcessingMatches || gameOver) {
		return;
	}
	if (selectedFlower === null) {
		// First selection
		selectedFlower = flower;
		selectedFlower.setSelected(true);
		LK.getSound('swap').play();
	} else if (selectedFlower === flower) {
		// Deselect
		selectedFlower.setSelected(false);
		selectedFlower = null;
	} else {
		// Second selection - check if adjacent
		if (gameBoard.areAdjacent(selectedFlower.row, selectedFlower.col, flower.row, flower.col)) {
			// Try to swap
			trySwapFlowers(selectedFlower, flower);
		} else {
			// Not adjacent, switch selection
			selectedFlower.setSelected(false);
			selectedFlower = flower;
			selectedFlower.setSelected(true);
			LK.getSound('swap').play();
		}
	}
}
// Try to swap flowers and check for matches
function trySwapFlowers(flower1, flower2) {
	// Swap flowers
	var row1 = flower1.row;
	var col1 = flower1.col;
	var row2 = flower2.row;
	var col2 = flower2.col;
	// Deselect first flower
	flower1.setSelected(false);
	selectedFlower = null;
	// Swap to check for matches
	gameBoard.swapFlowers(row1, col1, row2, col2, true, function () {
		// Check for matches after swap
		var matches = findAllMatches();
		if (matches.length > 0) {
			// Valid move - process matches
			decreaseMoves();
			processMatches(matches);
		} else {
			// Invalid move - swap back
			LK.getSound('invalid').play();
			gameBoard.swapFlowers(row2, col2, row1, col1, true);
		}
	});
}
// Decrease moves and check game over
function decreaseMoves() {
	movesLeft--;
	updateUI();
	// Check if game is over
	if (movesLeft <= 0 && remainingFlowers > 0) {
		endGame(false);
	}
}
// Process all matches
function processMatches(matches) {
	if (matches.length === 0) {
		return;
	}
	isProcessingMatches = true;
	// Calculate score based on match length
	var matchScore = 0;
	var matchCounts = {};
	// Group matches by type
	matches.forEach(function (match) {
		var flower = gameBoard.getFlower(match.row, match.col);
		if (flower) {
			if (!matchCounts[flower.type]) {
				matchCounts[flower.type] = 0;
			}
			matchCounts[flower.type]++;
		}
	});
	// Calculate score based on matches
	// Track licorice ball spawn positions
	var licoriceToSpawn = [];
	Object.keys(matchCounts).forEach(function (type) {
		var count = matchCounts[type];
		if (count >= 5) {
			matchScore += count * 15;
			LK.getSound('match5').play();
		} else if (count === 4) {
			matchScore += count * 10;
			LK.getSound('match4').play();
			// Find the 4-in-a-row and mark for licorice ball spawn
			// Horizontal
			for (var row = 0; row < ROWS; row++) {
				for (var col = 0; col < COLS - 3; col++) {
					var f1 = gameBoard.getFlower(row, col);
					var f2 = gameBoard.getFlower(row, col + 1);
					var f3 = gameBoard.getFlower(row, col + 2);
					var f4 = gameBoard.getFlower(row, col + 3);
					if (f1 && f2 && f3 && f4 && f1.type === type && f2.type === type && f3.type === type && f4.type === type) {
						// Place licorice ball at the second or third flower (centered)
						licoriceToSpawn.push({
							row: row,
							col: col + 1
						});
					}
				}
			}
			// Vertical
			for (var col = 0; col < COLS; col++) {
				for (var row = 0; row < ROWS - 3; row++) {
					var f1 = gameBoard.getFlower(row, col);
					var f2 = gameBoard.getFlower(row + 1, col);
					var f3 = gameBoard.getFlower(row + 2, col);
					var f4 = gameBoard.getFlower(row + 3, col);
					if (f1 && f2 && f3 && f4 && f1.type === type && f2.type === type && f3.type === type && f4.type === type) {
						licoriceToSpawn.push({
							row: row + 1,
							col: col
						});
					}
				}
			}
		} else {
			matchScore += count * 5;
			LK.getSound('match3').play();
		}
		// Count this as a successful match for level progression
		matchCounter++;
	});
	// Update score
	currentScore += matchScore;
	remainingFlowers -= matches.length;
	// Animate matches and remove flowers
	var animationsCompleted = 0;
	matches.forEach(function (match) {
		var flower = gameBoard.getFlower(match.row, match.col);
		if (flower) {
			gameBoard.removeFlower(match.row, match.col);
			flower.animateMatch(function () {
				flower.destroy();
				animationsCompleted++;
				// When all animations complete, make flowers fall and check for new matches
				if (animationsCompleted === matches.length) {
					// Spawn licorice balls if needed
					if (typeof licoriceToSpawn !== "undefined" && licoriceToSpawn.length > 0) {
						for (var i = 0; i < licoriceToSpawn.length; i++) {
							var pos = licoriceToSpawn[i];
							// Only spawn if cell is empty (flower was matched)
							if (!gameBoard.getFlower(pos.row, pos.col)) {
								var licorice = new LicoriceBall(pos.row, pos.col);
								// Place licorice ball in grid (so it can be found for explosion)
								gameBoard.grid[pos.row][pos.col] = licorice;
								// Position licorice ball
								licorice.x = pos.col * CELL_SIZE - gameBoard.boardWidth / 2 + CELL_SIZE / 2;
								licorice.y = pos.row * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
								gameBoard.addChild(licorice);
							}
						}
					}
					updateUI();
					makeFlowersFall(function () {
						fillEmptySpaces(function () {
							// Check for new matches after filling
							var newMatches = findAllMatches();
							if (newMatches.length > 0) {
								processMatches(newMatches);
							} else {
								isProcessingMatches = false;
								// Check if player reached required match count
								if (matchCounter >= matchesRequiredForNextLevel) {
									// Level completed
									endGame(true);
								} else if (remainingFlowers <= 0) {
									// All flowers cleared (alternative win condition)
									endGame(true);
								}
							}
						});
					});
				}
			});
		}
	});
}
// Make flowers fall to fill empty spaces
function makeFlowersFall(callback) {
	var animationsInProgress = 0;
	// Process columns bottom to top
	for (var col = 0; col < COLS; col++) {
		var emptySpaces = 0;
		// Process rows bottom to top
		for (var row = ROWS - 1; row >= 0; row--) {
			var flower = gameBoard.getFlower(row, col);
			if (!flower) {
				emptySpaces++;
			} else if (emptySpaces > 0) {
				// Move flower down by the number of empty spaces
				var newRow = row + emptySpaces;
				animationsInProgress++;
				// Update grid reference
				gameBoard.grid[row][col] = null;
				gameBoard.grid[newRow][col] = flower;
				// Update flower position properties
				flower.row = newRow;
				// Animate the fall
				var targetY = newRow * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
				if (typeof flower.moveTo === "function") {
					flower.moveTo(flower.x, targetY, 300, function () {
						animationsInProgress--;
						if (animationsInProgress === 0 && callback) {
							callback();
						}
					});
				} else {
					// Fallback for objects without moveTo (e.g. LicoriceBall)
					flower.y = targetY;
					animationsInProgress--;
					if (animationsInProgress === 0 && callback) {
						callback();
					}
				}
			}
		}
	}
	if (animationsInProgress === 0 && callback) {
		callback();
	}
}
// Fill empty spaces at the top with new flowers
function fillEmptySpaces(callback) {
	var animationsInProgress = 0;
	for (var col = 0; col < COLS; col++) {
		// Find empty spaces at the top
		for (var row = 0; row < ROWS; row++) {
			if (!gameBoard.getFlower(row, col)) {
				// Create a new flower above the board
				var flower = new Flower(FLOWER_TYPES[Math.floor(Math.random() * FLOWER_TYPES.length)]);
				gameBoard.addFlower(flower, row, col);
				// Position it above the board
				flower.y -= (row + 1) * CELL_SIZE;
				// Animate it falling down
				animationsInProgress++;
				remainingFlowers++;
				var targetY = row * CELL_SIZE - gameBoard.boardHeight / 2 + CELL_SIZE / 2;
				flower.moveTo(flower.x, targetY, 300, function () {
					animationsInProgress--;
					if (animationsInProgress === 0 && callback) {
						callback();
					}
				});
			}
		}
	}
	if (animationsInProgress === 0 && callback) {
		callback();
	}
}
// Find all matching flowers on the board
function findAllMatches() {
	var matches = [];
	var visited = {};
	// Check horizontal matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS - 2; col++) {
			var flower1 = gameBoard.getFlower(row, col);
			var flower2 = gameBoard.getFlower(row, col + 1);
			var flower3 = gameBoard.getFlower(row, col + 2);
			if (flower1 && flower2 && flower3 && flower1.type === flower2.type && flower2.type === flower3.type) {
				// Add match if not already added
				var key1 = row + "," + col;
				var key2 = row + "," + (col + 1);
				var key3 = row + "," + (col + 2);
				if (!visited[key1]) {
					matches.push({
						row: row,
						col: col
					});
					visited[key1] = true;
				}
				if (!visited[key2]) {
					matches.push({
						row: row,
						col: col + 1
					});
					visited[key2] = true;
				}
				if (!visited[key3]) {
					matches.push({
						row: row,
						col: col + 2
					});
					visited[key3] = true;
				}
			}
		}
	}
	// Check vertical matches
	for (var row = 0; row < ROWS - 2; row++) {
		for (var col = 0; col < COLS; col++) {
			var flower1 = gameBoard.getFlower(row, col);
			var flower2 = gameBoard.getFlower(row + 1, col);
			var flower3 = gameBoard.getFlower(row + 2, col);
			if (flower1 && flower2 && flower3 && flower1.type === flower2.type && flower2.type === flower3.type) {
				// Add match if not already added
				var key1 = row + "," + col;
				var key2 = row + 1 + "," + col;
				var key3 = row + 2 + "," + col;
				if (!visited[key1]) {
					matches.push({
						row: row,
						col: col
					});
					visited[key1] = true;
				}
				if (!visited[key2]) {
					matches.push({
						row: row + 1,
						col: col
					});
					visited[key2] = true;
				}
				if (!visited[key3]) {
					matches.push({
						row: row + 2,
						col: col
					});
					visited[key3] = true;
				}
			}
		}
	}
	return matches;
}
// Check if any valid moves exist
function hasValidMoves() {
	// Check each position for potential swaps that create matches
	for (var row = 0; row < ROWS; row++) {
		for (var col = 0; col < COLS; col++) {
			// Check right swap
			if (col < COLS - 1) {
				// Simulate swap right
				var flower1 = gameBoard.getFlower(row, col);
				var flower2 = gameBoard.getFlower(row, col + 1);
				if (flower1 && flower2) {
					// Swap
					gameBoard.swapFlowers(row, col, row, col + 1, false);
					// Check for matches
					var matches = findAllMatches();
					// Swap back
					gameBoard.swapFlowers(row, col + 1, row, col, false);
					if (matches.length > 0) {
						return true;
					}
				}
			}
			// Check down swap
			if (row < ROWS - 1) {
				// Simulate swap down
				var flower1 = gameBoard.getFlower(row, col);
				var flower2 = gameBoard.getFlower(row + 1, col);
				if (flower1 && flower2) {
					// Swap
					gameBoard.swapFlowers(row, col, row + 1, col, false);
					// Check for matches
					var matches = findAllMatches();
					// Swap back
					gameBoard.swapFlowers(row + 1, col, row, col, false);
					if (matches.length > 0) {
						return true;
					}
				}
			}
		}
	}
	return false;
}
// End the game
function endGame(success) {
	gameOver = true;
	if (success) {
		// Level completed
		currentLevel++;
		storage.currentLevel = currentLevel;
		// Reset match counter and increase requirements for next level
		matchCounter = 0;
		matchesRequiredForNextLevel = 5 + (currentLevel - 1) * 3; // 5 for level 1, +3 for each level
		// Update high score
		if (currentScore > highScore) {
			highScore = currentScore;
			storage.highScore = highScore;
		}
		// Show you win screen
		LK.getSound('levelup').play();
		LK.showYouWin();
	} else {
		// Game over - ran out of moves
		currentLevel = 1;
		storage.currentLevel = currentLevel;
		// Update high score
		if (currentScore > highScore) {
			highScore = currentScore;
			storage.highScore = highScore;
		}
		// Show game over screen
		LK.showGameOver();
	}
}
// Initialize the game
initGame();
// Main game update loop
game.update = function () {
	// If no valid moves exist, shuffle the board
	if (!isProcessingMatches && !gameOver && !hasValidMoves()) {
		// Shuffle the board
		var allFlowers = [];
		// Collect all flowers
		for (var row = 0; row < ROWS; row++) {
			for (var col = 0; col < COLS; col++) {
				var flower = gameBoard.removeFlower(row, col);
				if (flower) {
					flower.destroy();
				}
			}
		}
		// Repopulate the board
		populateBoard();
	}
};
// Handle touch/mouse input on game board
game.down = function (x, y, obj) {
	// This is handled in the Flower class
};
game.move = function (x, y, obj) {
	// Handle dragging of selected flower
	if (selectedFlower && !isProcessingMatches && !gameOver) {
		// Get position in gameBoard coordinates
		var localPos = gameBoard.toLocal({
			x: x,
			y: y
		});
		// Calculate which cell the player is hovering over
		var hoverCol = Math.floor((localPos.x + gameBoard.boardWidth / 2) / CELL_SIZE);
		var hoverRow = Math.floor((localPos.y + gameBoard.boardHeight / 2) / CELL_SIZE);
		// Check if it's a valid cell and adjacent to the original position
		if (hoverRow >= 0 && hoverRow < ROWS && hoverCol >= 0 && hoverCol < COLS && gameBoard.areAdjacent(selectedFlower.row, selectedFlower.col, hoverRow, hoverCol)) {
			// Get the flower at the hover position
			var targetFlower = gameBoard.getFlower(hoverRow, hoverCol);
			if (targetFlower && targetFlower !== selectedFlower) {
				// Try to swap the flowers
				trySwapFlowers(selectedFlower, targetFlower);
			}
		}
	}
};
game.up = function (x, y, obj) {
	// No global up handling needed
};
// Show language selection menu
function showLanguageMenu() {
	if (languageMenuOpen) return;
	languageMenuOpen = true;
	// Create language menu container
	languageMenuContainer = new Container();
	// Create background overlay
	var overlay = languageMenuContainer.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 2048,
		height: 2732,
		tint: 0x000000,
		alpha: 0.8
	});
	// Create menu background
	var menuBackground = languageMenuContainer.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 1200,
		height: 1800,
		tint: 0xFFFFFF
	});
	// Create title
	var titleText = new Text2(getText('chooseLanguage'), {
		size: 80,
		fill: 0x000000
	});
	titleText.anchor.set(0.5, 0.5);
	titleText.y = -700;
	languageMenuContainer.addChild(titleText);
	// Create language buttons
	var buttonStartY = -500;
	var buttonSpacing = 120;
	for (var i = 0; i < SUPPORTED_LANGUAGES.length; i++) {
		var lang = SUPPORTED_LANGUAGES[i];
		var langButton = new Container();
		// Button background
		var buttonBg = langButton.attachAsset('cell', {
			anchorX: 0.5,
			anchorY: 0.5,
			width: 800,
			height: 100,
			tint: currentLanguage === lang.code ? 0x00FF00 : 0x808080
		});
		// Language name
		var langName = new Text2(lang.name, {
			size: 50,
			fill: 0x000000
		});
		langName.anchor.set(0, 0.5);
		langName.x = -300;
		langButton.addChild(langName);
		// Choice button
		var choiceButton = new Container();
		var choiceBg = choiceButton.attachAsset('cell', {
			anchorX: 0.5,
			anchorY: 0.5,
			width: 200,
			height: 80,
			tint: 0x0066CC
		});
		var choiceText = new Text2(getText('choice'), {
			size: 40,
			fill: 0xFFFFFF
		});
		choiceText.anchor.set(0.5, 0.5);
		choiceButton.addChild(choiceText);
		choiceButton.x = 250;
		// Add choice button event
		choiceButton.languageCode = lang.code;
		choiceButton.down = function (x, y, obj) {
			selectLanguage(this.languageCode);
		};
		langButton.addChild(choiceButton);
		langButton.y = buttonStartY + i * buttonSpacing;
		languageMenuContainer.addChild(langButton);
	}
	// Create back button
	var backButton = new Container();
	var backBg = backButton.attachAsset('cell', {
		anchorX: 0.5,
		anchorY: 0.5,
		width: 300,
		height: 100,
		tint: 0xFF0000
	});
	var backText = new Text2(getText('back'), {
		size: 50,
		fill: 0xFFFFFF
	});
	backText.anchor.set(0.5, 0.5);
	backButton.addChild(backText);
	backButton.y = 700;
	backButton.down = function (x, y, obj) {
		hideLanguageMenu();
	};
	languageMenuContainer.addChild(backButton);
	// Position and add to game
	languageMenuContainer.x = 2048 / 2;
	languageMenuContainer.y = 2732 / 2;
	game.addChild(languageMenuContainer);
}
// Hide language menu
function hideLanguageMenu() {
	if (languageMenuContainer) {
		languageMenuContainer.destroy();
		languageMenuContainer = null;
	}
	languageMenuOpen = false;
}
// Select a language
function selectLanguage(languageCode) {
	currentLanguage = languageCode;
	storage.language = languageCode;
	// Update all UI text
	updateAllUIText();
	// Hide language menu
	hideLanguageMenu();
}
// Update all UI text with current language
function updateAllUIText() {
	// Update main UI
	updateUI();
	// Update button texts
	var topContainer = LK.gui.top;
	for (var i = 0; i < topContainer.children.length; i++) {
		var child = topContainer.children[i];
		if (child.textElement && child.textElement.text) {
			if (child.textElement.text.indexOf('Change') >= 0 || child.textElement.text.indexOf('Changer') >= 0 || child.textElement.text.indexOf('Cambiar') >= 0 || child.textElement.text.indexOf('Cambia') >= 0 || child.textElement.text.indexOf('Schimbă') >= 0 || child.textElement.text.indexOf('Zmień') >= 0 || child.textElement.text.indexOf('Αλλαγή') >= 0 || child.textElement.text.indexOf('Spielsprache') >= 0 || child.textElement.text.indexOf('更改') >= 0 || child.textElement.text.indexOf('ゲーム言語') >= 0) {
				child.textElement.setText(getText('changeLanguage'));
			}
		}
	}
	var topRightContainer = LK.gui.topRight;
	for (var i = 0; i < topRightContainer.children.length; i++) {
		var child = topRightContainer.children[i];
		if (child.textElement && child.textElement.text) {
			if (child.textElement.text === 'RESET' || child.textElement.text === 'リセット' || child.textElement.text === 'ΕΠΑΝΑΦΟΡΑ' || child.textElement.text === '重置') {
				child.textElement.setText(getText('reset'));
			}
		}
	}
}
// Trigger the licorice explosion: remove all flowers in the column, trigger combo mode for 8 seconds
function triggerLicoriceExplosion(row, col) {
	if (gameOver || isProcessingMatches) return;
	isProcessingMatches = true;
	// Remove all flowers in the column (except LicoriceBall itself)
	for (var r = 0; r < ROWS; r++) {
		var obj = gameBoard.getFlower(r, col);
		if (obj && !(obj instanceof LicoriceBall)) {
			gameBoard.removeFlower(r, col);
			if (typeof obj.animateMatch === "function") {
				obj.animateMatch(function () {
					obj.destroy();
				});
			} else {
				obj.destroy();
			}
			remainingFlowers--;
		}
	}
	// Remove the LicoriceBall itself
	var licorice = gameBoard.getFlower(row, col);
	if (licorice && licorice instanceof LicoriceBall) {
		gameBoard.removeFlower(row, col);
		licorice.destroy();
	}
	// Combo mode: for 8 seconds, after each match, auto-match adjacent flowers
	var comboEndTime = Date.now() + 8000;
	var originalProcessMatches = processMatches;
	var comboActive = true;
	// Helper to auto-match adjacent flowers after each match
	function comboProcessMatches(matches) {
		originalProcessMatches(matches);
		// After normal match processing, auto-match adjacent flowers if combo is still active
		if (comboActive && !gameOver) {
			LK.setTimeout(function () {
				var newMatches = [];
				// Find all adjacent pairs and add to matches
				for (var row = 0; row < ROWS; row++) {
					for (var col = 0; col < COLS; col++) {
						var f = gameBoard.getFlower(row, col);
						if (!f || f instanceof LicoriceBall) continue;
						// Check right
						var fRight = gameBoard.getFlower(row, col + 1);
						if (fRight && fRight.type === f.type && !(fRight instanceof LicoriceBall)) {
							newMatches.push({
								row: row,
								col: col
							});
							newMatches.push({
								row: row,
								col: col + 1
							});
						}
						// Check down
						var fDown = gameBoard.getFlower(row + 1, col);
						if (fDown && fDown.type === f.type && !(fDown instanceof LicoriceBall)) {
							newMatches.push({
								row: row,
								col: col
							});
							newMatches.push({
								row: row + 1,
								col: col
							});
						}
					}
				}
				// Remove duplicates
				var seen = {};
				var uniqueMatches = [];
				for (var i = 0; i < newMatches.length; i++) {
					var key = newMatches[i].row + "," + newMatches[i].col;
					if (!seen[key]) {
						uniqueMatches.push(newMatches[i]);
						seen[key] = true;
					}
				}
				if (uniqueMatches.length > 0 && comboActive) {
					comboProcessMatches(uniqueMatches);
				} else {
					isProcessingMatches = false;
				}
			}, 350); // Wait for match animation
		} else {
			isProcessingMatches = false;
		}
	}
	// Override processMatches for combo mode
	processMatches = comboProcessMatches;
	// End combo mode after 8 seconds
	LK.setTimeout(function () {
		comboActive = false;
		processMatches = originalProcessMatches;
		isProcessingMatches = false;
	}, 8000);
	// After explosion, let flowers fall and fill, then check for matches
	makeFlowersFall(function () {
		fillEmptySpaces(function () {
			var matches = findAllMatches();
			if (matches.length > 0) {
				processMatches(matches);
			} else {
				isProcessingMatches = false;
			}
		});
	});
}