/*-----------------------------------------------------------------------
	Copyrighted Andrew Stuart, 2005-2009, andrew@scanraid.com
	First version: 23 May 2005
	This version: 1.60, 20-JUN-2009
-----------------------------------------------------------------------*/
var stage=0,laststage=0,prevlaststage=0;
var showhints=true;
var steps=0;
var save_dstring='';
var some_changes=false;
var firsttime=true;
var some_saved=false;
var cordX;
var cordY;
var rcbname=["Row","Col"];
var abety="ABCDEFGHJ";
var abetx="123456789";
var editmode=true;
var MAX_STRAT = kdu6x6_list.length+7;
var coordmode=1;
var validkenken = false;

// Mask is a 2D array of ints which actually store bit arrays of numbers 1 to 6.
var mask=[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var g   =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var save=[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var orig=[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var last=[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var rcm =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var cid =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var map =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var ccl =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var opp =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var csz =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var dog =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var gnt =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var show =[[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0],[0,0,0,0,0,0]];
var which_box=[[0,0,0,1,1,1],[0,0,0,1,1,1],[2,2,2,3,3,3],[2,2,2,3,3,3],[4,4,4,5,5,5],[4,4,4,5,5,5]];
var offset=[0,0,0,0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,3,3,3,3,4,4,4];
var sq_bck=['#ccffcc','#ffffcc','#ccccff','#ffcccc','#ffccff'];
var sq_line=['#99dd99','#dddd99','#9999dd','#dd9999','#dd99dd'];
var propop = ["","","+","&times;","-","&divide;"];

var example = [
		["112212332314121334121221332311132322","2-,0,9x,0,5-,5,11+,0,0,12+,0,3+,12x,2/,11+,0,0,0,0,0,0,2/,0,120x,9+,0,2/,5-,0,0,6,0,0,0,5+,0"], //AndrewKenDokuSamples.July2nd0001.txt
		["121122121331212131212123331323221311","4-,2/,11+,0,3/,0,0,0,0,9x,0,5+,12x,3-,5-,2/,0,0,0,0,0,0,9+,3-,2/,0,15x,5-,0,0,2-,0,0,0,3-,0"], //AndrewKenDokuSamples.July2nd0002.txt
		["121121123321211341332242313342113113","11+,2/,1-,0,3-,8+,0,0,6x,0,0,0,3,7+,0,0,72x,0,4x,0,11+,0,0,3/,0,11+,40x,0,0,0,0,0,0,3/,0,5"], //AndrewKenDokuSamples.July2nd0003.txt
		["111211233233231311311323322123113111","15+,0,0,12x,2/,0,2/,4x,0,0,11+,0,0,0,12+,5-,8+,0,2/,0,0,0,5+,2-,0,5+,0,12+,0,0,15x,0,6,0,0,0"], //AndrewKenDokuSamples.July2nd0004.txt
		["112122332133344123123322121443331133","4-,0,2/,36x,12x,0,72x,0,0,0,25x,0,0,3+,0,0,48x,0,1-,11+,5-,0,0,0,0,0,13+,5+,0,36x,5+,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0005.txt
		["112121221121333212114212234121231121","3/,0,5,16x,3-,7+,3/,0,0,0,0,0,30x,0,0,11+,2/,3/,2-,0,5-,0,0,0,3-,15x,0,7+,4-,2-,0,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0006.txt
		["122112134432131232241211241331555322","15+,15x,0,2/,0,12x,0,5-,3/,0,10x,0,0,0,12x,4-,0,0,3/,3-,0,0,11+,0,0,0,0,72x,0,0,48x,0,0,0,4-,0"], //AndrewKenDokuSamples.July2nd0007.txt
		["112112132233331441123321321123332213","36x,0,16x,1-,0,1,0,40x,0,0,5+,0,0,0,3,5-,0,1-,5,3-,3/,0,8+,0,10+,0,3+,0,0,4-,0,0,2-,0,4,0"], //AndrewKenDokuSamples.July2nd0008.txt
		["121221121341212342213132123132123211","2-,3+,24x,3/,0,2/,0,0,0,5-,1-,0,5-,9+,2,0,0,90x,0,0,15x,1-,1-,0,2-,2/,0,0,0,0,0,0,0,2,5-,0"], //AndrewKenDokuSamples.July2nd0009.txt
		["112211221123213323212212133412223441","2-,0,2/,0,15x,0,300x,0,3/,0,5-,3-,0,3+,2-,0,0,0,0,0,2/,0,2/,4-,1,60x,0,8+,0,0,3/,0,0,0,0,5"], //AndrewKenDokuSamples.July2nd0010.txt
		["122121131321211312244432112233133311","3+,1-,0,3,24x,7+,0,6,8+,5-,0,0,11+,0,0,0,2,3/,0,9+,0,0,14+,0,24x,0,6+,0,0,0,0,13+,0,0,3-,0"], //AndrewKenDokuSamples.July2nd0011.txt
		["121211121233333123221121233231114231","7+,2-,2-,9+,1-,0,0,0,0,0,6x,0,48x,0,0,30x,11+,0,3x,0,0,0,0,12+,0,7+,0,5-,2/,0,2/,0,4,0,0,0"], //AndrewKenDokuSamples.July2nd0012.txt
		["111221233441223142144132125533221122","7+,0,0,1-,0,1-,60x,180x,0,4x,0,0,0,0,0,2/,0,4-,2/,3/,0,0,15+,0,0,13+,12x,0,0,0,0,0,5+,0,1-,0"], //AndrewKenDokuSamples.July2nd0013.txt
		["122122112132223131213241311242322112","90x,7+,0,15+,15x,0,0,0,0,0,2/,0,40x,0,2/,0,0,2-,0,8+,0,2/,2/,0,1-,0,0,0,0,3-,0,11+,0,1-,0,0"], //AndrewKenDokuSamples.July2nd0014.txt
		["122122233112212321212121132131144433","4,3/,0,9+,60x,0,10+,4-,0,0,0,0,0,3-,72x,3,1-,6+,0,0,0,30x,0,0,7+,4,0,0,12x,0,0,8+,0,0,0,0"], //AndrewKenDokuSamples.July2nd0015.txt
		["112122232133232441213311311223444213","11+,0,24x,5-,1-,0,10x,3/,0,0,3-,0,0,0,0,2/,0,10+,0,11+,11+,0,0,0,4,0,0,13+,0,4-,10+,0,0,0,2,0"], //AndrewKenDokuSamples.July2nd0016.txt
		["111221222311131332121142323311331122","10+,0,0,1-,0,15+,36x,0,0,5x,0,0,1-,4,36x,0,0,2/,0,10x,0,0,3,0,11+,0,20x,0,2/,0,0,0,1-,0,6+,0"], //AndrewKenDokuSamples.July2nd0017.txt
		["121112122342331322211441223311113322","4-,13+,6+,0,0,15+,0,0,0,3/,5,0,5-,0,10+,0,0,0,40x,0,0,2/,0,3x,0,0,16+,0,0,0,1-,0,0,0,3/,0"], //AndrewKenDokuSamples.July2nd0018.txt
		["121211121233133111221232331232222112","60x,3-,3-,4-,2-,0,0,0,0,0,1-,0,0,3/,0,11+,0,0,2/,0,3-,1-,5-,15x,2/,0,0,0,0,0,20x,0,0,4-,0,0"], //AndrewKenDokuSamples.July2nd0019.txt
		["122211134441233312212232312231344551","3-,20x,0,0,13+,0,0,17+,6x,0,0,0,5+,0,0,0,1,1-,0,5-,15+,0,3-,0,10x,0,0,0,0,7+,0,2/,0,2-,0,0"], //AndrewKenDokuSamples.July2nd0020.txt
		["122112134433231211221233133211112331","4-,2/,0,2-,0,6,0,1-,5-,0,2/,0,60x,0,3/,24x,2-,0,0,0,0,0,5-,0,8+,3/,0,0,20x,0,0,0,5,3/,0,0"], //AndrewKenDokuSamples.July2nd0021.txt
		["121112123342211241331221132121112333","2-,2/,36x,0,0,4-,0,0,2-,0,10+,0,5,10+,0,10x,0,24x,48x,0,0,0,0,0,9+,0,2/,5,0,0,0,0,0,13+,0,0"], //AndrewKenDokuSamples.July2nd0022.txt
		["122122131133233222221332144411111221","1-,3/,0,12+,2/,0,0,4x,0,0,5-,0,60x,0,0,16+,0,0,0,0,6,3-,0,0,10+,120x,0,0,18x,0,0,0,0,3-,0,0"], //AndrewKenDokuSamples.July2nd0023.txt
		["112212233112231221441331222122331122","2-,0,2-,0,9+,5-,3-,9+,0,0,0,0,0,0,4-,5-,0,7+,2/,0,0,10x,0,0,9+,0,0,16x,16+,0,15x,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0024.txt
		["122111113322221212211233233113112244","9+,24x,0,10+,0,0,0,0,3/,0,4x,0,14+,0,15x,1-,6,0,0,0,0,0,10+,0,0,5-,0,1-,0,0,12x,0,6+,0,3/,0"], //AndrewKenDokuSamples.July2nd0025.txt
		["121122122313331313221121233421112441","2-,12+,5-,0,9+,0,0,0,0,15x,5-,2/,1-,0,20x,0,0,0,6x,0,0,0,2-,90x,0,2-,0,12x,0,0,2/,0,6,0,0,0"], //AndrewKenDokuSamples.July2nd0026.txt
		["122311133311244442241122112321444331","8+,3/,0,14+,40x,0,0,0,0,0,0,0,5-,160x,0,0,0,14+,0,0,15x,0,0,0,3/,0,1,12+,0,4-,60x,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0027.txt
		["121123122113213322212131332131111222","5+,13+,180x,0,2,5-,0,0,0,0,0,0,1-,5+,2-,0,3/,0,0,0,5-,3+,8+,1-,2/,0,0,0,0,0,9+,0,0,12+,0,0"], //AndrewKenDokuSamples.July2nd0028.txt
		["112122232133231231441244112122332112","2/,0,1-,6x,1-,0,2/,2-,0,0,12+,0,0,0,2-,2-,0,3,20x,0,0,0,2/,0,5-,0,2/,10x,72x,0,8+,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0029.txt
		["122211113123223123132212131122223311","36x,10+,0,0,3/,0,0,0,3+,11+,2-,3-,1-,0,0,0,0,0,6+,5-,2-,0,2,60x,0,0,1-,0,0,0,2/,0,2-,0,5-,0"], //AndrewKenDokuSamples.July2nd0030.txt
		["111221233441123422122113334433114111","12x,0,0,2-,0,5+,5,10+,0,12+,0,0,4-,10+,0,0,3-,0,0,0,0,5-,0,14+,2/,0,10+,0,0,0,8+,0,0,7+,0,0"], //AndrewKenDokuSamples.July2nd0031.txt
		["112221121341221344112214233412211412","10+,0,20x,0,0,3/,0,50x,1-,10+,15+,0,0,0,0,0,0,0,2-,0,3/,0,13+,0,2/,5-,0,1-,0,3-,0,2-,0,0,0,0"], //AndrewKenDokuSamples.July2nd0032.txt
		["112212223312144221122331331122312211","1-,0,3/,0,7+,24x,1-,0,7+,0,0,0,5-,15x,0,2-,0,4-,0,2/,0,2/,0,0,60x,0,1-,0,1-,0,0,1,1-,0,2/,0"], //AndrewKenDokuSamples.July2nd0033.txt
		["121221123311331123113323122312444412","3/,2/,6,1-,0,20x,0,0,1-,0,0,0,1-,0,3+,0,2-,24x,10+,0,16x,0,0,0,0,3/,0,0,5-,1-,13+,0,0,0,0,0"], //AndrewKenDokuSamples.July2nd0034.txt
		["112211233231121132123232233213211313","3-,0,48x,0,9+,0,2,2-,0,0,12+,0,2/,3-,3/,0,0,2/,0,0,12+,1-,0,0,4-,0,0,0,2/,2/,0,1-,0,1,0,0"], //AndrewKenDokuSamples.July2nd0035.txt
		["112212233412231433441213113213223444","2/,0,12x,0,5-,1-,1-,14+,0,2/,0,0,0,0,5-,0,108x,0,1-,0,0,1-,2-,0,5+,0,3-,0,0,0,2/,0,0,10+,0,0"], //AndrewKenDokuSamples.July2nd0036.txt
		["121112132212231331211241332242113322","11+,3,120x,0,0,3-,0,2-,5-,0,0,0,3/,0,60x,5-,0,2-,0,0,0,24x,1-,0,2/,0,0,0,0,12x,1-,0,2/,0,0,0"], //AndrewKenDokuSamples.July2nd0037.txt
		["112211221122112332332331121221121332","1-,0,2/,0,3-,0,1-,0,1-,0,16x,0,11+,0,1-,12+,0,0,3+,0,0,0,0,2-,1-,6x,3-,1-,0,0,0,0,0,3-,0,2"], //AndrewKenDokuSamples.July2nd0038.txt
		["121122122333332132211112334442112242","2/,10x,1-,0,5-,0,0,0,0,15+,0,0,2-,0,0,240x,0,60x,2,0,0,0,0,0,1-,0,14+,0,0,0,5-,0,2/,0,0,0"], //AndrewKenDokuSamples.July2nd0039.txt
		["122112133344122244331233221331211221","30x,2/,0,2-,0,6,0,10+,0,0,15+,0,0,7+,0,0,0,0,1-,0,16+,0,15+,0,11+,0,0,0,0,2-,0,0,0,3-,0,0"], //AndrewKenDokuSamples.July2nd0040.txt
	];

//var g2 = ["121122123332321144331124144421113321","4+,7+,8+,,11+,,,,13+,,,,15+,,10+,,14+,,,,,,7+,,13+,10+,,,,5+,,,9+,,,,"]; // killer

var block1;
var sq_col=['black','#CC0000','blue','blue'];
var sq_siz=['10pt','22pt','22pt','22pt','8pt','18pt','18pt','18pt'];
var cur_id = 1;

jig=-3; /* KenKodu */

/*---------------------------------------------------------------------*/
/* Draws the content of a square on the board							*/
/*---------------------------------------------------------------------*/
function set_square( x, y, val, setup )
{
	var t, s;

	// Get the table cell name out using the coordinates
	t=document.getElementById("a"+y+x);
	if( t.style.backgroundColor != sq_bck[map[y][x]-1] )
		t.style.backgroundColor = sq_bck[map[y][x]-1];

	if( (setup===0 && showhints) || setup > 0 )
		 t.innerHTML=val;	// Assign the new value to the cell
	else t.innerHTML='&nbsp;';	// Assign the new value to the cell
	t.style.color=sq_col[setup];
	t.style.fontSize=sq_siz[setup];
	if( setup == 3 ) t.style.backgroundColor = '#ff0000';
}
/*----------------------------------------------------------------------*/
/* Converts the bit array to a string of numbers for display			*/
/*----------------------------------------------------------------------*/
function lable_square( y, x, deduct )
{
	var lable, c, i, modfact=3;
	lable='';
	c=0;
	if( (mask[y][x] & deduct) != deduct ) alert(mask[y][x] + " != " + deduct);
	mask[y][x] -= deduct;
	show[y][x] += deduct;

	for( i=0;i<6;i++ )
	{
		if( mask[y][x] & (1 << i) )	// i=0 to 8 so first shift is 0 bits
		{
			if( show[y][x] & (1 << i) )
				lable=lable + "<span class=\"fsh\">" + (i+1) + "</span>";
			else
				lable=lable + (i+1);
		}
		else
		{
			if( show[y][x] & (1 << i) )
				lable=lable + "<span class=\"fsh\">" + (i+1) + "</span>";
			else lable=lable + '&nbsp;&nbsp;';
		}
		if( (i % modfact) == 2 )
			lable=lable + "<br>";
		else lable=lable + "&nbsp;";
	}
	some_changes=true;
	set_square(x,y,lable,0);
}

function find_cage_size(y,x,target_col)
{
	var c=0;
	if( x<0 || x>5 || y<0 || y>5 ) return 0;
	if( map[y][x] != target_col ) return 0;
	if( csz[y][x] != 0 ) return 0;
	csz[y][x] = -1;
	cid[y][x] = cur_id;
	c++;
	c+=find_cage_size(y,x-1,target_col);
	c+=find_cage_size(y,x+1,target_col);
	c+=find_cage_size(y-1,x,target_col);
	c+=find_cage_size(y+1,x,target_col);
	return c;
}
function set_cage_size(y,x,target_col,s)
{
	if( x<0 || x>5 || y<0 || y>5 ) return 0;
	if( map[y][x] != target_col ) return 0;
	if( csz[y][x] != -1 ) return 0;
	csz[y][x] = s;
	set_cage_size(y,x-1,target_col,s);
	set_cage_size(y,x+1,target_col,s);
	set_cage_size(y-1,x,target_col,s);
	set_cage_size(y+1,x,target_col,s);
}
function compute_doglegs()
{
	var y,x,i,j,s,n=0,isdog=0;;
	cordX=new Array(36);
	cordY=new Array(36);

	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
			if( cid[y][x] == cur_id )
			{
				cordX[n] = x;
				cordY[n] = y;
				n++;
			}

	for(i=0;i<n-1;i++)
		for(j=i+1;j<n;j++)
		{
			if( cordX[i]!=cordX[j] && cordY[i]!=cordY[j] && which_box[cordY[i]][cordX[i]]!=which_box[cordY[j]][cordX[j]] )
				isdog++;
		}
	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
			if( cid[y][x] == cur_id )
				dog[y][x] = isdog;
}
function compute_cage_sizes()
{
	var i,j,s;
	cur_id = 1;
	for(j=0;j<6;j++)
		for(i=0;i<6;i++)
			if( csz[j][i]==0 ) {
				s = find_cage_size(j,i,map[j][i]);
				set_cage_size(j,i,map[j][i],s);
				compute_doglegs();
				cur_id++;
			}
}
var recc = new Array(36);

function str2map( s )
{
	var x,y,c;
	for(y=0;y<6;y++) for(x=0;x<6;x++) {
		c = s.substr((y*6)+x,1);
		map[y][x]=c*1;
	}
}
/*function str2ccl( s )
{
	var x,y,c;
	for(y=0;y<6;y++) for(x=0;x<6;x++) {
		c = s.substr(((y*6)+x)*2,2)
		ccl[y][x]=c*1;
		opp[y][x]='+';s
	}
}*/

function str2ccl( s )
{
	var x,y,c,v,vl;
	var arr = s.split(',');
	if( arr.length==1 ) return;
	for(y=0;y<6;y++) for(x=0;x<6;x++)
	{
		v = arr[y*6+x];
		if( v.length==0 ) {
			ccl[y][x] = 0;
			opp[y][x] = '';
		}
		else
		{
			vl = v.charAt(v.length-1);
			if( vl == '+' || vl == '-' || vl == 'x' || vl == '/' ) {
				c = v.substr(0,v.length-1);
				ccl[y][x]=c*1;
				opp[y][x]=vl;
			}
			else
			{
				ccl[y][x]=v*1;
				opp[y][x]='+';
			}
		}
	}
}
function comb(t) {
	var y = t.id.charAt(1);
	var x = t.id.charAt(2);
	var s = '',tmp;
	var dogleg = 1;
	if( t.innerHTML == '' ) return;
	if( csz[y][x]==1 ) {
		s = 'Single Cage';
	}
	else
	{
		switch( opp[y][x] ) {
		case 'x' : operator = 3; break;
		case '-' : operator = 4; break;
		case '/' : operator = 5; break;
		default  : operator = 2; break;
		}
		switch( dog[y][x] ) {
		case 0 :
			for(var i=0;i<combinations_1box.length;i++)
				if( combinations_1box[i][0] == csz[y][x]
				 && combinations_1box[i][operator] == ccl[y][x] ) {
					if( s!='' ) s+='<br>';
					{
						tmp = combinations_1box[i][1];
						if( operator==5 ) tmp = tmp.charAt(2) + '&divide;' + tmp.charAt(0);
						s += tmp;
					}
				}
			if( operator!=5 ) s = s.replace(/-/g,propop[operator]);
			break;
		case 1 :
			for(var i=0;i<combinations_2box.length;i++)
				if( combinations_2box[i][0] == csz[y][x]
				 && combinations_2box[i][operator] == ccl[y][x] ) {
					if( s!='' ) s+='<br>';
					 s += combinations_2box[i][1];
				}
			s = s.replace(/-/g,propop[operator]);
			dogleg = 2;
			break;
		case 2 :
		case 3 :
			for(var i=0;i<combinations_3box.length;i++)
				if( combinations_3box[i][0] == csz[y][x]
				 && combinations_3box[i][operator] == ccl[y][x] ) {
					if( s!='' ) s+='<br>';
					 s += combinations_3box[i][1];
				}
			s = s.replace(/-/g,propop[operator]);
			dogleg = 2;
			break;
		}
		if( s=='' ) s = 'Combination cannot be<br>tool-tipped at this time ';
	}
	tooltip.show(s,dogleg);
}
function load_from_fields()
{
	var i,j,t;
	var frm = document.forms.servsolv;

	prevlaststage=laststage=stage=0;

	for(j=0;j<6;j++)
		for(i=0;i<6;i++)
		{
			g[j][i]=csz[j][i]=show[j][i]=cid[j][i]=last[j][i]=map[j][i]=ccl[j][i]=dog[j][i]=gnt[j][i] = 0;
			orig[j][i]=mask[j][i]=63;
		}

	str2ccl(frm.elements['cluemap'].value);
	str2map(frm.elements['colmap'].value);

	cordX=new Array(36);
	cordY=new Array(36);

	compute_cage_sizes();

	for(j=0;j<6;j++)
		for(i=0;i<6;i++)
		{
			if( csz[j][i]==1 ) { g[j][i] = ccl[j][i]; mask[j][i]=0; }
			if( g[j][i] > 0 )
				set_square(i,j,g[j][i],1);
			else
			{
				lable_square( j,i,0 );
			}
			t = document.getElementById("K"+ j + i);
			t.innerHTML=( ccl[j][i]>0 ) ? ccl[j][i]+((opp[j][i]=='/')?'&divide;':opp[j][i]) : '';
			t.style.backgroundColor = sq_bck[map[j][i]-1];

		}
	for(j=0;j<6;j++)
		for(i=0;i<5;i++)
		{
			t = document.getElementById("CR"+ j + i);
			t.style.backgroundColor = ( map[j][i]==map[j][i+1] ) ? sq_line[map[j][i]-1] : '#000000';
		}
	for(j=0;j<5;j++)
		for(i=0;i<6;i++)
		{
			t = document.getElementById("CB"+ j + i);
			t.style.backgroundColor = ( map[j][i]==map[j+1][i] ) ? sq_line[map[j][i]-1] : '#000000';
		}

	reset_yes_no( kdu6x6_list,5 );
	document.getElementById("takestep").onclick=take_step;
	document.getElementById("takestep").className = 'SButton';
/*	if( readCookie('scanraidkenken6x6cookie') )
	{
		document.getElementById("reload").className="SButton";
		some_saved=true;
	} */
	some_changes=false;
	firsttime=false;
}
function load_board()
{
	var colmap='', cluemap='';
	w = document.forms.DataEntry.elements["Example"].selectedIndex;
	if( w<0 ) return;
	cluemap = example[w][1];
	colmap = example[w][0];
	if( colmap=='' ) return;
	frm = document.forms.servsolv;
	frm.elements['colmap'].value = colmap;
	frm.elements['cluemap'].value = cluemap;
	load_from_fields();

	if( !document.ifrm )
		 doc = document.getElementById("ifrm").contentDocument;
	else doc = document.ifrm.document;
	doc.body.innerHTML='Results go here';

}
function load_print_board()
{
	var x,y,cage;
	var styleline,b='',internal='';
	var isSol = false;
	var inColour = (location.search=='?p=1');

	for(y=0;y<6;y++) for(x=0;x<6;x++) csz[y][x]=ccl[y][x]=rcm[y][x]=map[y][x]=0;

	if( opener === null
	 || opener.document === null
	 || opener.document.getElementById('servsolv') === null ) {
		alert('Cannot find the parent document - the KenKen Solve page');
		return;
	}
	frm = opener.document.getElementById('servsolv');

	str2map(frm.elements['colmap'].value);
	str2ccl(frm.elements['cluemap'].value);

	document.getElementById("colmap").value = frm.elements['colmap'].value;
	document.getElementById("cluemap").value = frm.elements['cluemap'].value;


	for(y=0;y<6;y++)
	{
		b = b + "<tr>\n";
		for(x=0;x<6;x++)
		{
			styleline = '';


			if( inColour ) styleline = styleline + "background-color:" + sq_bck[map[y][x]-1] + ";";

			cage = 0;
			if( x == 0 )
			{	styleline = styleline + "border-left: 6px solid #000000;"; cage++; }
			else if( map[y][x] != map[y][x-1] )
			{	styleline = styleline + "border-left: 3px solid #000000;"; cage++; }

			if( x == 5 )
			{	styleline = styleline + "border-right: 6px solid #000000;"; cage++; }
			else if( map[y][x] != map[y][x+1] )
			{	styleline = styleline + "border-right: 3px solid #000000;"; cage++; }

			if( y == 0 )
			{	styleline = styleline + "border-top: 6px solid #000000;"; cage++; }
			else if( map[y][x] != map[y-1][x] )
			{	styleline = styleline + "border-top: 3px solid #000000;"; cage++; }

			if( y == 5 )
			{	styleline = styleline + "border-bottom: 6px solid #000000;"; cage++; }
			else if( map[y][x] != map[y+1][x] )
			{	styleline = styleline + "border-bottom: 3px solid #000000;"; cage++; }


			internal = "\n<table border=0 width=100% height=100%><tr><td style=\""
			if( isSol || cage==4 )
				internal = internal + "\" class=\"InnerSol\"";
			else
				internal = internal + "\" class=\"InnerK\"";


			if( isSol )
				internal = internal + ">" & g[y][x] & "</td></tr></table>\n";
			else
			{
				if( ccl[y][x] == 0 )
					internal = internal + ">&nbsp</td></tr></table>\n";
				else if( cage==4 )
					internal = internal + ">" + ccl[y][x] + "</td></tr></table>\n";
				else
				{
					o = opp[y][x];
					if( o=='x' ) o = "&times;"
					if( o=='/' ) o = "&divide;"
					internal = internal + ">" + ccl[y][x] + o + "</td></tr></table>\n";
				}
			}
			b += "<td class=\"InnerTDone\" style=\"" + styleline + "\">" + internal + "</td>\n";
			if( x==2 ) b += '<td style="width:3px;background-color:#dddddd;border-right:solid 1px black"><img src="images/s.gif"></td>';
		}
		b = b + "</tr>\n";
		if( y==1 || y==3 ) b += '<tr><td colspan=7 style="height:3px;background-color:#dddddd;border-top:solid 1px black"><img src="images/s.gif"></tr>';
	}
	document.getElementById("boardgoeshere").innerHTML = "<table border=0 cellpadding=0 cellspacing=0>" + b + "</table>";
}
function fill_transfer_vars(cur_strat)
{
	var x,y,s='',st='',frm;
	var cluemap='',colmap='';

	for(y=0;y<6;y++)		// Redraw the board to clear any user highlighting
		for(x=0;x<6;x++)
		{
			if( ccl[y][x]>0 ) cluemap += ccl[y][x]+opp[y][x];
			cluemap += ',';
		//	cluemap = cluemap + padzero(ccl[y][x]);
			colmap = colmap + map[y][x];
			if( g[y][x] )
				 s = s + ',' + (1 << (g[y][x]-1));
			else s = s + ',' + mask[y][x];
		}
	for( x=5;x<kdu6x6_list.length;x++) if( document.getElementById("CB"+kdu6x6_list[x]).checked===false )
	{
		st+=kil_list[x];
	}

	frm = document.forms.servsolv;
	frm.elements['coordmode'].value = coordmode;
	frm.elements['strat'].value = cur_strat;
	frm.elements['stratmask'].value = st;
	frm.elements['colmap'].value = colmap;
	frm.elements['cluemap'].value = cluemap;
	frm.elements['board'].value = s.substr(1,s.length-1);
}
function import_kendoku(isNew)
{
	var dstring;
	var actualstr='';
	var c,i,j,s,t;

	if( isNew ) fill_transfer_vars(0);


	var SGW=window.open('KenDoku6x6Designer.htm?n=' + isNew,'_designer','resizable=no,scrollbars=no,screenX=200,screenY=200,width=710,height=490');
	if (!SGW.opener) SGW.opener=self;
}
function save_board()
{
	fill_transfer_vars(0);

	document.getElementById("reload").className="SButton";
	some_saved=true;

	var date = new Date();
	date.setTime(date.getTime()+(30*24*60*60*1000));

	var frm = document.forms.servsolv;

	document.cookie ='scanraidkenken6x6cookiea=' + frm.elements['colmap'].value + '; expires=' + date.toGMTString() + '; path=/';
	document.cookie ='scanraidkenken6x6cookieb=' + frm.elements['cluemap'].value + '; expires=' + date.toGMTString() + '; path=/';
	document.cookie ='scanraidkenken6x6cookiec=' + frm.elements['board'].value + '; expires=' + date.toGMTString() + '; path=/';

	alert("Current Board Saved (as a cookie)");
}
function reload_board()
{
	var x = readCookie('scanraidkenken6x6cookiea');
	if (x)
	{
		var frm = document.forms.servsolv;
		frm.elements['colmap'].value = x;
		frm.elements['cluemap'].value = readCookie('scanraidkenken6x6cookieb');
		frm.elements['board'].value = readCookie('scanraidkenken6x6cookiec');
		load_from_fields();
	}
	else
	{
		alert("No saved board found");
	}
}
function check_for_single()
{
	var i,x,y,done=0;
	for( y=0;y<6;y++ )
		for( x=0;x<6;x++ )	// for every square on the board
		{
			for(i=0;i<6;i++)	// if the bit array contains only one bit
				if( mask[y][x] == (1 << i) )
				{
					g[y][x]=i+1;		// we have a single number and a solution
					mask[y][x]=0;		// ...wipe the mask
					set_square(x,y,g[y][x],2);	// and draw the number
					done++;
			//		some_changes=true;
				}
		}
	return done;
}
function check_for_one_single( y,x )
{
	var n;
	for(n=0;n<6;n++)
		if( mask[y][x] == (1 << n) )
		{
			g[y][x]=n+1;		// we have a single number and a solution
			mask[y][x]=0;		// ...wipe the mask
			set_square(x,y,g[y][x],2);	// and draw the number
			some_changes=true;
			return true;
		}
	return false;
}

function show_candidates()
{
	var changes;
	var x,y,i,a,b,j,zz,yy,n;

	/*----------------------------------------------------------------------*/
	/* check the rows and columns of each square							*/
	/* and to remove any bits for numbers that are found. Ie,we start with	*/
	/* 123456 and zero any numbers in the array in each row/column		*/
	/*----------------------------------------------------------------------*/
	for( y=0;y<6;y++ )
		for( x=0;x<6;x++ )	// for every square on the board
			if( !g[y][x] )	// if it is an unknown square...
			{
				changes=false;
				for( i=0;i<6;i++) // for the size of the board
				{
					if( i != x && g[y][i] > 0 ) // check values in row
						if( (mask[y][x] & (1 << (g[y][i]-1))) )
						{
							mask[y][x] -= (1 << (g[y][i]-1));	// remove that bit
							changes=true;
						}
					if( i != y && g[i][x] > 0 ) // check values in column
						if( (mask[y][x] & (1 << (g[i][x]-1))) )
						{
							mask[y][x] -= (1 << (g[i][x]-1));	// remove that bit
							changes=true;
						}
				}
				if( changes ) lable_square( y,x,0 );
			}

	/*----------------------------------------------------------------------*/
	/* check number in each box - which MUST 								*/
	/* contain only 1 to 6. If we have known numbers then they must be		*/
	/* removed from the choices in the bit array found in test_row_col		*/
	/*----------------------------------------------------------------------*/
	for(a=0;a<6;a+=2)		// for each box (6 of them 3 by 3 each)
		for(b=0;b<6;b+=3)
			for(i=a;i<a+2;i++)		// which means looking in each 3 by 3 box
				for(j=b;j<b+3;j++)
					if( g[i][j]>0 )
						for(zz=a;zz<a+2;zz++)	// ..check every other cell
							for(yy=b;yy<b+3;yy++)
							{
								n=g[i][j]-1;
								if( mask[zz][yy] & (1 << n) )
								{
									mask[zz][yy] -= (1 << n);
									lable_square( zz,yy,0);
								}
							}

}
function singles_in_row_col( )
{
	var y,x,n,cr,cc,k;

	for(y=0;y<6;y++)
		for(x=0;x<6;x++)	// for every square on the board...
			if( !g[y][x] )	// if it is an unknown square...
			{
				for(n=0;n<6 && !g[y][x];n++) if( mask[y][x] & (1 << n) ) // For all numbers,if the number is a possible
				{
					for( cc=cr=k=0;k<6;k++)
					{
						if( !g[y][k] && (mask[y][k] & (1 << n)) ) cr++;  // check the row
						if( !g[k][x] && (mask[k][x] & (1 << n)) ) cc++;  // check the column
					}
					if( cr==1 || cc==1 )
					{
						if( cr==1 ) strat_add("SINGLE: " + cordit(y,x) + " set to " + abetx.charAt(n) + ", unique in Row<br>");
						if( cc==1 ) strat_add("SINGLE: " + cordit(y,x) + " set to " + abetx.charAt(n) + ", unique in Column<br>");
						show[y][x]=(1 << n);
						lable_square(y,x,0);
						mask[y][x]=(1 << n);
					}
				}
			}
}
function singles_in_box( )
{
	var ax=new Array(12);
	var ay=new Array(12);
	var bb,cc,n,c,i,j;

	/*----------------------------------------------------------------------*/
	/* Point of check_box is that now we have a whole board set up with	*/
	/* a bit array for each square. Lets check that bit array in each		*/
	/* box to see if any of the nine squares have numbers which only occur	*/
	/* once. If so we have a NEW solution for that square.					*/
	/*----------------------------------------------------------------------*/

	for(bb=0;bb<6;bb+=2)		// Once more, for each box (6 of them 3 by 2 each)
		for(cc=0;cc<6;cc+=3)
			for(n=0;n<6;n++)	// .. check each number
			{
				c=0;
				for(i=bb;i<bb+2 && c<6;i++)	// which means looking in each 3 by 3 box
					for(j=cc;j<cc+3 && c<6;j++)
					{
						if( g[i][j]===0 && (mask[i][j] & (1 << n)) )
						{
							ax[c]=j;	// Store the coordinates
							ay[c++]=i; // and count how many times this happens
						}
						else if( g[i][j]==n+1 ) c=6;	// if that number is known we can ignore it
					}
				if( c == 1 )	// If we only have one occurance...
				{
					strat_add("SINGLE: " + cordit(ay[0],ax[0]) + " set to " + abetx.charAt(n) + ", unique in Box<br>");
					show[ay[0]][ax[0]]=(1 << n);
					lable_square(ay[0],ax[0],0);
					mask[ay[0]][ax[0]]=(1 << n);
					some_changes=true;
				}
			}
}



/*-------------------------------------------------------------------------*/
/* Purpose of hidden_pairs is to look for pairs of numbers, eg 3-7 and 3-7 */
/* mixed up in the same two squares with other numbers - which can be      */
/* eliminated. 															   */
/*-------------------------------------------------------------------------*/
var gotsome;
function apply_new_mask( desc,direction,unit,y,x,h )
{
	strat_add(desc + mask2str(h) + direction + abetx.charAt(unit) + ": " + cordit(y,x) + " - " + mask2str(mask[y][x]) + " -> " + mask2str(mask[y][x] & h) + "<br>");
	show[y][x] = mask[y][x] - (mask[y][x] & h);
	mask[y][x] &= h;
	lable_square( y,x,0 );
	gotsome = true;
}
function hidden_pairs()
{
	var x,y,n,m,i,bb,cc,box=0,h;
	var pos=new Array(6);

	for(bb=0;bb<6;bb+=2)		// Once more, for each box (6 of them 3 by 3 each)
		for(cc=0;cc<6;cc+=3)
		{
			for(n=0;n<6;n++)	// .. check each number
			{
				pos[n]=i=0;
				for(y=bb;y<bb+2;y++)	// which means looking in each 3 by 3 box
					for(x=cc;x<cc+3;x++,i++)
						if( !g[y][x] && (mask[y][x] & (1 << n)) )
							pos[n] += (1 << i);  // ith position of n
			}
			for(n=0;n<5;n++)
				for(m=n+1;m<6;m++)
					if( bit_count(pos[n])==2 && pos[n] == pos[m] )
					{
						i=0;
						for(y=bb;y<bb+2;y++)	// which means looking in each 3 by 3 box
							for(x=cc;x<cc+3;x++,i++)
								if( pos[n] & (1 << i) && bit_count(mask[y][x]) > 2 )
								{
									h=(1 << n) + (1 << m);
									apply_new_mask( "HIDDEN PAIR: ", " in box ", box,y,x,h );
								}
					}
			box++;
		}

	/*-------------------------------------------------------------------------*/
	/* Checking in the box will get most hidden pairs, but some are aligned    */
	/* over two box but still on the same row or columns				       */
	/*-------------------------------------------------------------------------*/
	for(y=0;y<6;y++)
	{
		for(n=0;n<6;n++)	// .. check each number
			for(pos[n]=x=0;x<6;x++)	// which means looking in each row/col
				if( !g[y][x] && (mask[y][x] & (1 << n)) )
					pos[n] += (1 << x);  // ith position of n

		for(n=0;n<5;n++)
			for(m=n+1;m<6;m++)
				if( bit_count(pos[n])==2 && pos[n] == pos[m] )
					for(x=0;x<6;x++)	// which means looking in each row/col
						if( pos[n] & (1 << x) && bit_count(mask[y][x]) > 2 )
						{
							h=(1 << n) + (1 << m);
							apply_new_mask( "HIDDEN PAIR: ", " in row ",y,y,x,h );
						}
	}
	for(x=0;x<6;x++)
	{
		for(n=0;n<6;n++)	// .. check each number
			for(pos[n]=y=0;y<6;y++)	// which means looking in each row/col
				if( !g[y][x] && (mask[y][x] & (1 << n)) )
					pos[n] += (1 << y);  // ith position of n

		for(n=0;n<5;n++)
			for(m=n+1;m<6;m++)
				if( bit_count(pos[n])==2 && pos[n] == pos[m] )
					for(y=0;y<6;y++)	// which means looking in each row/col
						if( pos[n] & (1 << y) && bit_count(mask[y][x]) > 2 )
						{
							h=(1 << n) + (1 << m);
							apply_new_mask( "HIDDEN PAIR: ", " in col ",x,y,x,h );
						}
	}
}
function hidden_triples()
{
	var x,y,n,m,p,i,bb,cc,a,b,c,h,box=0;
	var pos=new Array(6);

	for(bb=0;bb<6;bb+=2)		// Once more, for each box (6 of them 3 by 3 each)
		for(cc=0;cc<6;cc+=3)
		{
			for(n=0;n<6;n++)	// .. check each number
			{
				pos[n]=i=0;
				for(y=bb;y<bb+2;y++)	// which means looking in each 3 by 3 box
					for(x=cc;x<cc+3;x++,i++)
						if( !g[y][x] && (mask[y][x] & (1 << n)) )
							pos[n] += (1 << i);  // ith position of n
			}
			for(n=0;n<4;n++)
				for(m=n+1;m<5;m++)
					for(p=m+1;p<6;p++)
						if( bit_count(pos[n] | pos[m] | pos[p]) == 3 && pos[n] && pos[m] && pos[p] )
						{
							i=0;
							for(y=bb;y<bb+2;y++)	// which means looking in each 3 by 3 box
								for(x=cc;x<cc+3;x++,i++)
								{
									a=pos[n] & (1 << i);
									b=pos[m] & (1 << i);
									c=pos[p] & (1 << i);
									if( (a || b || c)
									  && bit_count(mask[y][x]) > ((a>0)+(b>0)+(c>0)) )
									{
										h=(1 << n) + (1 << m) + (1 << p);
										apply_new_mask( "HIDDEN TRIPLE: ", " in box ",box,y,x,h );
									}
								}
						}
			box++;
		}

	/*-------------------------------------------------------------------------*/
	/* Checking in the box will get most hidden pairs, but some are aligned    */
	/* over two box but still on the same row or columns				       */
	/*-------------------------------------------------------------------------*/
	for(y=0;y<6;y++)
	{
		for(n=0;n<6;n++)	// .. check each number
			for(pos[n]=x=0;x<6;x++)	// which means looking in each row/col
				if( !g[y][x] && (mask[y][x] & (1 << n)) )
					pos[n] += (1 << x);  // ith position of n

		for(n=0;n<4;n++)
			for(m=n+1;m<5;m++)
				for(p=m+1;p<6;p++)
					if( bit_count(pos[n] | pos[m] | pos[p]) == 3 && pos[n] && pos[m] && pos[p] )
					{
						for(x=0;x<6;x++)
						{
							a=pos[n] & (1 << x);
							b=pos[m] & (1 << x);
							c=pos[p] & (1 << x);
						//	if( y==4 ) alert( x + ' abc: ' + a + ' ' + b + ' ' + c + ' nmp: ' + n + ' ' + m + ' ' + p );
							if( (a || b || c)
							  && bit_count(mask[y][x]) > ((a>0)+(b>0)+(c>0)) )
							{
								h=(1 << n) + (1 << m) + (1 << p);
								apply_new_mask( "HIDDEN TRIPLE: ", " in row ",y,y,x,h );
							}
						}
					}
	}
	for(x=0;x<6;x++)
	{
		for(n=0;n<6;n++)	// .. check each number
			for(pos[n]=y=0;y<6;y++)	// which means looking in each row/col
				if( !g[y][x] && (mask[y][x] & (1 << n)) )
					pos[n] += (1 << y);  // ith position of n

		for(n=0;n<4;n++)
			for(m=n+1;m<5;m++)
				for(p=m+1;p<6;p++)
					if( bit_count(pos[n] | pos[m] | pos[p]) == 3 && pos[n] && pos[m] && pos[p] )
					{
						for(y=0;y<6;y++)
						{
							a=pos[n] & (1 << y);
							b=pos[m] & (1 << y);
							c=pos[p] & (1 << y);
							if( (a || b || c)
							  && bit_count(mask[y][x]) > ((a>0)+(b>0)+(c>0)) )
							{
								h=(1 << n) + (1 << m) + (1 << p);
								apply_new_mask( "HIDDEN TRIPLE: ", " in col ",x,y,x,h );
							}
						}
					}
	}
}
/*----------------------------------------------------------------------*/
/* MAIN PAIR TEST														*/
/*----------------------------------------------------------------------*/
function main_pair_test()
{
	var bb,cc,n,m,i,j,k,a,b,y,x1,x2,x3,h,cn;
	var mbox=new Array(6);
	var cnt=new Array(6);

	/*----------------------------------------------------------------------*/
	/* Purpose of this pair test is to look for pairs of numbers,			*/
	/* eg 3-7 and 3-7 in the same box. Since both numbers MUST be on both   */
	/* cells they can be eliminated from the rest of the box				*/
	/*----------------------------------------------------------------------*/
	for(bb=0;bb<6;bb+=2)		// Once more, for each box (6 of them 3 by 3 each)
		for(cc=0;cc<6;cc+=3)
		{
			k=0;
			for(i=bb;i<bb+2;i++)	// put the box in a 1D array for ease of use
				for(j=cc;j<cc+3;j++)
				{
					mbox[k]=mask[i][j];
					cnt[k]=bit_count(mask[i][j]);
					cordX[k]=j;
					cordY[k++]=i;
				}
			for(a=0;a<5;a++)	// .. check each pair in the 1D box array
				for(b=a+1;b<6;b++)
				{
					if( cnt[a]==2 && mbox[a] == mbox[b] )  // If same 2 numbers in the same 2 squares
					{
						for(m=0;m<6;m++)	// for all squares in the box
							for(n=0;n<6;n++) // for all numbers
							{
								if( m!=a && m!=b && (mbox[a] & (1 << n)) && (mbox[m] & (1 << n)) )
								{
								//	alert("here n=" + n + " m=" + m + " a=" + a + " mbox[a]=" + mbox[a] + " cnt[m]=" + cnt[m]);
									cn=abetx.charAt(n);
									strat_add("NAKED PAIR (Box): " + cordit(cordY[a],cordX[a]) + "/" + cordit(cordY[b],cordX[b]) + " removes " + cn + " from " + cordit(cordY[m],cordX[m]) + "<br>");
									mbox[m] -= (1 << n); // remove that number
									lable_square( cordY[m],cordX[m],(1 << n) );
								}
							}
					}
				}
		}

	/*----------------------------------------------------------------------*/
	/* Purpose of pair_test2 is to look for pairs of numbers, eg 3-7 and 3-7 */
	/* in the same row/col. Since both numbers MUST be on both cells they 	*/
	/* can be elininated from the rest of the ROW or COLUMN they are		*/
	/* aligned with. How cool is that?										*/
	/*----------------------------------------------------------------------*/
	for(y=0;y<6;y++)
		for(x1=0;x1<5;x1++)	// For every square...
			for(x2=x1+1;x2<6;x2++)
			{
				// This block checks the ROW the pair resides in...
				if( bit_count(mask[y][x1])==2 && mask[y][x1] == mask[y][x2] )
					for(i=0;i<6;i++)
					{
						h=(mask[y][i] & mask[y][x1]);
						if( i!=x1 && i!=x2 && !g[y][i] && h )
						{
							strat_add("NAKED PAIR (Row): " + cordit(y,x1) + "/" + cordit(y,x2) + " removes " + mask2str(mask[y][i] & h) + " from " + cordit(y,i) + "<br>");
							lable_square( y,i,h );
						}
					}

				// This block checks the COLUMN the pair resides in...
				if( bit_count(mask[x1][y])==2 && mask[x1][y] == mask[x2][y] )
					for(i=0;i<6;i++)
					{
						h=(mask[i][y] & mask[x1][y]);
						if( i!=x1 && i!=x2 && !g[i][y] && h )
						{
							strat_add("NAKED PAIR (Col): " + cordit(x1,y) + "/" + cordit(x2,y) + " removes " + mask2str(mask[i][y] & h) + " from " + cordit(i,y) + "<br>");
							lable_square( i,y,h );
						}
					}
			}
}

function main_triple_test()
{
	var bb,cc,i,j,k,y,x1,x2,x3,h,off;
	var mbox=new Array(6);
	var cnt=new Array(6);

	// LOOK FOR TRIPLES
	for(y=0;y<3;y++)
		for(x1=0;x1<4;x1++)	// For each triple
			for(x2=x1+1;x2<5;x2++)
				for(x3=x2+1;x3<6;x3++)
				{
					// This block checks the ROW the triple resides in...
					if( bit_count(mask[y][x1])>1 && bit_count(mask[y][x2])>1 && bit_count(mask[y][x3])>1 )
					{
						h=mask[y][x1] | mask[y][x2] | mask[y][x3];
						if( bit_count(h)==3 )
							for(i=0;i<6;i++)
							{
								off=(mask[y][i] & h);
								if( i!=x1 && i!=x2 && i!=x3 && off )
								{
									strat_add("NAKED TRIPLE (Row): " + cordit(y,x1) + "/" + cordit(y,x2) + "/" + cordit(y,x3) + " removes " + mask2str(off) + " from " + cordit(y,i) + "<br>");
									lable_square( y,i,off );
								}
							}
					}
					// This block checks the COLUMN the triple resides in...
					if( bit_count(mask[x1][y])>1 && bit_count(mask[x2][y])>1 && bit_count(mask[x3][y])>1 )
					{
						h=mask[x1][y] | mask[x2][y] | mask[x3][y];
						if( bit_count(h)==3 )
							for(i=0;i<6;i++)
							{
								off=(mask[i][y] & h);
								if( i!=x1 && i!=x2 && i!=x3 && off )
								{
									strat_add("NAKED TRIPLE (Col): " + cordit(x1,y) + "/" + cordit(x2,y) + "/" + cordit(x3,y) + " removes " + mask2str(off) + " from " + cordit(i,y) + "<br>");
									lable_square( i,y,off );
								}
							}
					}
				}

	/*----------------------------------------------------------------------*/
	// This block checks the BOX the triple resides in...
	/*----------------------------------------------------------------------*/
	for(bb=0;bb<6;bb+=2)		// Once more, for each box (6 of them 3 by 3 each)
		for(cc=0;cc<6;cc+=3)
		{
			k=0;
			for(i=bb;i<bb+2;i++)	// put the box in a 1D array for ease of use
				for(j=cc;j<cc+3;j++)
				{
					mbox[k]=mask[i][j];
					cnt[k]=bit_count(mask[i][j]);
					cordX[k]=j;
					cordY[k++]=i;
				}
			for(x1=0;x1<5;x1++)	// For each triple
				for(x2=x1+1;x2<5;x2++)
					for(x3=x2+1;x3<6;x3++)
					{
						if( cnt[x1]>1 && cnt[x2]>1 && cnt[x3]>1 )
						{
							h=mbox[x1] | mbox[x2] | mbox[x3];
							if( bit_count(h)==3 )
								for(i=0;i<6;i++)
								{
									off=(mbox[i] & h);
									if( i!=x1 && i!=x2 && i!=x3 && off )
									{
										strat_add("NAKED TRIPLE (Box): " + cordit(cordY[x1],cordX[x1]) + "/" + cordit(cordY[x2],cordX[x2]) + "/" + cordit(cordY[x3],cordX[x3]) + " removes " + mask2str(off) + " from " + cordit(cordY[i],cordX[i]) + "<br>");
										mbox[i] -= off; // remove that number
										lable_square( cordY[i],cordX[i],off ); // remove that number
									}
								}
						}
					}
		}
}
/*----------------------------------------------------------------------*/
/* Function to check for conflicts with the rules						*/
/*----------------------------------------------------------------------*/
function sanity_check()
{
	var bb,cc,n,i,j,c,x,y,zz,yy,failed=0;

	for( x in g )
		for( y in g[x] )	// for every square on the board...
			if( g[x][y]===0 && mask[x][y]===0 )	// if it is an known square...
			{
				set_square(y,x,g[x][y],3);	// hightlight conflicting squares
				return true;
			}

	for( x in g )
		for( y in g[x] )	// for every square on the board...
			if( g[x][y] )	// if it is an known square...
			{
				for( i=0;i<6;i++ ) // check values in row
				{
					if( i != y && g[x][i] == g[x][y] )
					{
						set_square(i,x,g[x][i],3);	// hightlight conflicting squares
						set_square(y,x,g[x][y],3);	// hightlight conflicting squares
						failed+=2;
					}
					if( i != x && g[i][y] == g[x][y] )
					{
						set_square(y,i,g[i][y],3);	// hightlight conflicting squares
						set_square(y,x,g[x][y],3);	// hightlight conflicting squares
						failed+=2;
					}
				}
			}

	for(bb=0;bb<6;bb+=2)			// for each box (6 of them 3 by 3 each)
		for(cc=0;cc<6;cc+=3)
			for(i=bb;i<bb+2;i++)		// which means looking in each 3 by 3 box
				for(j=cc;j<cc+3;j++)
					if( g[i][j] ) // if the square is known ...
						for(zz=bb;zz<bb+2;zz++)	// ..check every other cell
							for(yy=cc;yy<cc+3;yy++)
								if( !(zz==i && yy==j) && g[zz][yy] == g[i][j] )	// .. if the number is known
								{
									set_square(yy,zz,g[zz][yy],3);	// hightlight conflicting squares
									set_square(j,i,g[i][j],3);	// hightlight conflicting squares
									failed+=2;
								}
	return failed;
}
/* Function to reset the board to its normal blue background */
function blue_board()
{
	var x,y,done=0;
	for(y=0;y<6;y++)		// Redraw the board to clear any user highlighting
		for(x=0;x<6;x++)
		{
			if( some_changes===false ) t=document.getElementById("a"+y+x);
			if( some_changes===false ) t.style.backgroundColor=sq_bck[map[y][x]-1];
			if( g[y][x]>0 ) done++;
		}
	return done;
}
function post_to_form(cur_strat) {
	var frm = document.forms.servsolv;
	fill_transfer_vars(cur_strat);
	frm.submit();
}
/*----------------------------------------------------------------------*/
/* Function to run the steps above in one go. Resets the board colors	*/
/*----------------------------------------------------------------------*/
function take_step()
{
	var i,j,done=0,t,found=0,x,y;

	done=blue_board();
//	if( stage>0 && done > 0 && !block_board() ) return;

	if( done === 36 )	// If the number of solutions=36, we're all done
	{
		if( sanity_check()>0 )
			 alert("Opps. Not a valid KenKen solution");
		else alert("Thats it! All done");
	}
	else
	{
		if( stage === 0 ) some_changes=false;

		if( stage!==0 && !some_changes )
		{
			for( x in g )
				for( y in g[x] ) last[x][y]=mask[x][y];
			prevlaststage=stage;
			laststage=stage;
		}
	//	alert('before: ' + stage + ' ' + some_changes);
		if( some_changes ) stage=0;
		else
		{
			if( stage==MAX_STRAT ) stage=1
			else if( stage<10 ) stage++;
			else
			{
				for( ;stage<MAX_STRAT-1 && document.getElementById("CB"+kdu6x6_list[stage]).checked==false;stage++);
				stage++;
				if( stage >= MAX_STRAT )
				{
					alert("No more strategies to try - check any unchecked ones");
					return;
				}
			}
		}

		if( stage == 0 )
		{
			found=check_for_single();
			document.getElementById("R0").innerHTML=(found)? '<font color=#00ff00><b>' + found + '</b></font>' : '<font color=#ff0000><b>0</b></font>';
			some_changes=false;
		}
		else
		{
		/*	if( !document.ifrm )
				 doc = document.getElementById("ifrm").contentDocument;
			else doc = document.ifrm.document;
			doc.body.innerHTML='';
			doc.body.style.backgroundColor='#ddeeff';
			doc.body.style.color='#000000';
		*/
			if( stage == 1 ) reset_yes_no( kdu6x6_list,5 );

			if( stage > 5 )
			{
				document.getElementById("takestep").onclick=null;
				document.getElementById("takestep").className = 'GButton';
			}
			if( sanity_check() )
				alert("Oops - you've got an error on the board");
			clear_results = true;

			if( stage == 1  ) show_candidates();
			if( stage == 2  ) singles_in_row_col();
			if( stage == 3  ) singles_in_box();
			if( stage == 4  ) { main_pair_test(); main_triple_test(); }
			if( stage == 5  ) { hidden_pairs(); hidden_triples(); }

			if( stage == 6  ) /*K1*/ 				post_to_form('KL1');
			if( stage == 7  ) /*Dog Legs*/ 			post_to_form('KIO');

			if( stage == 8 ) /*X-Wing*/ 			post_to_form('XWG');
			if( stage == 9 ) /*Simple Colouring*/ 	post_to_form('SCN');
			if( stage == 10 ) /*Y-Wing*/ 			post_to_form('YWG');
			if( stage == 11 ) /*Sword-Fish */ 		post_to_form('SFH');
			if( stage == 12 ) /*Multivalue X-Wing */post_to_form('MXW');
			if( stage == 13 ) /*X-Cycles */ 		post_to_form('XCY');
			if( stage == 14 ) /*XYZ-Wing */ 		post_to_form('XYZ');
			if( stage == 15 ) /*remote pairs*/ 		post_to_form('RPC');
			if( stage == 16 ) /*XY-Chain */ 		post_to_form('XYC');

			if( stage == 17 ) /*aligned pair exc */ post_to_form('APE');
			if( stage == 18 ) /*Grouped X-Cycles */ post_to_form('GXC');
			if( stage == 19 ) /*Sue-de-Coq*/ 		post_to_form('COQ');
			if( stage == 20 ) /*MultiColouring*/ 	post_to_form('MCO');
			if( stage == 21 ) /*Forcing Chains*/ 	post_to_form('FCN');

			if( stage == 22 ) /*AIC*/ 				post_to_form('AIC');
			if( stage == 23 ) /*AIC*/ 				post_to_form('AI2');
			if( stage == 24 ) /*AIC*/ 				post_to_form('AI3');
			if( stage == 25 ) /*ALS*/ 				post_to_form('ALS');
			if( stage == 26 ) /*Death Blossom*/ 	post_to_form('DBL');

			if( stage == 1 )
				for( x in g )
					for( y in g[x] ) if( mask[y][x] && show[y][x] ) { show[y][x]=0; lable_square(y,x,0); }

			if( stage < 6  ) {
				document.getElementById("R" + stage).innerHTML=(some_changes)? '<font color=#00ff00><b>Yes</b></font>' : '<font color=#ff0000><b>No</b></font>';
			} else {
				document.getElementById("R" + kdu6x6_list[stage-6]).innerHTML=(some_changes)? '<font color=#00ff00><b>Yes</b></font>' : '<font color=#ffff00><b>Wait</b></font>';
			}
			for( x in g )
				for( y in g[x] ) orig[x][y]=mask[x][y];
		}
		if( sanity_check() )
			alert("Oops - you've got an error on the board");

		t=document.getElementById("TestT");
		for(i=0;i<MAX_STRAT-1;i++)
			t.rows[i*1+offset[i]].cells[1].style.backgroundColor=(stage==i) ? "#777700" : ((((i*1+offset[i])%2)==0)?"#333333":"#222222");
		document.getElementById("backstep").className='SButton';
		if( stage==MAX_STRAT && some_changes == false )
			alert("No more known logical steps to take - you have to enter a number somewhere and then click 'Take Step'");
	}
}
function back_step()
{
	var i,j,s;
	if( document.getElementById("backstep").className == 'GButton' ) return;
	for( j in g )
		for( i in g[j] )
		{
			if( last[j][i]>0 )
			{
				show[j][i]=g[j][i]=0;
				orig[j][i]=mask[j][i]=last[j][i];
				lable_square( j,i,0 );
			}
		}
	some_changes=false;
	stage=(stage==0)?prevlaststage:laststage;
	t=document.getElementById("TestT");
	for(i=0;i<MAX_STRAT-1;i++)
		t.rows[i*1+offset[i]].cells[1].style.backgroundColor=(stage==i) ? "#777700" : ((((i*1+offset[i])%2)==0)?"#333333":"#222222");
	backup_yes_no6x6( kdu6x6_list, stage, 6 );

	document.getElementById("backstep").className='GButton';
	document.getElementById("takestep").onclick=take_step;
	document.getElementById("takestep").className = 'SButton';
	blue_board();
}
/*------------------------------------------------------------------------*/
/* Function to colour the board according to what the user has clicked on */
/*------------------------------------------------------------------------*/
var inside_cell=false;

function Sudoku1( afield,y,x )
{
	var i,j,cell,t;
	var fval=convert_str2mask(afield.value);

	if( fval == 0 )
	{
		g[y][x]=0;
		mask[y][x]=63;
		lable_square( y,x,0 );
	}
	else
	{
		if( bit_count(fval) == 1 )
		{
			g[y][x]=bit2int(fval)+1;
			mask[y][x]=0;
			set_square( x,y,g[y][x],2 );
		}
		else
		{
			g[y][x]=0;
			mask[y][x]=fval;
			lable_square( y,x,0 );
		}
	}
	cell=document.getElementById("a"+y+x);
	cell.onclick=color_same;
	stage=0;
	t=document.getElementById("TestT");
	for(i=0;i<MAX_STRAT-1;i++)
		t.rows[i*1+offset[i]].cells[1].style.backgroundColor=(stage==i) ? "#777700" : ((((i*1+offset[i])%2)==0)?"#333333":"#222222");
}
function color_same(e)
{
	var targ,x,y,i,t;
	var inputbox,ival='';
	if (!e) var e=window.event;
	if (e.target) targ=e.target;
	else if (e.srcElement) targ=e.srcElement;
	if (targ.nodeType == 3) // defeat Safari bug
		targ=targ.parentNode;

	x=targ.id.charAt(2);
	y=targ.id.charAt(1);
	if( editmode==true )
	{
		targ.onclick=null;

		if( g[y][x] )	// If user clicked on an unknown square..
			ival=g[y][x];
		else
			for(i=0;i<6;i++) if( mask[y][x] & (1 << i) )
				ival=ival + (i*1+1)

		targ.innerHTML="<input type=\"text\" value=\"" + ival + "\" size=9 class=\"iput2\" maxlength=9 id=\"iput\" onblur=\"javascript:Sudoku1(this," + y + "," + x + ");\">"

		document.getElementById("iput").focus();
	}
	else
	{
		for(j=0;j<6;j++)	// For each square on the board
			for(i=0;i<6;i++)
			{
				// Get the table cell name
				t=document.getElementById("a"+j+i);
				if( g[y][x]==0 )	// If user clicked on an unknown square..
				{
					if( g[j][i]>0 && (mask[y][x] & (1 << (g[j][i]-1))) )
						t.style.backgroundColor='#ddccaa';
					else if( mask[j][i] & mask[y][x] )
						t.style.backgroundColor='#ffeedd';
					else
						t.style.backgroundColor='#ddeeff';
				}
				else // If user clicked on a known number..
				{
					if( (x==i && y==j) || g[j][i]==g[y][x] ) // Highlight other occurances of that number
						t.style.backgroundColor='#ddccaa';
					else if( (mask[j][i] & (1 << (g[y][x]-1))) )  // .. and where its possible
						t.style.backgroundColor='#ffeedd';
					else	// .. otherwise its the normal background color
						t.style.backgroundColor='#ddeeff';
				}
			}
	}
}
function print_board(ptype)
{
	SGW=window.open('KenDoku6x6Printable.htm?p='+ptype,'_blank','resizable=yes,toolbar=1,scrollbars=yes,left=100,top=10,screenX=100,screenY=10,width=670,height=680');
	if (!SGW.opener) SGW.opener=self;
}
function fired_event()
{
	var s,c,y,x,n,t,stratname;
	var doc;

	if( !document.ifrm )
		 doc = document.getElementById("ifrm").contentDocument;
	else doc = document.ifrm.document;
	if( !doc.getElementById("kbin") ) return;
	s = doc.getElementById("kbin").value;
	stratname = doc.getElementById("nstage").value;
	t=document.getElementById("TestT");

	if( stratname!="NO" )
	{
		stage = get_stage(kdu6x6_list,stratname);
		for(y=0;y<6;y++) for(x=0;x<6;x++) rcm[y][x]=0;
		for(i=0;i<s.length;i+=3)
		{
			c = s.charAt(i);
			if( c == '{' ) break;
			y = s.charAt(i)-1;
			x = s.charAt(i+1)-1;
			n = s.charAt(i+2)-1;
			rcm[y][x] |= (1 << n);
			some_changes = true;
		}
		for(y=0;y<6;y++)
			for(x=0;x<6;x++)
			{
				if( rcm[y][x] ) lable_square(y,x,rcm[y][x] & mask[y][x]);
				switch( s.charAt(y*6+x+i+1) ){
				case '1' : document.getElementById("a"+y+x).style.backgroundColor='#ffff55'; break;
				case '2' : document.getElementById("a"+y+x).style.backgroundColor='#eeaa55'; break;
				case '3' : document.getElementById("a"+y+x).style.backgroundColor='#55ff55'; break;
				case '4' : document.getElementById("a"+y+x).style.backgroundColor='#55ffcc'; break;
				}
			}
		for(i=0;i<MAX_STRAT-1;i++)
		{
			t.rows[i*1+offset[i]].cells[1].style.backgroundColor=(stage==i) ? "#777700" : ((((i*1+offset[i])%2)==0)?"#333333":"#222222");
		}
		paint_yes_no( kdu6x6_list, stratname );
	}
	else
	{
		for(i=0;i<MAX_STRAT-1;i++)
			t.rows[i*1+offset[i]].cells[1].style.backgroundColor=((((i*1+offset[i])%2)==0)?"#333333":"#222222");
		paint_yes_no( kdu6x6_list, stratname );
	}
	document.getElementById("takestep").onclick=take_step;
	document.getElementById("takestep").className = 'SButton';
}
function toggle_strats( whichset )
{
	var i;
	switch( whichset ) {
	case 2 :
		for(i=11;i<=15;i++)
			document.getElementById("CB" + kdu6x6_list[i]).checked = !document.getElementById("CB" + kdu6x6_list[i]).checked;
		break;
	case 3 :
		for(i=16;i<=22;i++)
			document.getElementById("CB" + kdu6x6_list[i]).checked = !document.getElementById("CB" + kdu6x6_list[i]).checked;
		break;
	case 4 :
		for(i=23;i<=34;i++)
			document.getElementById("CB" + kdu6x6_list[i]).checked = !document.getElementById("CB" + kdu6x6_list[i]).checked;
		break;
	}
}
function add_cage_num(t)
{
	var x,y;
	x=t.id.charAt(2);
	y=t.id.charAt(3);
	if( !IsNumericKenKen(t.value) )
		t.value='';

	validate_kendoku();
}
function isBlack( t )
{
	if( t.style.backgroundColor == '') return true;
	if( t.style.backgroundColor == 'rgb(0, 0, 0)') return true;
	if( t.style.backgroundColor == 'rgb(0,0,0)') return true;
	if( t.style.backgroundColor == '#000000') return true;
	return false;
}
function set_pentomino_id( y, x )
{
	var many=0;
	if( cid[y][x]!=0 ) return 0;
	cid[y][x] = cur_id;
	many = 1;
	if( y > 0 && !isBlack(document.getElementById("CBL"+(y-1)+x)) ) many += set_pentomino_id( y-1, x );
	if( x > 0 && !isBlack(document.getElementById("CRL"+y+(x-1))) ) many += set_pentomino_id( y, x-1 );
	if( y < 5 && !isBlack(document.getElementById("CBL"+y+x)) ) many += set_pentomino_id( y+1, x );
	if( x < 5 && !isBlack(document.getElementById("CRL"+y+x)) ) many += set_pentomino_id( y, x+1 );
	return many;
}
function set_pentomino_size( y, x, target_id, many )
{
	if( x < 0 || x > 5 ) return 0;
	if( y < 0 || y > 5 ) return 0;

	if( cid[y][x] != target_id ) return 0;
	if( rcm[y][x] == 1 ) return 0;
	rcm[y][x] = 1;
	csz[y][x] = many;
	set_pentomino_size(y,x-1,target_id, many);
	set_pentomino_size(y,x+1,target_id, many);
	set_pentomino_size(y-1,x,target_id, many);
	set_pentomino_size(y+1,x,target_id, many);
}
function get_neighbour_colours( y, x, tcid )
{
	var c = 0;
	if( x < 0 || x > 5 ) return 0;
	if( y < 0 || y > 5 ) return 0;

	if( rcm[y][x] == 1 ) return 0;
	rcm[y][x] = 1;

	if( cid[y][x] != tcid )
	{
		if( map[y][x]==0 ) return 0;
		return (1 << map[y][x]);
	}
	c |= get_neighbour_colours( y-1, x, tcid );
	c |= get_neighbour_colours( y, x-1, tcid );
	c |= get_neighbour_colours( y+1, x, tcid );
	c |= get_neighbour_colours( y, x+1, tcid );
	return c;
}
function paint_cells( y, x, tcid, newcol )
{
	if( x < 0 || x > 5 ) return;
	if( y < 0 || y > 5 ) return;

	if( rcm[y][x] == 1 ) return;
	if( cid[y][x] != tcid ) return;
	if( map[y][x] > 0 ) return;

	rcm[y][x] = 1;
	map[y][x] = newcol;

	var t = document.getElementById("KL"+y+x);
	if( t.style.backgroundColor != sq_bck[map[y][x]-1] ) {

		t.style.backgroundColor = sq_bck[map[y][x]-1];

		if( y<5 && !isBlack(document.getElementById("CBL"+y+x)) )
			document.getElementById("CBL"+y+x).style.backgroundColor = sq_line[map[y][x]-1];

		if( x<5 && !isBlack(document.getElementById("CRL"+y+x)) )
			document.getElementById("CRL"+y+x).style.backgroundColor = sq_line[map[y][x]-1];
	}

	document.getElementById('board').value = y + ' ' + x;


	paint_cells( y-1, x, tcid, newcol );
	paint_cells( y, x-1, tcid, newcol );
	paint_cells( y+1, x, tcid, newcol );
	paint_cells( y, x+1, tcid, newcol );
}

function asign_four_color_map()
{
	var emptycells = 36;
	var ncol;
	var y,x,sx,sy,i,j;

	while( emptycells )
	{
		for(j=0;j<6;j++) for(i=0;i<6;i++) rcm[j][i]=0;
		x=y=-1;
		for(sy=0;sy<6 && y==-1;sy++)
			for(sx=0;sx<6 && x==-1;sx++)
				if( map[sy][sx]===0 ) { x=sx;y=sy; }
		if( x==-1 ) break;

		ncol = get_neighbour_colours( y, x, cid[y][x] );
		lastncol = ncol;

		for(j=0;j<6;j++) for(i=0;i<6;i++) rcm[j][i]=0;
		if( ncol == 62 ) { return false; }
		if( !ncol || (ncol & 2) == 0 ) paint_cells( y, x, cid[y][x], 1 );
		else if( (ncol & 4) == 0 ) paint_cells( y, x, cid[y][x], 2 );
		else if( (ncol & 8) == 0 ) paint_cells( y, x, cid[y][x], 3 );
		else if( (ncol & 16) == 0 ) paint_cells( y, x, cid[y][x], 4 );
		else if( (ncol & 32) == 0 ) paint_cells( y, x, cid[y][x], 5 );

		for(emptycells=y=0;y<6;y++) for(x=0;x<6;x++) if( map[y][x]==0 ) emptycells++;
	}
	return true;
}
function cager(t)
{
	var x=t.id.charAt(4);
	var y=t.id.charAt(3);
	t.style.backgroundColor = ( isBlack(t) ) ? sq_bck[map[y][x]-1] : '#000000';

	validate_kendoku();
}
function cageb(t)
{
	var x=t.id.charAt(4);
	var y=t.id.charAt(3);
	t.style.backgroundColor = ( isBlack(t) ) ? sq_bck[map[y][x]-1] : '#000000';

	validate_kendoku();
}
function load_parent_puzzle()
{
	var x,y,s='',st=0,frm,t;

	for(y=0;y<6;y++) for(x=0;x<6;x++) csz[y][x]=ccl[y][x]=rcm[y][x]=map[y][x]=0;

	if( location.search != '?n=1' )
	{
		validate_kendoku();
		return;
	}
	if( opener === null
	 || opener.document === null
	 || opener.document.getElementById('servsolv') === null ) {
		alert('Cannot find the parent document - the KenKen Solve page');
		return;
	}
	frm = opener.document.getElementById('servsolv');

	str2map(frm.elements['colmap'].value);
	str2ccl(frm.elements['cluemap'].value);

	document.getElementById("colmap").value = frm.elements['colmap'].value;
	document.getElementById("cluemap").value = frm.elements['cluemap'].value;

	for(y=0;y<6;y++) for(x=0;x<6;x++)
	{
		t = document.getElementById("KL"+y+x);
		t.style.backgroundColor = sq_bck[map[y][x]-1];
		document.forms.BoardDesign.elements["CL"+y+x].value=( ccl[y][x]>0 ) ? ccl[y][x]+opp[y][x] : '';
	}

	for(y=0;y<6;y++)
		for(x=0;x<5;x++)
		{
			t = document.getElementById("CRL"+ y + x);
			if( t ) t.style.backgroundColor = ( map[y][x]==map[y][x+1] ) ? sq_line[map[y][x]-1] : '#000000';
		}
	for(y=0;y<5;y++)
		for(x=0;x<6;x++)
		{
			t = document.getElementById("CBL"+ y + x);
			if( t ) t.style.backgroundColor = ( map[y][x]==map[y+1][x] ) ? sq_line[map[y][x]-1] : '#000000';
		}
	compute_cage_sizes();

}

function validate_kendoku()
{
	var x,y,many;
	var cluemap = '',colmap='';
	var totcur = 0;

	validkenken = true;

	for(y=0;y<6;y++) for(x=0;x<6;x++) cid[y][x]=csz[y][x]=rcm[y][x]=map[y][x]=0;
	cur_id = 1;
	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
		{
			many = set_pentomino_id( y, x );
			set_pentomino_size( y, x, cur_id, many );
			cur_id++;
		}

//	for(y=0;y<6;y++) for(x=0;x<6;x++) document.forms.BoardDesign.elements["CL"+y+x].value=ccl[y][x];

	if( !asign_four_color_map() )
		alert('oops, cant assign 4 colors');

	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
		{
			v = document.getElementById("CL"+y+x);
			if( v.value != '' ) totcur += parseInt(v.value);
		}

	document.getElementById("sendsolv").className = (validkenken) ? 'GrnButton' : 'GButton';

	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
		{
			v = document.getElementById("CL"+y+x);
			cluemap += v.value +',';
		//	cluemap += cell2opp(v.value);
		//	cluemap += padzero(v.value);
			colmap += map[y][x].toString();
		}
	document.getElementById("cluemap").value = cluemap;
	document.getElementById("colmap").value = colmap;

}
function validate_kendoku_but()
{
	validate_kendoku();
}

function cell2opp( v )
{
	if( v.length>0 )
	{
		var vl = v.charAt(v.length-1);
		if( vl == '+' || vl == '-' || vl == 'x' || vl == '/' ) {
			var c = v.substr(0,v.length-1);
			return padzero(c*1);
		}
		else
		{
			return padzero(v*1);
		}
	}
	return "00";
}

function send_to_solver()
{
	var x,y,many;
	var cluemap = '',colmap='';

	if( !validkenken ) {
		alert('Current KenKen is not validating, please modify');
	}

	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
		{
			v = document.getElementById("CL"+y+x);
			cluemap += v.value +',';
		//	cluemap += cell2opp(v.value);
			colmap += map[y][x].toString();
		}

	document.getElementById("cluemap").value = cluemap;
	document.getElementById("colmap").value = colmap;


		if( opener === null
		 || opener.document === null
		 || opener.document.getElementById('servsolv') === null ) {
			alert('Cannot find the parent document - the KenKen Solve page');
			return;
		}


	frm = opener.document.getElementById('servsolv');

	frm.elements['cluemap'].value = cluemap;
	frm.elements['colmap'].value = colmap;

	opener.load_from_fields();

	window.close();
}
function clear_design()
{
	var x,y;
	for(y=0;y<6;y++)
		for(x=0;x<6;x++)
		{
			document.getElementById("CL"+y+x).value = '';
		}
	for(y=0;y<6;y++)
		for(x=0;x<5;x++)
		{
			document.getElementById("CRL"+ y + x).style.backgroundColor = '#000000';
		}
	for(y=0;y<5;y++)
		for(x=0;x<6;x++)
		{
			document.getElementById("CBL"+ y + x).style.backgroundColor = '#000000';
		}
	validate_kendoku();
}