function organizeTiles()
{
	tiles
		.forEach 	(
						(e) =>	{
									e.neighbours.left = tiles.find(f => f.coords.left == e.coords.left - 1 && f.coords.top == e.coords.top);
									e.neighbours.top = tiles.find(f => f.coords.left == e.coords.left && f.coords.top == e.coords.top - 1);
									e.neighbours.right = tiles.find(f => f.coords.left == e.coords.left + 1 && f.coords.top == e.coords.top);
									e.neighbours.bottom = tiles.find(f => f.coords.left == e.coords.left && f.coords.top == e.coords.top + 1);
									if (destroyedCells[e.index])
									{
										tiles[e.index].tile.addClass('usedTile');
									}
									else
									{
										tiles[e.index].tile.removeClass('usedTile');
									}
								}
					)
}

function findBlock(number, way, stack)
{
	const tile = tiles[number];
	let result = [tile];
	stack = stack == undefined ? [] : stack;
	if (way != 'right' && tile.neighbours.left && tile.neighbours.left.type == tile.type && !stack.find(e => e == tile.neighbours.left.index))
	{
		stack.push(tile.neighbours.left.index);
		result.push(tile.neighbours.left, ...findBlock(tile.neighbours.left.index, 'left', stack));
	}
	if (way != 'bottom' && tile.neighbours.top && tile.neighbours.top.type == tile.type && !stack.find(e => e == tile.neighbours.top.index))
	{
		stack.push(tile.neighbours.top.index);
		result.push(tile.neighbours.top, ...findBlock(tile.neighbours.top.index, 'top', stack));
	}
	if (way != 'left' && tile.neighbours.right && tile.neighbours.right.type == tile.type && !stack.find(e => e == tile.neighbours.right.index))
	{
		stack.push(tile.neighbours.right.index);
		result.push(tile.neighbours.right, ...findBlock(tile.neighbours.right.index, 'right', stack));
	}
	if (way != 'top' && tile.neighbours.bottom && tile.neighbours.bottom.type == tile.type && !stack.find(e => e == tile.neighbours.bottom.index))
	{
		stack.push(tile.neighbours.bottom.index);
		result.push(tile.neighbours.bottom, ...findBlock(tile.neighbours.bottom.index, 'bottom', stack));
	}
	return [...new Set(result)];
}

function createNewTile(topPosition, line, column, index, chances)
{
	let newTile = {};
	let specialChances = chances == undefined ? bonusChances : chances;
	let theType = "";
	let draw = Object.keys(specialChances).sort((a, b) => specialChances[a] < specialChances[b] ? 1 : -1).map(e => {const result = Math.random(); return {bonus: e, value: result, special: result <= specialChances[e] / 1000};});
	if (!draw.some(e => e.special == true))
	{
		theType = "stone-" + parseInt(1 + (Math.random() * numberOfTypes));
		newTile.specialType = 'none';
		newTile.specialTypeData = 'none';
	}
	else
	{
		theType = draw.find(e => e.special).bonus;
		newTile.specialType = theType;
		newTile.specialTypeData = 'none';
		if (theType == 'rocket')
		{
			newTile.specialTypeData = [180, 270, 0, 90][parseInt(Math.random() * 4)];
		}
	}
	let tile = 	$('<img draggable="false" class="tile" data-id="' + line + '-' + column + '" data-index="' + index + '" src="images/' + theType + '.png">')
					.css 	(
								{
									left: (column * tileSize) + 'px',
									top: topPosition + 'px',
									transform: newTile.specialTypeData == 'none' ? '' : 'rotate(' + (newTile.specialTypeData) + 'deg)'
								}
							);
	newTile.coords = {left: column, top: line};
	newTile.neighbours = {};
	newTile.type  = theType;
	newTile.tile = tile;
	newTile.index = index;
	return newTile;
}

function doCommand(e)
{
    let command = $(e.currentTarget).attr('data-cmd');
	if (window[command])
	{
		window[command](e);
	}
	else
	{
 		console.log("La commande " + command + " n'existe pas");
	}
}

function startGame()
{
	playRandomSong();
	playWooshSound();
	$('.mainPanelContainer').css('top', '105%');
	setTimeout 	(
					showLevelGoal,
					1000
				);
}

function showLevelGoal()
{
	playWooshSound();
	$('.menuPanel, .bonusPanel, .gameOverPanel').addClass('cache');
	$('.levelPanel').removeClass('cache');
	$('.levelTitle').text('Niveau ' + gameLevel);
	levelTimeLimit = [95, 85, 70, 55][Math.min(3, parseInt(gameLevel / 15))];
	missionGoal = Math.min(79 + gameLevel, 117);
	maxTurn = [50, 45, 40, 35, 30, 25, 20, 15][Math.min(7, parseInt(gameLevel / 5))];
	numberOfTypes = 2 + (1 + parseInt(gameLevel / 15));
	$('.explainGoalLevel').text('Pour ce niveau vous disposez de ' + levelTimeLimit + ' secondes pour nettoyer au moins ' + missionGoal + ' cases en un maximum de ' + maxTurn + ' coups.' + (gameLevel % 15 == 0 ? " Un nouveau type de gemmes entre en jeu à partir de ce niveau !" : ""));
	$('.mainPanelContainer').css('top', '5%');
	setTimeout 	(
					e => 	{
								playWooshSound();
								$('.mainPanelContainer').css('top', '105%');
								setTimeout  (
												e => 	{
															$('.mainPanel').addClass('cache');
															launchGame();
														},
														1000
											);
							},
					5000
				);
}

