/**
 *---------------------
 *  JS连连看游戏
 *  作者：jat
 *  2006年9月6日
 *  www.tmcode.net
 *---------------------
 */
var rows = 10;
var cols = 14;
var paused = false;
var uncellNum = (rows-2)*(cols-2);
var styleImg = new Array();
var aImgCell = new Array();
var icons = new Array();
var inicell = "";
var aCell = new Array(rows*cols);
var PathQ = new Array();
var loadedImg = 0;
var startCell = null;
var endCell = null;
var blinkStat = 0;
var blinkInter = null;
var theme = "war";
var score = 3000;
var level = Math.floor(score / 1000);
var gameTime = 0;
var lockLD = true;
var countTimer = null;
var loadTimeout = null;       // 加载过期timerID
var timeout = 60000;          // 加载图标时的超时时间，默认为一分钟
var showingTimer = null;      // 路径显示timerID
var dist = 20;                // 分数移动执行次数
var alpha = 100;              // 分数透明度
var scoTimer = null;          // 分数冒泡timerID
var cfHidding = null;
function setTheme()
{
	document.getElementById("cover").style.backgroundImage = "url(img/" + theme + "/cover.gif)";
	document.getElementById("pan").style.backgroundImage = "url(img/" + theme + "/background.gif)";
	/**
	 * 预加载部分
	 */
	icons[0]      = new Image(48,48);                         //消失效果
	icons[0].src  = "img/" + theme + "/hide.gif";
	icons[1]      = new Image(48,48);                         //空白
	icons[1].src  = "img/blank.gif";
	icons[2]      = new Image(48,48);                         //点亮的边框
	icons[2].src  = "img/" + theme + "/active.gif";     //以下为路径
	icons[3]      = new Image(48,48);
	icons[3].src  = "img/" + theme + "/px-1py0nx1ny0.gif";
	icons[4]      = new Image(48,48);
	icons[4].src  = "img/" + theme + "/px0py1nx0ny-1.gif";
	icons[5]      = new Image(48,48);
	icons[5].src  = "img/" + theme + "/px0py1nx1ny0.gif";
	icons[6]      = new Image(48,48);
	icons[6].src  = "img/" + theme + "/px0py1nx-1ny0.gif";
	icons[7]      = new Image(48,48);
	icons[7].src  = "img/" + theme + "/px0py-1nx0ny1.gif";
	icons[8]      = new Image(48,48);
	icons[8].src  = "img/" + theme + "/px0py-1nx1ny0.gif";
	icons[9]      = new Image(48,48);
	icons[9].src  = "img/" + theme + "/px0py-1nx-1ny0.gif";
	icons[10]     = new Image(48,48);
	icons[10].src = "img/" + theme + "/px1py0nx0ny1.gif";
	icons[11]     = new Image(48,48);
	icons[11].src = "img/" + theme + "/px1py0nx0ny-1.gif";
	icons[12]     = new Image(48,48);
	icons[12].src = "img/" + theme + "/px1py0nx-1ny0.gif";
	icons[13]     = new Image(48,48);
	icons[13].src = "img/" + theme + "/px-1py0nx0ny1.gif";
	icons[14]     = new Image(48,48);
	icons[14].src = "img/" + theme + "/px-1py0nx0ny-1.gif";
	/*预加载部分*/
}

