var ready_done = false, ready = function() { if (ready_done) return; ready_done = true; loadSol(); if (isChallenge) challengeLoad(); } if (document.readyState === 'complete') ready(); else if (document.addEventListener) { // gecko, webkit, opera, IE 9 document.addEventListener("DOMContentLoaded", ready, false); window.addEventListener("load", ready, false); } else if (document.attachEvent) { // IE 8- document.attachEvent("onreadystatechange", ready); window.attachEvent("onload", ready); } var isChallenge = false; var solution = new Array(); var blocks = new Array(); var count = new Array(); var mapdata = new Array(); var mapjson = new Array(); var htmlnotification = ''; var jsonmapdata = new Object; //var jsonmapdata.solutions = new Array(); var mapType; // 1 = simple, 2 = normal, ...; used for mixpanel tracking var pressedGoTime = 0; function loadSol(sol, moves) { if (sol == null) if (document.getElementById('mapsol') != undefined) sol = document.getElementById('mapsol').innerHTML; if (sol) { tmp = sol.split(':'); position = tmp[1].split('.'); mapid = tmp[0]; clearwalls(mapid); for(var i in position) { if (document.getElementById(mapid+','+position[i]) != undefined) { object = document.getElementById(mapid+','+position[i]); grid_click(object); } } } if (moves && mapid) { updateDsp(mapid, 'dspCount', moves+ " moves"); } } function showNotification(html) { var div = document.createElement('div'); var pref = '
'; pref += '
[Close]
'; pref += '
'; var suff = '
'; //var suff = ''; div.innerHTML = pref+html+suff; document.body.appendChild(div.firstChild); } function changeWallColor(newColor) { playerWallColor = newColor; loadSol(null); } function changeWallEmblem(newEmblem) { playerWallEmblem = newEmblem; loadSol(null); } function grid_click(obj) { //Prepare data tmp = obj.id.split(','); mapid = tmp[0] - 0; y = tmp[1]; x = tmp[2]; //The users solution - prepare it if it's not started if (solution[mapid] == undefined) { getmapdata(mapid); } //Is this placing a wall, or removing one? var tmp = obj.id; childdiv = document.getElementById('child_'+tmp); if (obj.cv) { //Removing a wall obj.cv = false; //Reset childdiv to it's default. childdiv.removeAttribute("class"); childdiv.setAttribute("class", "grid_inner"); //childdiv.style.backgroundColor = 'transparent'; //return the td obj back to it's default. obj.style.backgroundColor = ''; obj.style.backgroundImage = ''; obj.removeAttribute("class"); obj.setAttribute("class", "grid_td"); blocks[mapid]++; //Remove wall solution[mapid] = solution[mapid].replace('.'+y+','+x+'.', '.'); } else { //Placing a wall if (blocks[mapid] < 1) { updateDsp(mapid, 'dspWalls', "OUT!"); return; } obj.cv = true; childdiv.removeAttribute("class"); childdiv.setAttribute("class", "grid_td_walls"); if (typeof playerWallColor === 'undefined' || playerWallColor == '') obj.style.backgroundColor = '#666666'; else obj.style.backgroundColor = playerWallColor; if (typeof playerWallEmblem !== 'undefined' && playerWallEmblem !== '') obj.style.backgroundImage="url(images/marks/"+playerWallEmblem+")"; //Add Wall solution[mapid] += y+','+x+'.'; blocks[mapid]--; } //document.getElementById('blocksdisplay').innerHTML = ""+blocks[mapid]+""; if (isChallenge == true) { challengeWall(mapid); } updateDsp(mapid, 'dspWalls', blocks[mapid]+" walls"); //document.getElementById(mapid+',dspWalls').innerHTML = " "+blocks[mapid]+" walls"; } function updateDsp(mapid, element, data) { //if (mapdata[mapid] == undefined) // return; //if (mapdata[mapid].example != true) { if (document.getElementById(mapid+','+element) != undefined) { handle = document.getElementById(mapid+','+element); handle.innerHTML = data; } //} } function getmapdata(mapid) { if (typeof(mapdata[mapid]) != 'object') mapdata[mapid] = decryptJSON(jsonmapdata[mapid]); blocks[mapid] = mapdata[mapid].walls; solution[mapid] = '.'; updateDsp(mapid, 'dspWalls', blocks[mapid]+" walls"); } function doSend(mapid) { if (solution[mapid] == undefined) { getmapdata(mapid); } pressedGoTime = new Date().getTime(); reqstr = "isChallenge="+isChallenge reqstr += "&r=getpath" reqstr += "&mapcode="+mapdata[mapid].code; reqstr += "&mapid="+mapid; reqstr += "&solution="+solution[mapid]; ajax.requestFile = "do.php?"+reqstr; //prepare strdata ajax.onCompletion = request_path_done; // specify function to be executed on response ajax.runAJAX(); } function requestSol(mapID) { ajax.requestFile = "do.php?r=getsol&mapID="+mapID; //prepare strdata ajax.onCompletion = requestSolDone; // specify function to be executed on response ajax.runAJAX(); } function requestSolDone() { var JO; JO = decryptJSON(ajax.response); if (JO.solution == 'undefined') return; //clearwalls(JO.mapid); loadSol(JO.mapid + ":" + JO.solution, JO.moves); } function clearwalls(mapid) { if (solution[mapid] == undefined) return; walls = solution[mapid].split('.'); for(var i in walls) { tmp = walls[i].split(','); eid = mapid+','+tmp[0]+','+tmp[1]; if (document.getElementById(eid) != undefined) { obj = document.getElementById(eid); obj.cv = false; childdiv = document.getElementById('child_'+obj.id); //Reset childdiv to it's default. childdiv.removeAttribute("class"); childdiv.setAttribute("class", "grid_inner"); //return the td obj back to it's default. obj.style.backgroundColor = ''; obj.style.backgroundImage = ''; obj.removeAttribute("class"); obj.setAttribute("class", "grid_td"); } } solution[mapid] = undefined; getmapdata(mapid); } function resetwalls(mapid) { answer = confirm("Remove walls and start fresh?"); if (answer) { clearwalls(mapid); } } function request_path_done() { var JO = decryptJSON(ajax.response); var mapid = JO.mapid; mapjson[mapid] = JO; var speedbox = document.getElementById(mapid+',speed'), speed = speedbox.options[speedbox.selectedIndex].text, mute = !checkSound(mapid); nowTime = new Date().getTime(); var responseTime = nowTime - pressedGoTime; mixpanel.track('click go', { 'speed': speed, 'mute': mute, 'mapid': mapid, 'type': mapType, 'response time': responseTime }); for(var i in JO.error) console.error('\n JO error ' + JO.error[i]); if (JO.blocked) { alert("The path is blocked!"); return; } var disptext = "Record: "+JO.best+" by "+JO.bestby; updateDsp(JO.mapid, 'dspID', disptext); mapdata[mapid].moveCount = new Object; mapdata[mapid].usedTiles = new Array(); mapdata[mapid].restoreTiles = new Array(); mapdata[mapid].pathColor = new Object; mapdata[mapid].pathsPending = JO.path.length; mapdata[mapid].isMultiPath = (JO.path.length > 1); for(i in JO.path) { mapdata[mapid].moveCount[i] = 0; mapdata[mapid].pathColor[i] = '#ffffff'; animatePath(JO.path[i].path, mapid, JO.path[i].start, i); } //Mark off challenges //TODO: Temporarly disabled because it breaks the tutorial; if(isChallenge && 2 == 4) { for(var i = 0; i < JO.completedChallenges.length; i++) { var challengeId = JO.completedChallenges[i]; document.getElementById("challenge_id_" + challengeId).className = "challenge_complete"; } } } function decryptJSON(text) { var JO; if (typeof(JSON) == 'undefined') { JO = !(/[^,:{}\[\]0-9.\-+Eaeflnr-u \n\r\t]/.test(text.replace(/"(\\.|[^"\\])*"/g, ''))) && eval('(' + text + ')'); } else { JO = JSON.parse(text); } return JO; } function animatePath(path, mapid, start, pathNumber) { var tmp = start.split(','); var y = tmp[0]; var x = tmp[1]; var p = path; //Prepare the path var c = p.substring(0, 1); p = p.substring(1); document.getElementById(mapid+',btn').disabled = true; doanimate(x, y, p, c, mapid, pathNumber); } function animatePathDone(mapid) { if (typeof(currentPage) == "object") scoresRequestPage(mapid, currentPage[mapid]); document.getElementById(mapid+',btn').disabled = false; if (isChallenge == true) { challengeGo(mapid); } } function checkSound(mapid) { if (document.getElementById(mapid+',mute').checked) { return false; } if (typeof(soundManager) != 'object') { return false; } return true; } function doanimate(x, y, p, c, mapid, pathNumber) { //x, y position //p path string being trunicated. //c current target code. //t next target code. t = p.substring(0, 1); //Animate current square, and move to next one. if (count[mapid] == undefined) { count[mapid] = 0; } //Set the color for the first target. if (count[mapid] == 0 && !(c > 0)) mapdata[mapid].pathColor[pathNumber] = targetColor(c); //Display movecount if (mapdata[mapid].moveCount[1] > 0 && mapdata[mapid].moveCount[0] > 0) updateDsp(mapid, 'dspCount', mapdata[mapid].moveCount[0] + ' + ' + mapdata[mapid].moveCount[1] + ' = ' + count[mapid] + " moves"); else updateDsp(mapid, 'dspCount', count[mapid]+ " moves"); //document.getElementById(mapid+',dspCount').innerHTML = count[mapid]+ " moves"; //Get a handle on the element. eid = mapid+','+x+','+y; //Verify. if (document.getElementById(eid) == undefined) { console.error("Path exited field...?"); animatePathDone(mapid); return; } handle = document.getElementById(eid); //Maintain our original classname, no matter the cost! origclass = handle.className; if ( origclass == 'grid_td_path'+pathNumber+'-1' || origclass == 'grid_td_path'+pathNumber+'-2' || origclass == 'grid_td_path'+pathNumber+'-3' || origclass == 'grid_td_path'+pathNumber+'-4' ) { // if (origclass == 'grid_td_animate' || origclass == 'grid_td_animate_pre' ) { origclass = handle.classOrigName; //setTimeout(handle.setAttribute('class', origclass), 850); } //handle.style.backgroundColor = mapdata[mapid].pathColor[pathNumber]; handle.classOrigName = origclass; //Animate the first square in a path. if (count[mapid] == 0 && !(c > 0)) { count[mapid]--; mapdata[mapid].moveCount[pathNumber]--; c = t; if (!(c > 0)) c = '2'; } switch(c) { //The path is moving to a new position case '1': //1 - Up case '2': //2 - Right case '3': //3 - Down case '4': //4 - Left //Track move count count[mapid]++; mapdata[mapid].moveCount[pathNumber]++; //Notify users on score levels; switch(count[mapid]) { //case mapjson[mapid].best: //flashelement(mapid+',dspCount', 4, "#FF0000"); //break; case 500: case 400: //case 350: case 300: //case 250: case 200: //case 150: case 100: //case 50: if (checkSound(mapid)) { soundManager.setVolume('charm', 40); soundManager.setPan('charm', 75) soundManager.play('charm'); } //Flash flashelement(mapid+',dspCount', 4); break; } childdiv = document.getElementById('child_'+handle.id); if (childdiv.className.indexOf('grid_td_walls') < 0) { childdiv.setAttribute('class', 'grid_td_path'+pathNumber+'-'+c); handle.style.backgroundColor = mapdata[mapid].pathColor[pathNumber]; var string = "if (document.getElementById('"+'child_'+eid+"').className == 'grid_td_path"+pathNumber+'-'+c+"')"; string += "document.getElementById('"+'child_'+eid+"').removeAttribute('class');"; setTimeout(string, 855); //Maintain disabled appearnce of checkpoints if (handle.pressed == true) { setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '#dddddd';", 865); } else { setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '';", 865); } } break; //Teleports case 't': case 'm': case 'g': case 'i': case 'k': //Outs case 'u': case 'n': case 'h': case 'j': case 'l': case 'r': // if (handle.pressed == true) // break; //case 'a': case 'b': case 'c': case 'd': case 'e': //handle.setAttribute('class', 'grid_td_pressed'); //handle.classOrigName = 'grid_td_pressed'; //if (handle.pressed == true) { //var currentColor = rgbStringToHex(handle.style.backgroundColor); //if (currentColor == '') // break; //var dulled = '#'+dullColor(currentColor, .6); //console.log('bgcolor', dulled, currentColor); //handle.style.backgroundColor = dulled; //setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '"+dulled+"';", 865); if (mapdata[mapid].isMultiPath == false) { handle.style.backgroundColor = '#dddddd'; setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '#dddddd';", 865); handle.pressed = true; } else { if (contains(mapdata[mapid].usedTiles, eid)) { handle.style.backgroundColor = '#dddddd'; setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '#dddddd';", 865); handle.pressed = true; } else { //mapdata[mapid].usedTiles.push(eid); //break; } } if (contains(mapdata[mapid].usedTiles, eid) == false) mapdata[mapid].usedTiles.push(eid); //mapdata[mapid].restoreTiles.push("document.getElementById('"+eid+"').style.backgroundColor = '';"); //mapdata[mapid].restoreTiles.push("document.getElementById('"+eid+"').pressed = false;"); //alert(mapdata[mapid].pathColor[pathNumber]); //break; } //Sound effects if (t == 'r') { if (checkSound(mapid)) { soundManager.setVolume('bling', 40); soundManager.setPan('bling', -75) soundManager.setVolume('blingb', 40); soundManager.setPan('blingb', 75) if (pathNumber == 0) soundManager.play('bling'); if (pathNumber == 1) soundManager.play('blingb'); } } //Done messing with current target //Now take pre-action regarding the next tile. //Speaking of the next tile - does it exist? //End of the line? if (t == '') { mapdata[mapid].pathsPending--; //console.log('path pending', mapdata[mapid].pathsPending); if (mapdata[mapid].pathsPending > 0) return; //console.log('path pending complete', mapdata[mapid].pathsPending); //Did we beat or tie any records? //Saw someone do this, thought it was clever. //Switch for range result. var disptext = "" var improvedScore = (count[mapid] > mapjson[mapid].mybest && mapjson[mapid].mybest != "0"); switch (true) { case (count[mapid] > mapjson[mapid].best): disptext = "Beat "+mapjson[mapid].bestby+"'s record of "+mapjson[mapid].best+" with "+count[mapid]+"!"; break; case (count[mapid] == mapjson[mapid].best): disptext = "Tied "+mapjson[mapid].bestby+"'s record of "+mapjson[mapid].best; break; case (mapjson[mapid].mybest == "0"): disptext = "You scored "+count[mapid]+"!"; break; case (count[mapid] > mapjson[mapid].mybest): disptext = "Improved score "+mapjson[mapid].mybest+ " to "+count[mapid]; break; case (count[mapid] == mapjson[mapid].mybest): disptext = "Tied personal best of "+count[mapid]; break; case (count[mapid] < mapjson[mapid].mybest): disptext = "You got "+count[mapid]+". Your best is "+mapjson[mapid].mybest; break; } //if anything worth mentioning happend let them know. if (disptext != "") { if (checkSound(mapid) && improvedScore) { soundManager.setVolume('charm', 50); soundManager.setVolume('sc', 50); soundManager.play('charm'); soundManager.play('sc'); } updateDsp(mapid, 'dspID', disptext); flashelement(mapid+',dspID', 8, "#FF3377"); } //This is the end, lets reset stuff to defaults. count[mapid] = 0; mapdata[mapid].pathColor[pathNumber] = '#ffffff'; //Bring the color back to our checkpoints/teleports. var eid; for(var i in mapdata[mapid].usedTiles) { //eval(mapdata[mapid].restoreTiles[i]); //setTimeout((mapdata[mapid].restoreTiles[i]), 2000); eid = mapdata[mapid].usedTiles[i]; setTimeout("document.getElementById('"+eid+"').style.backgroundColor = '';", 2500); setTimeout("document.getElementById('"+eid+"').pressed = false;" , 2500); } //Clear mapdata[mapid].usedTiles = new Array(); //We're done, animatePathDone(mapid); return; } //The next tile exists, how fast should we get there? rs = 84; //How fast should we be going? selectbox = document.getElementById(mapid+',speed'); selected = selectbox.options[selectbox.selectedIndex].value; switch (selected) { case '1': rs =120; break; case '2': rs =84; break; case '3': rs =44; break; case '4': rs =22; break; } //The next path code. switch(t) { //Are we just moving someplace? case '1': x--; break; //1 - Up case '2': y++; break; //2 - Right case '3': x++; break; //3 - Down case '4': y--; break; //4 - Left //Special codes within the path. //Did we aquire a target? //Checkpoint targets: case 'a': case 'b': case 'c': case 'd': case 'e': case 'f': rs = rs + 410; mapdata[mapid].pathColor[pathNumber] = targetColor(t); break; //Hey, we've ran into a teleport. case 'u': //tp1 case 'n': //tp2 case 'h': //tp3 case 'j': //tp4 case 'l': //tp5 //Get teleport coords tmp = p.split(t); loc = tmp[1].split(','); y = loc[0]; x = loc[1]; //Flash teleport-out //Teleport Element ID tpEid = mapid+','+x+','+y; if (checkSound(mapid)) { soundManager.setVolume('ufoblip', 30); if (pathNumber == 0) soundManager.setPan('ufoblip', 70); else soundManager.setPan('ufoblip', -70); soundManager.play('ufoblip'); } document.getElementById(tpEid).style.backgroundColor=''; flashelement(tpEid, 8, mapdata[mapid].pathColor[pathNumber]); //The path once teleported - and an r to indicate to gray the teleport-out too. p = 'q'+tmp[2]; //Slow down rs = rs + 1200; break; } //Remove move from p p = p.substring(1); //rs = (10 * p.length) + 40; // if (mapdata[mapid].moveCount[1] < mapdata[mapid].moveCount[pathNumber] - 2 // || mapdata[mapid].moveCount[0] < mapdata[mapid].moveCount[pathNumber] - 2) // rs = rs + 100; setTimeout("doanimate("+x+","+y+",'"+p+"','"+t+"','"+mapid+"','"+pathNumber+"')",rs); } function targetColor(target) { var r = '#ccc'; switch(target) { case 'a': r = '#F777FF'; break; case 'b': r = '#FFFF11'; break; case 'c': r = '#FF4466'; break; case 'd': r = '#ff9911'; break; case 'e': r = '#00FFFF'; break; case 'f': r = '#ccc'; } return r; } function flashelement(eid, times, color, speed) { if (document.getElementById(eid) == undefined) return; if (!color) { color = "#FFFF44"; } if (!speed) { speed = 220; } speedon = speed * .5; //document.getElementById(eid).setAttribute('class', 'no_transition'); var currentclass = document.getElementById(eid).className; if (document.getElementById(eid).classOrigName != undefined) currentclass = document.getElementById(eid).classOrigName; var currentColor = document.getElementById(eid).style.backgroundColor; document.getElementById(eid).className='no_transition '+currentclass; document.getElementById(eid).style.backgroundColor = '#000000'; for (var i=0; i