function launchGame()
{
	gameInPlay = true;
	playedTurns = 0;
	$('.gameBoard, .infoZone').removeClass('cache');
	$('.timeBarValue').css (
				    {
				      height: '99.4%',
				      background: 'springgreen'
				    }
				  );
	if (gameLevel >= 1)
	{
		destroyedCells = [];
		tiles = [];
		$('.tile').remove();
	}
	loadTiles();
	updateGoal();
	setTimeout (
		      e => {animateTimeBar(levelTimeLimit);},
		      3000
		    );
}

function updateGoal()
{
	$('#goalLevel').text("Niveau " + gameLevel + ' - ' + Math.max(0, missionGoal) + (missionGoal > 1 ? " cases restantes" : " case restante") + " - " + (playedTurns == 0 ? "Aucun coup joué" : (playedTurns == 1 ? "Premier coup joué" : playedTurns + " coups joués")) + ' - Vies : ' + numberOfPlay);
	if (missionGoal <= 0 || playedTurns > maxTurn)
	{
		gameInPlay = false;
		showLevelStatus();
	}
}

function showLevelStatus()
{
	stopTimeBarAnimation();
	if (missionGoal <= 0)
	{
		playWooshSound();
		$('.timeBar').removeClass('blink').css('opacity', '1');
		$('.mainPanel, .bonusPanel').removeClass('cache');
		$('.menuPanel, .levelPanel, .gameOverPanel').addClass('cache');
		$('.bonusPanel .explainGame').text('Excellent ! Vous venez de terminer le niveau ' + gameLevel);
		$('.mainPanelContainer').css('top', '5%');
		playLevelUpSound();
		addBonusLevel();
		setTimeout  (
						e =>	{
									gameLevel++;
									playWooshSound();
									$('.mainPanelContainer').css('top', '105%');
									setTimeout  (
													e => 	{
																showLevelGoal();
															}
													,1000
												);
								},
						4000
					);
	}
	else
	{
		playLevelFailSound();
		$('.timeBar').removeClass('blink').css('opacity', '1');
		if (--numberOfPlay > 0)
		{
			playWooshSound();
			$('.mainPanel, .bonusPanel').removeClass('cache');
			$('.menuPanel, .levelPanel, .gameOverPanel').addClass('cache');
			$('.bonusPanel .explainGame').text('Dommage ! ' + (playedTurns > maxTurn ? 'Le nombre maximal de coups a été joué' : 'Le temps imparti est écoulé') + ' et le contrat n\'est pas rempli. Il vous reste ' + numberOfPlay + ' tentative' + (numberOfPlay > 1 ? 's' : '') + ', courage !');
			$('.mainPanelContainer').css('top', '5%');
			setTimeout  (
							e =>	{
										playWooshSound();
										$('.mainPanelContainer').css('top', '105%');
										setTimeout  (
														e => 	{
																	showLevelGoal();
																}
														,1000
													);
									},
							5000
						);
		}
		else
		{
			stopMusic();
			gameInPlay = false;
			$('.mainPanel, .gameOverPanel').removeClass('cache');
			$('.menuPanel, .levelPanel, .bonusPanel').addClass('cache');
			$('.gameOverPanel .explainGame').text('Dommage ! ' + (playedTurns > maxTurn ? 'Le nombre maximal de coups a été joué' : 'Le temps imparti est écoulé') + ' et le contrat n\'est pas rempli. Vous avez manqué toutes vos tentatives, la partie est maintenant terminée.');
			$('.mainPanelContainer').css('top', '5%');
		}
	}
}

function goToMenu()
{
	playWooshSound();
	$('.gameBoard, .infoZone').addClass('cache');
	$('.mainPanelContainer').css('top', '105%');	
	setTimeout  (
					e =>	{
								$('.tile').remove();
								tiles = [];
								destroyedCells = [];
								addToScore(-playerScore);
								gameLevel = 1;
								numberOfPlay = 3;
								playedTurns = 0;
								numberOfTypes = 3;
								$('.timeBar').removeClass('blink');
								$('.mainPanel, .menuPanel').removeClass('cache');
								$('.levelPanel, .bonusPanel, .gameOverPanel').addClass('cache');
								$('.mainPanelContainer').css('top', '5%');
								playWooshSound();
							},
					1500
				);
}