function pause(tar)
{
	if(!paused)
	{
		paused = true;
		showCover("pause");
		clearInterval(countTimer);
		tar.value = " 继 续 ";
	}
	else
	{
		showCover("");
		countTimer = setInterval("countdown()",1000);
		paused = false;
		tar.value = " 暂 停 ";
	}
}
function showCover(action)
{
	var cover = document.getElementById("cover");
	cover.style.height = cover.parentNode.offsetHeight - 4;
	cover.style.visibility = "visible";
	switch(action)
	{
		case "pause":cover.children[0].innerText = "暂停中...";cover.children[1].style.visibility = "hidden";
		break;
		case "loading":cover.children[0].innerText = "正在加载图标...";cover.children[1].style.visibility = "visible";
		break;
		case "done":cover.children[0].innerText = "完成！";cover.children[1].style.visibility = "hidden";
		break;
		case "loose":cover.children[0].innerText = "失败！";cover.children[1].style.visibility = "hidden";
		break;
		default:cover.style.visibility = "hidden";cover.children[1].style.visibility = "hidden";
	}
}
function countdown()
{
	gameTime ++;
	document.getElementById("tTime").value = gameTime;
	if(score > 0)
	{
		score -= level + 1;
		level = Math.max(Math.floor(score / 1000),0);
		document.getElementById("level").value = level;
		document.getElementById("tscore").value = score;
	}
}
function errLoad()
{
	clearInterval(loadTimeout);
	alert("超时，未能完成加载！");
	showCover("");
}
function loaded()
{
	if(!lockLD)
	{
		loadedImg ++;
		var LDpercent = Math.floor(loadedImg / uncellNum * 100);
		document.getElementById("loadInc").style.width = LDpercent + "%";
		document.getElementById("loadInc").innerText = LDpercent + "%";
		if(LDpercent == 100)
		{
			showCover("");
			loadedImg = 0;
			clearTimeout(loadTimeout);
			clearInterval(countTimer);
			countTimer = setInterval("countdown()",1000);
			lockLD = true;
		}
	}
}
////////////////////////////////////////
Array.prototype.Random = function()
{
	var rnd;
	var swap;
	for(var i = 0;i< this.length;i++)
	{
		rnd = Math.floor(Math.random()*(i+1));
		swap = this[i];
		this[i]=this[rnd];
		this[rnd]=swap;
	}
return this;
}
document.write("<table cellspacing=\"0\" cellpadding=\"0\" border=\"0\">");
for(i=0;i<rows;i++)
{
	document.write("<tr>");
	for(j=0;j<cols;j++)
	{
		var cellIndex = cols * i + j;
		document.write("<td class='blank'><img src=\"img/blank.gif\" class=\"cellimg\" onmousedown='connCell("+cellIndex+")' height=\"48\" width=\"48\" border=\"0\" hspace=\"0\" vspace=\"0\" id=\"cell_"+cellIndex+"\" onload=\"loaded()\" /></td>");
		aCell[cellIndex] = new Cell(0,j,i);
	}
	document.write("</tr>");
}
document.write("</table>");
////////////////////////////////////////
function Cell(stat,x,y)
{
	this.x = x;
	this.y = y;
	this.stat = stat;
	this.index = this.y * cols + this.x;
}
function Cell.prototype.setStat(stat)
{
	this.stat = stat;
	setStyle(this.index);
}
function Cell.prototype.Blink()
{
	blinkInter = setInterval("blinkCell("+this.index+")",200);
}
function blinkCell(cellIndex)
{
	if(blinkStat == 0)
		document.getElementById("cell_"+cellIndex).offsetParent.style.backgroundColor = "transparent";
	if(blinkStat == 1)
		document.getElementById("cell_"+cellIndex).offsetParent.style.backgroundColor = "white";
	if(blinkStat == 2)
	{
		document.getElementById("cell_"+cellIndex).offsetParent.style.backgroundColor = "red";
		blinkStat = 0;
	}
	blinkStat ++ ;
}
function resetMap()
{
	clearInterval(countTimer);
	document.getElementById("loadInc").style.width = 0;
	showCover("loading");
	uncellNum = (rows - 2) * (cols - 2);//用于检测游戏完成，在此初始
	lockLD = false;
	loadedImg = 0;
	gameTime = 0;   //初始游戏时间
	if(paused)
	{
		paused = false;
		document.getElementById("pausebutton").value = "-暂-停-"
	}
	for(var sel = 0;sel < document.getElementById("themes").options.length;sel ++)   //检查主题
		if(document.getElementById("themes").options[sel].selected == true)
		{
			theme = document.getElementById("themes").options[sel].value;
			document.getElementById("cTheme").value = document.getElementById("themes").options[sel].innerText;
			break;
		}
	setTheme();
	for(imgN = 1;imgN<=30;imgN++)
	{
		styleImg[imgN-1] = imgN;
	}
	for(var A1=0;A1 < (rows-2)*(cols-2);A1+=2)                      //生成成对的图标
	{
		var tmp = Math.floor(Math.random()*styleImg.length);
		aImgCell[A1] = styleImg[tmp];
		aImgCell[A1+1] = styleImg[tmp];
	}
	score = 3000;
	loadTimeout = setTimeout("errLoad()",timeout);
	//document.getElementById("rndButton").innerText = "打乱 × " + (score / 1000);
	rndMap(false);
}


/////////////////////////////////////////////
function hotcell(cell)
{
	var tar = document.getElementById("cell_" + cell).offsetParent;//alert(theme)
	if(tar.style.backgroundImage != "url(img/" + theme + "/active.gif)")
	{
		tar.style.backgroundImage = "url(img/" + theme + "/active.gif)";
	}
	else
	{
		tar.style.backgroundImage = "url(img/blank.gif)";
	}
}
function setStyle(cellIndex)
{
	if(typeof aCell[cellIndex].stat == "number")
	{
		if(aCell[cellIndex].stat > 0)
			document.getElementById("cell_"+cellIndex).src = "img/" + theme + "/" + aCell[cellIndex].stat +".gif";
		if(aCell[cellIndex].stat == 0)
			document.getElementById("cell_"+cellIndex).src = icons[1].src;
		if(aCell[cellIndex].stat == -1)
			document.getElementById("cell_"+cellIndex).src = icons[0].src;
	}
	else
	{
		document.getElementById("cell_"+cellIndex).src = "img/" + theme + "/" + aCell[cellIndex].stat +".gif";
	}
}
function rndMap(imp)//随机打乱图标
{
	if(score >= 1000 || !imp)
	{
		aImgCell.Random();
		for(var i=1;i<rows-1;i++)
			for(var j=1;j<cols-1;j++)
			{
				aCell[i * cols + j].setStat(aImgCell[(i - 1) * (cols - 2) + (j-1)]);
			}
		if(imp)
		{
			showScore(-1000);
		}
	}
	else
	{
		showScore("需要等级" + (level + 1) + "！");
	}
	document.getElementById("rndButton").innerText = "打乱 × " + level;
}
///////////////////////////////////
function getRoad_NS(cell)
{
	var tmp = cell.y + 1;
	var trainInd = 1;
	var train = new Array();
	train[0] = cell.y;
	while(tmp < rows)
	{
		if(aCell[tmp*cols+cell.x].stat <= 0)
		{
			train[trainInd] = tmp;
			trainInd++;
			tmp++;
		}
		else
		break;
	}
	tmp = cell.y-1;
	while(tmp >= 0)
	{
		if(aCell[tmp*cols+cell.x].stat <= 0)
		{
			train[trainInd] = tmp;
			trainInd++;
			tmp--;
		}
		else
		break;
	}
	return train;
}
function getRoad_WE(cell)
{
	var tmp = cell.x+1;
	var trainInd = 1;
	var train = new Array();
	train[0] = cell.x;
	while(tmp < cols)
	{
		if(aCell[cell.y*cols+tmp].stat <= 0)
		{
			train[trainInd] = tmp;
			trainInd++;
			tmp++;
		}
		else
		break;
	}
	tmp = cell.x-1;
	while(tmp >= 0)
	{
		if(aCell[cell.y*cols+tmp].stat <= 0)
		{
			train[trainInd] = tmp;
			trainInd++;
			tmp--;
		}
		else
		break;
	}
	return train;;
}
function getBridgeX(sCell,eCell)
{
	var bridgeStart = Math.min(sCell.x,eCell.x)+1;
	var edge = new Array();
	var bridgeL = Math.abs(sCell.x - eCell.x) + bridgeStart;
	var edgeInd = 0;
	
	var sCellRoad = getRoad_NS(sCell);
	var eCellRoad = getRoad_NS(eCell);
	for(var i=0;i<sCellRoad.length;i++)
		for(var j=0;j<eCellRoad.length;j++)
			if(sCellRoad[i] == eCellRoad[j])
			{
				edge[edgeInd] = sCellRoad[i];
				edgeInd++;
				break;
			}
	for(var ii=0;ii<edge.length;ii++)
		for(var jj = bridgeStart;jj<bridgeL;jj++)
		{
			if(aCell[jj+cols*edge[ii]].stat > 0 && !(jj == sCell.x && edge[ii] == sCell.y) && !(jj == eCell.x && edge[ii] == eCell.y))
			{
				break;
			}
			if(jj == bridgeL -1)
			return edge[ii];
		}
	return false;
}
function getBridgeY(sCell,eCell)
{
	var bridgeStart = Math.min(sCell.y,eCell.y)+1;
	var edge = new Array();
	var bridgeL = Math.abs(sCell.y - eCell.y) + bridgeStart;
	var edgeInd = 0;
	
	var sCellRoad = getRoad_WE(sCell);
	var eCellRoad = getRoad_WE(eCell);
	for(var i=0;i<sCellRoad.length;i++)
		for(var j=0;j<eCellRoad.length;j++)
			if(sCellRoad[i] == eCellRoad[j])
			{
				edge[edgeInd] = sCellRoad[i];
				edgeInd++;
				break;
			}
	for(var ii=0;ii<edge.length;ii++)
		for(var jj = bridgeStart;jj<bridgeL;jj++)
		{
			if(aCell[edge[ii]+cols*jj].stat > 0 && !(jj == sCell.y && edge[ii] == sCell.x) && !(jj == eCell.y && edge[ii] == eCell.x))
			{
				break;
			}
			if(jj == bridgeL -1)
			return edge[ii];
		}
	return false;
}
function makePath(sCell,eCell)//查找并反回路径数组，不存在路径则反回false
{
	var path = new Array();
	var inc1,inc2,inc3;
	var Ind = 0;
	
	var bridge = null;
	
	if(getBridgeX(sCell,eCell) !== false)
	{
		bridge = getBridgeX(sCell,eCell);
		var startLength = Math.abs(bridge - sCell.y);
		var endLength = Math.abs(eCell.y - bridge);
		var bridgeLength = Math.abs(eCell.x - sCell.x) + 1;
		if(sCell.y != bridge)
			inc1 = (bridge - sCell.y)/startLength;
		else
			inc1 = 0;
		inc2 = (eCell.x - sCell.x)/Math.abs(eCell.x - sCell.x);
		if(eCell.y != bridge)
			inc3 = (eCell.y - bridge)/endLength;
		else
			inc3 = 0;
		for(var i = 1;i < startLength;i++)
		{
			path[Ind] = aCell[sCell.x + (sCell.y + i * inc1) * cols];
			Ind++;
		}
		for(var j = 0;j < bridgeLength;j++)
		{
			if(!(j == 0 && bridge == sCell.y) && !(j == bridgeLength - 1 && bridge == eCell.y))
			{
			path[Ind] = aCell[sCell.x + (j * inc2) + bridge * cols];
			Ind++;
			}
		}
		for(var k = 1;k < endLength;k++)
		{
			path[Ind] = aCell[eCell.x + (bridge + k * inc3) * cols];
			Ind++;
		}
		return path;
	}
	else if (getBridgeY(sCell,eCell) !== false)
		 {
	 	bridge = getBridgeY(sCell,eCell);
	 	var startLength = Math.abs(bridge - sCell.x);
		var endLength = Math.abs(eCell.x - bridge);
		var bridgeLength = Math.abs(eCell.y - sCell.y) + 1;
		if(sCell.x != bridge)
			inc1 = (bridge - sCell.x)/startLength;
		else
			inc1 = 0;
		inc2 = (eCell.y - sCell.y)/Math.abs(eCell.y - sCell.y);
		if(eCell.x != bridge)
			inc3 = (eCell.x - bridge)/endLength;
		else
			inc3 = 0;
		for(var i = 1;i < startLength;i++)
		{
			path[Ind] = aCell[sCell.y * cols + (sCell.x + i * inc1)];
			Ind++;
		}
		for(var j = 0;j < bridgeLength;j++)
		{
			if(!(j == 0 && bridge == sCell.x) && !(j == bridgeLength - 1 && bridge == eCell.x))
			{
			path[Ind] = aCell[(sCell.y  + j * inc2)* cols + bridge];
			Ind++;
			}
		}
		for(var k = 1;k < endLength;k++)
		{
			path[Ind] = aCell[eCell.y * cols + (bridge + k * inc3)];
			Ind++;
		}
		return path;;
	 	}
		 else
			return false;
}
//////////////////////////////////////////
function matchCell()
{
	var cell1;
	if(startCell == null)
	{
		cell1 = cols + 1;
	}
	else
	{
		cell1 = startCell.index;
	}
	for(var i = cell1;i < (cols * rows - cols) - 1;i++)
	{
		if(aCell[i].stat > 0)
		{
			for(var j = i + 1;j < (cols * rows - cols) - 1;j++)
			{
				if(aCell[j].stat == aCell[i].stat && makePath(aCell[j],aCell[i]))
				{//alert(aCell[j].stat+" == "+aCell[i].stat)
					return [i,j];
				}
			}
		}
	}
	return false;
}
function showMatchCell()
{//alert(matchCell())
	var cf1 = document.getElementById("cf1");
	var cf2 = document.getElementById("cf2");
	if(matchCell())
	{//alert(matchCell()[0])
		cf1.style.top  = document.getElementById("cell_" + matchCell()[0]).getBoundingClientRect().top + document.body.scrollTop - 6;
		cf1.style.left = document.getElementById("cell_" + matchCell()[0]).getBoundingClientRect().left + document.body.scrollLeft - 6;
		cf2.style.top  = document.getElementById("cell_" + matchCell()[1]).getBoundingClientRect().top + document.body.scrollTop - 6;
		cf2.style.left = document.getElementById("cell_" + matchCell()[1]).getBoundingClientRect().left + document.body.scrollLeft - 6;
		cf1.children[0].src = "img/" + theme + "/cf.gif";
		cf2.children[0].src = "img/" + theme + "/cf.gif";
		cf1.style.visibility = "visible";
		cf2.style.visibility = "visible";//alert(document.getElementById("cell_" + matchCell()[0]).getBoundingClientRect().top)
		if(cfHidding != null)
		{
			clearTimeout(cfHidding);
			cfHidding = null;
		}
		cfHidding = setTimeout("cf1.style.visibility = 'hidden';cf2.style.visibility = 'hidden';",2000);
	}
}
function autoPlay()
{
	if(matchCell())
	{
		showPath(aCell[matchCell()[0]],aCell[matchCell()[1]]);
		setTimeout("autoPlay()",1000);
	}
}
///////////////////////////////////
function showPath(sCell,eCell)
{
	uncellNum -= 2;
	if(uncellNum == 0)
	{
		showCover("done");
		clearInterval(countTimer);
		score = 0;
		level = 0;
		gameTime = 0;
	}
	aImgCell[(sCell.x - 1) + (sCell.y - 1) * (cols - 2)] = 0;
	aImgCell[(eCell.x - 1) + (eCell.y - 1) * (cols - 2)] = 0;
	sCell.stat = -1;
	eCell.stat = -1;
	PathQ.push(makePath(sCell,eCell));
	var currPath = PathQ.length-1;
	showScore((PathQ[currPath].length) * 10);
	PathQ[currPath].push(eCell);
	PathQ[currPath].unshift(sCell);
	PathQ[currPath].unshift(PathQ[PathQ.length-1].length-1);
	if(showingTimer == null)
	{
		showingTimer = setInterval("showing()",50);
	}
}
function showing()
{
	var prev_node;
	var next_node;
//	var path_str;//document.all("jjj").value=new Date().getTime();
	var comp =0;
	for(var i=0;i < PathQ.length;i++)
	{
		if(PathQ[i][0] > 1)
		{
			prev_node = PathQ[i][PathQ[i][0]-1];next_node = PathQ[i][PathQ[i][0]+1];
			path_str = "px" + (prev_node.x - PathQ[i][PathQ[i][0]].x) + "py" + (prev_node.y - PathQ[i][PathQ[i][0]].y) + "nx" + (next_node.x - PathQ[i][PathQ[i][0]].x) + "ny" + (next_node.y - PathQ[i][PathQ[i][0]].y);//alert(path_str);
			PathQ[i][PathQ[i][0]].setStat(path_str);//alert(PathQ[i][0])
			PathQ[i][0] --;
		}
		else
		{
			comp++;
			if(comp == PathQ.length)
			{
				clearInterval(showingTimer);
				showingTimer = null;
				for(pl=0;pl < PathQ.length;pl++)
				hidePath(pl);
				PathQ.length = 0;
			}
		}
	}
}
function hidePath(p)
{//alert(p)
	for(var i = 2;i < PathQ[p].length-1;i++)
		PathQ[p][i].setStat(0);
	PathQ[p][1].setStat(-1);
	PathQ[p][PathQ[p].length-1].setStat(-1);
}

function hideScore()
{
	var sco = document.getElementById("scorePan");
	sco.style.pixelTop -= 2;
	//sco.style.filter = "alpha(opacity=" + alpha + ")";//alert(alpha)
	//alpha -= 5;
	dist -= 1;
	//alert(dist)
	if(dist < 0)
	{
		sco.style.visibility = "hidden";
		clearInterval(scoTimer);
		dist = 20;
	}
}

function showScore(cur_score)
{
	var sco = document.getElementById("scorePan");
	var scColor = "#FFFFFF";
	sco.innerText = cur_score;
	if(event)
	{//alert(event.offsetX)
		sco.style.left = event.clientX - event.offsetX + document.body.scrollLeft - 2;
		sco.style.top = event.clientY - event.offsetY + document.body.scrollTop - 2;
	}
	else
	{
		sco.style.left = 100 + document.body.scrollLeft - 2;
		sco.style.top = 100 + document.body.scrollTop - 2;
	}
	if(typeof cur_score == "number")
	{
		switch(cur_score)
		{
			case 0: scColor = "#000000";break;
			case 10:scColor = "#9D0038";break;
			case 20:scColor = "#964A4A";break;
			case 30:scColor = "#1BA593";break;
			case 40:scColor = "#FFB93F";break;
			case 50:scColor = "#0000FF";break;
			case 60:scColor = "#A1A1A1";break;
			case 70:scColor = "#00A650";break;
			case 80:scColor = "#C69C6D";break;
			case 90:scColor = "#FFFFFF";break;
			case 100:scColor = "#C445EE";break;
			case 110:scColor = "#00FFFF";break;
			case 120:scColor = "#FF00FF";break;
			case 130:scColor = "#00AEEF";break;
			case 140:scColor = "#00FF00";break;
			case 150:scColor = "#FFFF00";break;
			default:scColor = "#FF0000"
		}
		sco.style.color = scColor;
		//sco.style.fontFamily = "Dayton";
		//sco.style.fontSize = "25px";
		score += cur_score;
		level = Math.max(Math.floor(score / 1000),0);//alert(Math.floor(score / 1000))
		document.getElementById("level").value = level;
		document.getElementById("tscore").value = score;
	}
	else
	{
		sco.style.fontFamily = "宋体";
		sco.style.color = "#ff0000";
		sco.style.fontSize = "16px";
		sco.style.fontWeight = "bold";
	}
	sco.style.visibility = "visible";
	dist = 20;
	alpha = 100;
	clearInterval(scoTimer);
	scoTimer = setInterval("hideScore()",80);
}
function connCell(cellIndex)
{
	//alert(aCell[cellIndex].y);
	if(aCell[cellIndex].stat > 0)
	{
		if(startCell == null)
		{
			startCell = aCell[cellIndex];
			hotcell(cellIndex);
			//startCell.Blink();          //选中时的闪烁效果
		}
		else
		{
			endCell = aCell[cellIndex];
			hotcell(startCell.x+startCell.y*cols);
			//clearInterval(blinkInter);  //结束闪烁
			//blinkStat = 0;
			//blinkCell(startCell.x+startCell.y*cols); //使闪烁后的背景复位
			if(startCell.stat == endCell.stat)
			{
				if(makePath(startCell,endCell) !== false)
				{//alert(makePath());
					showPath(startCell,endCell);
					
				}
				else
				{
					showScore(-10);
				}
			}
			else
			{
				showScore(-20);
			}
			startCell = null;
			endCell = null;
		}
	}
}
