var debug=1;
var wiki=0; 
try{
  if (typeof wgPageName !='undefined')
    wiki=1;
}catch(e){
  wiki=0;
}

var uid = readCookie('uid');
if (!uid) {
  uid = Math.random()*1E9;
  createCookie('uid',uid);
}

function createCookie(name,value) {
	days = 365;
	var date = new Date();
	date.setTime(date.getTime()+(days*24*60*60*1000));
	var expires = "; expires="+date.toGMTString();
	document.cookie = name+"="+value+expires+"; path=/";
}

function readCookie(name) {
	var nameEQ = name + "=";
	var ca = document.cookie.split(';');
	for(var i=0;i < ca.length;i++) {
		var c = ca[i];
		while (c.charAt(0)==' ') c = c.substring(1,c.length);
		if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length);
	}
	return null;
}

function eraseCookie(name) {
	createCookie(name,"",-1);
}

function flip(id){
//Used by the hint tags - hide or show the hint
document.getElementById(id).style.display =
  (document.getElementById(id).style.display=="none")?"block":"none";
}
function flipSize(id){
  var blurb = document.forms[id];
  while (blurb && blurb.className != 'usercontrols') blurb=blurb.parentNode;
  blurb = blurb.previousSibling;
  while (blurb && blurb.nodeName != 'DIV')
    blurb=blurb.previousSibling;
  if (document.forms[id].elements['c'].className=='biggerTextarea'){
    document.forms[id].elements['c'].className='nix';
    blurb.className='blurb';
  }else{
    document.forms[id].elements['c'].className='biggerTextarea';
    blurb.className='nix';
  }
}

function getProg(gForm,fForm){
  var prog;
  if (fForm.elements['shell'])
    prog = fForm.elements['shell'].value;
  if (!prog && document.forms['shell'])
      prog = unescape(document.forms['shell']['import'].value);
  if (!prog) prog = 'QcQ';
  //prog = decodeURIComponent(prog);
  if (gForm.elements['width'])
    prog = prog.replace(/QwidthQ/g,gForm.elements['width'].value);
  if (gForm.elements['height'])
    prog = prog.replace(/QheightQ/g,gForm.elements['height'].value);
  if (gForm.elements['frames'])
    prog = prog.replace(/QframesQ/g,gForm.elements['frames'].value);
  if (navigator && navigator.appName=="Microsoft Internet Explorer")
    prog = prog.replace(/\r/g,'').
           split(String.fromCharCode(10)).join("\n\r");
  prog = prog.replace(/QcQ/g,fForm.elements['c'].value);
  return prog;
}

function flipWhole(t,lang){
  var wc = document.getElementById('sw'+t+"."+lang);
  var g = "g"+lang+t; var f = "f"+lang+t;
  if (wc.style.display != "block"){
    wc.removeChild(wc.firstChild);
    var prog = getProg(document.forms[g],document.forms[f]);
    prog = prog.replace(/Q[()]Q/g,"");
//    var txt = document.forms[f].shell.value || 'QcQ';
//    txt = unescape(txt.replace(/%0A/g,'%0D%0A'));
//    if (document.forms[f].c)
//        txt = txt.replace("QcQ",document.forms[f].c.value);
//    if (document.forms[g].width)
//        txt = txt.replace("QwidthQ",document.forms[g].width.value);
//    if (document.forms[g].height)
//        txt = txt.replace("QheightQ",document.forms[g].height.value);

    wc.appendChild(document.createTextNode(prog));
    wc.style.display = 'block';
  } else{
    wc.style.display = 'none';
  }
}
//var httpRequest;
var rememberProg = {};

function goBaby(n,lang){
// n identifies the form pair
  //if (undefined == lang || !lang) lang = 'java';
  var g = "g"+lang+n; var f = "f"+lang+n;
  var gForm = document.forms[g];
  var fForm = document.forms[f];
  var preMix = document.getElementById('pre'+lang+n);
         //getPreMix(fForm,'pre'+lang+n);
  if (preMix){
    var execRecord = extractValue(preMix);
    fForm.c.value = execRecord.run;
    if (!fForm.record){
      fForm.appendChild(nn('input',{type:'hidden',name:'record'}));
    }
    if (fForm.record) fForm.record.value = execRecord.record;
  }
  if (fForm.c.value.match(/^\s*$/)){
    alert("No code found.\n"+
          "Type your program into the white box to see it run.");
    return;
  }
  if (gForm.answer)
    gForm.answer.value
      = fForm.answer.value;
  if (gForm.shell){
    gForm.shell.value
      = document.forms[f].shell.value;
    if (!gForm.shell.value && document.forms['shell']){
      if (document.forms['shell'].elements['import'])  //TODO
         gForm.shell.value =
           unescape(document.forms['shell'].elements['import'].value);
    }
    if (!gForm.shell.value) gForm.shell.value = 'QcQ';
  }
  if ((fForm.shell &&
       fForm.shell.value)||
      (gForm.shell && gForm.shell.value)){
    gForm.prog.value
      = document.forms[f].c.value;
    gForm.c.value = '';
  }else{
    gForm.c.value
      = document.forms[f].c.value
  }
  //set up AJAX request
  //var url = 'http://progzoo.net/s.cgi';
  var url = document.forms[g].action;
//  if (debug && wgUserName=='Andr3w')
//    url = 'http://progzoo.net/s.cgi';
  var oParams = {};
  
  oParams.uid=uid;
  oParams.file=gForm.elements['className'].value;
  if (gForm.elements['classpath'] && gForm.elements['classpath'].value)
    oParams.classpath=gForm.elements['classpath'].value;
  oParams.lang=lang;
  if (wiki){
    oParams.tut=wgPageName;
    oParams.wgUserName =wgUserName;
    oParams.wgCurRevisionId=wgCurRevisionId;
  }else
    oParams.tut=gForm.elements['tut'].value;
  oParams.version = (wiki)?wgCurRevisionId:gForm.elements['lstat'].value;
  oParams.quest=gForm.elements['quest'].value;
  if (fForm.c.value==gForm.elements['deftxt'].value)
    oParams.virgin=1;
  var prog = (gForm.elements['shell'])?gForm.elements['shell'].value:'QcQ';
  if (!prog) prog="QcQ";
  if (gForm.elements['width'])
    prog = prog.replace(/QwidthQ/g,gForm.elements['width'].value);
  if (gForm.elements['height'])
    prog = prog.replace(/QheightQ/g,gForm.elements['height'].value);
  if (gForm.elements['frames'])
    prog = prog.replace(/QframesQ/g,gForm.elements['frames'].value);
  if (gForm.elements['answer'].value){
    var answer = prog;
    answer = answer.replace(/QcQ/g,fForm.elements['answer'].value);
    oParams.answer=answer;
  }
  if (gForm.elements['prog']){
    prog = prog.replace(/QcQ/g,gForm.elements['prog'].value);
    oParams.frag=(fForm.record)?fForm.record.value
                               :gForm.elements['prog'].value;
  }
  oParams.prog=prog;
  if (gForm.elements['switches'])
    oParams.switches=gForm.elements['switches'].value;
  if (gForm.elements['imgOut'])
    oParams.imgOut=gForm.elements['imgOut'].value;
  if (gForm.elements['copyFile'])
    oParams.copy=gForm.elements['copyFile'].value;
//  if (fForm.record && fForm.record.value)
//    oParams.record=fForm.record.value;
  oParams.gimmeTicket=Math.random();
  var cParams = '';
  for (var i in oParams)
    cParams += i+"="+encodeURIComponent(oParams[i])+"&";

  rememberProg[lang+n] = oParams;

  var httpRequest = mkNewHttpRequest();
  if (!httpRequest) {
    alert('Cannot create an XMLHTTP instance');
    return false;
  }else{
   var tmsg = document.getElementById('tgtmsg_'+lang+n);
   var tend = document.getElementById('tgtend_'+lang+n);
   var tres = document.getElementById('tgtres_'+lang+n);
   var tgt = document.getElementById('tgt_'+lang+n);
   tmsg.innerHTML = "Loading...";
   tgt.style.display = 'block';
   tres.style.height = '5ex';
   tres.style.visibility = 'hidden';
   tres.style.marginBottom = '3ex';
   tres.style.marginRight = '2ex';
   //if (tend.scrollIntoView)
   //  tend.scrollIntoView(false);
  }
/*  new Ajax.Request(url,
    {onsuccess:function() { alertContents(httpRequest,n,lang); }
    ,postBody:cParams
    ,method:'POST'
    ,aysnchronous:true
    });
*/
  httpRequest.open('POST', url, true);
  httpRequest.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
  httpRequest.setRequestHeader("Content-length", cParams.length);
  httpRequest.setRequestHeader("Connection", "close");
  httpRequest.onreadystatechange = function() { alertContents(httpRequest,n,lang); };
  httpRequest.send(cParams);
}

function makeCall(ticket,n,lang,msg){
  var tmsg = document.getElementById('tgtmsg_'+lang+n);
  var url = document.forms['g'+lang+n].action;
//  if (debug && wgUserName=='Andr3w')
//    url = 'http://progzoo.net/s.cgi';
  var httpRequest = mkNewHttpRequest();
  httpRequest.onreadystatechange = function() {
    alertContents(httpRequest,n,lang); };
  httpRequest.open('POST', url, true);
  httpRequest.setRequestHeader('Content-Type',
                               'application/x-www-form-urlencoded');
  httpRequest.send('lang='+lang+'&ticket='+ticket+'&rnd='+Math.random());
  tmsg.innerHTML = msg||'Loading (checking queue)...';
}

function alertContents(httpRequest,n,lang,dbg) {
  if (httpRequest.readyState == 4) {
    if (httpRequest.status == 200) {
      var txt = httpRequest.responseText;
      if (!txt) {
        alert("The server responded with nothing!");
        return;
      }
      var r;
      try{
        r = eval("("+txt+")");
      }catch (e){
        alert("Corruption at the server. Please visit http://progzoo.net/wiki/Panic.\n"+txt);
        return;
      }
      var tgt = document.getElementById('tgt_'+lang+n);
      var tmsg = document.getElementById('tgtmsg_'+lang+n);
      var tque = document.getElementById('tgtque_'+lang+n);
      var tres = document.getElementById('tgtres_'+lang+n);
      var tend = document.getElementById('tgtend_'+lang+n);
      removeChildren(tmsg);
      removeChildren(tres);
      tres.style.visibility = 'visible';
      var usrBox;
      var ansBox;
      if (r.usrImg) usrBox = nn('img',{src:r.usrImg,
                                       style:'border:solid 1px gray'},[]);
      if (r.usrTxt!=undefined)
        usrBox = nn('pre',{style:'border-style:solid;padding:0.5em;'+
                           'height:'+boxHeight(r.usrTxt)+';overflow:auto'},
                fixLineEnds(r.usrTxt.toString()));
      if (document.forms['g'+lang+n].htmlOut){
        var tmp = document.createElement('span');
        tmp.innerHTML = r.usrTxt;
        usrBox = tmp;
      }
      if (r.ansImg) ansBox = nn('img',{src:r.ansImg,
                                       style:'border:solid 1px gray'},[]);
      if (r.ansTxt){
        ansBox = nn('pre',{style:'border-style:solid;padding:0.5em;'+
                           'height:'+boxHeight(r.ansTxt)+';overflow:auto'},
                    fixLineEnds(r.ansTxt.toString()));
        if (document.forms['g'+lang+n].htmlOut){
          var tmp = document.createElement('span');
          tmp.innerHTML = r.ansTxt;
          ansBox = tmp;
        }
      }
      if (r.queue){
        var status = jobStatus(r.queue,r.ticket);
        if (status=='lost'){
          tmsg.innerHTML = 'Unfortunately your program has been lost. Sorry about that. Your ticket was:'+r.ticket;
          return;
        }
        if (status=="running"){ //Call back immediately
          tmsg.innerHTML = "Your program is running...";
          if (prevQ && prevQ['me']) renderQueue(tque,r.queue,r.ticket);
          makeCall(r.ticket,n,lang,"Your program is running...");
          return;
        }
        tmsg.innerHTML = "You are in a queue.";
        renderQueue(tque,r.queue,r.ticket);
        setTimeout("makeCall("+r.ticket+","+n+",'"+lang+"')",3000);
        return;
      }else{
        renderQueue(tque,[]);
      }
      if (r.error){
        var msg;
        if (r.error == 'compile time'){
          msg="Your program did not compile.";
          msg='';
        }else if (r.error == 'run time')
          msg = "Your program compiled but then had an error.";
        var piii = nn('div', {},["AWH"]);
        var pre = nn('pre',
                     {style:'border:solid;padding:.5em'},
                     fixLineEnds(r.errorMsg));
        var hi = hiLightProg(rememberProg[lang+n],r);
        if (r.error=='server') {
          hi = nn('div',{},[]);
          hi.innerHTML = r.page;
        }
        tres.appendChild(nn('div',{},
          [nn('div',{},[pre])
          ,nn('div',{},[hi])
          ]));
      }else{
        if (r.score) showScore(lang,{qNum:n,bst:r.score});
        if (r.score == 100){
          tres.appendChild(nn('div',{'class':'score'},["Well Done! 100%"]));
          tres.appendChild(usrBox);
        }
        if (r.score && r.score!=100){
          //var msg = "Your score is "+Math.floor(r.score)+"%";
          var msg = nn('div',{'class':'score'},
                     ["Your score is "+Math.floor(r.score)+"%"]);
          tres.appendChild(msg);
        }
        if (r.score >= 98){
          var rnd=Math.floor(1000000*Math.random());
          var model = nn('pre',
           {id:'model'+rnd,style:'display:none;border-style:solid;padding:1ex'},
           [document.forms['g'+lang+n].answer.value ]);
          var button = nn('input',{type:'button',
                 value:'View model answer',
                 onclick:function () {flip("model"+rnd);}},[]);
          if (button.addEventListener)
           button.addEventListener('click',function(e){flip("model"+rnd)},true);
          else
           button.onclick = new Function("flip('model"+rnd+"')");
          tres.appendChild(button);
          tres.appendChild(model);
        }
        if (usrBox && ansBox && r.score!=100){
          tres.appendChild(nn('table',{},[
                  nn('tbody',{},[
                   nn('tr',{},[//nn('td',{rowspan:2},[msg,button,model]),
                               nn('td',{style:'background:white;'},[" Your answer."]),
                               nn('td',{style:'background:white;'},[" The right answer."])]),
                   nn('tr',{},[
                    nn('td',{valign:'top'},[usrBox]),
                    nn('td',{valign:'top'},[ansBox])])])]));
        }
        if (usrBox && !ansBox){
          tres.appendChild(nn('table',{},[
                  nn('tbody',{},[
                   nn('tr',{},[nn('td',{style:'background:white'},[" Your answer."])]),
                   nn('tr',{},[nn('td',{valign:'top'},[usrBox])
                     ])])]));
        }
      }
      if (r.processedBy){
        var server = r.processedBy.replace(/http:\/\//,'')
                                  .replace(/\/.*$/,'');
        var tickit = r.processedBy.replace(/\?/,'');
        tres.appendChild(nn('div',{style:'float:right'},
          ['Processed by: '+ r.processedBy]));
      }
      tres.style.height = '';
      //Effect.Appear(tres);
      
    } else {
      alert('There was a problem with the request. Status Code: '+httpRequest.status);
    }
  }
}

function jobStatus(queue,ticket){
  for(var i=0;i<queue.length;i++)
    if (queue[i].ticket==ticket)
      return (queue[i].isRunner)?'running':'waiting';
  return 'lost';
}

function hiLightProg(oProg,oErr){
  var el = {};
  if (oErr.errorLine)
    for (var i=0;i<oErr.errorLine.length;i++)
      el[oErr.errorLine[i]]=1;
  var a = oProg.prog.split("\n");
  var r = new Array();
  r[0] = "";
  for (var i=0;i<a.length;i++){
    var l = ("   "+(i+1)).substr(-3)+" "+a[i]+"\n";
    if (!el[i+1])
      r[r.length-1] += l;
    else{
      r.push(nn('span',{style:'color:black;background-color:gray;'},[l]));
      r.push("");
    }
  }
  return nn('pre',{style:'border-style:solid;line-height:110%'},r);
}

function boxHeight(txt){
//Reurn height of the result box in css units
//Make the maximum about 30 lines
  var n = (txt+'').split("\n").length;
  n = Math.ceil(n*1.2+2);
  n = Math.min(n,30);
  return n+'em';
}

function fixLineEnds(t){
  var l = t.split(/\n/);
  if (l.length==0) return [];
  var m = [l[0]];
  for (var i=1;i<l.length;i++)
    m.push(document.createElement("br"),
        document.createTextNode(l[i]));
  return m;
}

function removeChildren(n){
  while (n.hasChildNodes())
    n.removeChild(n.firstChild);
}

var prevQ = new Object();

function renderQueue(e,q,me){
  var thisQ = new Object();
  for (var i=0;i<q.length;i++){
    var item = {'q':q[i],'wannaBeX':(i*30+40)};
    if (prevQ[q[i].ticket]){
      item.startAtX = prevQ[q[i].ticket].wannaBeX;
      item.img = prevQ[q[i].ticket].img;
    }else{
      item.startAtX = item.wannaBeX;
      item.img = nn("img",{'src':q[i].uimg,
             'style':'position:absolute;left:'+item.startAtX+'px'});
      e.appendChild(item.img);
      e.appendChild(document.createTextNode(' '));
    }
    if (q[i].isRunner)
      item.img.style.border = 'solid thin blue';
    thisQ[q[i].ticket] = item;
    if (q[i].ticket==me){
      var me = {'me':1,'wannaBeX':(i*30+40)};
      if (prevQ['me']){
        me.startAtX = prevQ['me'].wannaBeX;
        me.img = prevQ['me'].img
      }else{
        me.startAtX = item.wannaBeX;
        me.img = nn("img",{'src':'/youarehere.gif',
             'style':'position:absolute;left:'+item.startAtX+'px'});
        e.appendChild(me.img);
      }
      thisQ['me'] = me;
    }
  }
  for (var i in prevQ)
    if (!thisQ[i]){
      var e = prevQ[i].img;
      e.parentNode.removeChild(e);
    }
  prevQ = thisQ;
  kickOffAnimation(prevQ);
}

var startTime;
function kickOffAnimation(q){
  startTime = (new Date()).getTime();
  endTime = startTime + 1000;
  setTimeout('goAni()',100);
}

function goAni(){
  var nw = (new Date()).getTime();
  progress = (nw-startTime)/(endTime-startTime);
  progress = Math.min(1,progress);
  for (var i in prevQ){
    var left = Math.floor(prevQ[i].startAtX*(1-progress)+
                            prevQ[i].wannaBeX*progress);
    if (prevQ[i].img)
      prevQ[i].img.style.left = left+'px';
  }
  if (progress<1)
    setTimeout('goAni()',100);
}

function nn(tagName,atts,content){
  var n = document.createElement(tagName);
  if (atts)
    for (var a in atts)
      if (a=='style'){
        var s=atts[a].split(/;/);
        for (var i=0;i<s.length;i++){
          var kv = s[i].split(/:/);
          var wrds = kv[0].split('-');
          if (wrds.length>1){
            kv[0]=wrds[0];
            for (var j=1;j<wrds.length;j++){
              kv[0] += wrds[j].substr(0,1).toUpperCase()+wrds[j].substring(1);
            }
          }
          n.style[kv[0]]=kv[1];
        }
      }else
        n.setAttribute(a,atts[a]);
  if (content)
    for (var i=0;i<content.length;i++)
      if (typeof content[i] == 'string')
        n.appendChild(document.createTextNode(content[i]));
      else
        n.appendChild(content[i]);
  return n;
}

function resetBaby(n,lang){
// n identifies the form pair
  var g = "g"+lang+n; var f = "f"+lang+n;
  document.forms[f].reset();
  document.forms[g].reset();
}
function setIt(id,v){
if (!wiki) v = unescape(v);
v=v.replace(/^\s+/,'');
document.forms[id].c.value = v;
}
function resetForm(lang,num){
var v=document.forms['g'+lang+num].deftxt.value;
v=v.replace(/^\s+/,'');
document.forms['f'+lang+num].c.value = v;
redoForms(lang);
}

function fliptip(lang,langs){
  for (var l in langs){
    var q=1;
    var dl=document.getElementById(langs[l]+".1");
    while (dl && dl.style){
      dl.style.display = (langs[l]==lang)?"block":"none";
      var r = document.getElementById("tgt_"+langs[l]+q);
      if (r && r.style) r.style.display = (langs[l]==lang)?"block":"none";
      q++;
      var dl=document.getElementById(langs[l]+"."+q);
    }
    var t=document.getElementById("tab"+langs[l]);
    if (t) t.className = (langs[l]==lang)?"current":"tabunselected";
  }
}

function mkNewHttpRequest(){
  var httpRequest;
  if (window.XMLHttpRequest) { // Mozilla, Safari, ...
    httpRequest = new XMLHttpRequest();
    //  if (httpRequest.overrideMimeType)
    //      httpRequest.overrideMimeType('text/xml');
  } else if (window.ActiveXObject) { // IE
    try {
      httpRequest = new ActiveXObject("Msxml2.XMLHTTP");
    } catch (e) {
      try {
        httpRequest = new ActiveXObject("Microsoft.XMLHTTP");
      } catch (e) {}
    }
  }
  return httpRequest;
}

function pzOnLoad(){
  if (wiki)
    wikiPreFill();
}

if (window.addEventListener) {
        window.addEventListener("load", pzOnLoad, false);
}
else if (window.attachEvent) {
        window.attachEvent("onload", pzOnLoad);
}

function setText(n,t){
if (!n) return;
while (n.firstChild) n.removeChild(n.firstChild);
var sp = nn('span');
sp.innerHTML = t;
n.appendChild(sp);
}

var prefixToLang = {'C#':'cs','C++':'cpp','perl':'pl','PHP':'php','Python':'py','Ruby':'rb',
                    'VB':'vb'};

function getFirstLang(){
  for (var i=0;i<document.forms.length;i++){
    var f = document.forms[i];
    if (f.lang)
      return f.lang.value;
  }
  if (wgCanonicalNamespace && prefixToLang[wgCanonicalNamespace])
    return prefixToLang[wgCanonicalNamespace];
  return 'java';
}

function getHardness(d){
  if (d && d.attempt && d.attempt>10)
    return "<span title='" + d.success + "/" + d.attempt + " successful attempts "  + "'>"+
        "Difficulty: <b>"+
        ("*****".substring(0,1-Math.round(-4*(d.attempt-d.success)/d.attempt)))+
        "<span style='color:rgb(192,192,192)'>"+
        ("*****".substring(0,4+Math.round(-4*(d.attempt-d.success)/d.attempt)))+
        "</span></b></span>";
  else
    return '';
}

function showScore(lang,ri,difficulty){
  var f = document.forms["f"+lang+ri.qNum];
  if (!f.answer || !f.answer.value)
    return;
  var hs  = document.getElementById('hiscore'+lang+'_'+ri.qNum);
  var currentScore = (hs)?hs.nodeValue||hs.textContent:0;
  if (currentScore)
    currentScore = currentScore.replace(/[^\d]*([\d]+).*/,"$1");
  currentScore *= 1;
  if (currentScore>ri.bst) ri.bst = currentScore;
  var hs_ = document.getElementById('hiscore'+lang+'_'+ri.qNum+"_");
  var txt = " High score: "+Math.floor(ri.bst)+"% "+
                   ((ri.bst==100)
                           ?String.fromCharCode(10004)
                           :String.fromCharCode(10007));
  var diff = (difficulty)?getHardness(difficulty[ri.qNum])
             :'';
  setText(hs ,txt + " " + diff);
  setText(hs_,txt);
  if (hs) hs.style.display  = ri.bst?'inline':'none';
  if (hs_) hs_.style.display = ri.bst?'inline':'none';
}

function redoForms(lang){
  for (var i=1;document.forms['f'+lang+i];i++){
    var f = document.forms['f'+lang+i];
    if (f.c){
      var oldNode = document.getElementById('pre'+lang+i);
      if (oldNode) oldNode.parentNode.removeChild(oldNode);
      var s = (f.c.firstChild)?f.c.firstChild.nodeValue:'';
      var re =  /Q\(Q(.*?)Q\)Q/gim;
      var found = re.exec(s);
      if (!found) continue;
      var lst = [];
      var prev = 0;
      while (found){
        lst.push(document.createTextNode(s.substring(prev,found.index)));
        var inp = nn("input",{value:found[1],size:found[1].length+3
         ,style:'border-width:2px 2px 2px 2px;'
               +'border-color:black;background-color:white;padding:0px 8px'
           });
        lst.push(inp);
        prev = re.lastIndex;
        found = re.exec(s);
      }
      lst.push(document.createTextNode(s.substring(prev)));
      var ne = nn("pre",{style:'background-color:rgb(200,200,230)',
                  id:'pre'+lang+i});
      for (var j=0;j<lst.length;j++)
        ne.appendChild(lst[j]);
      f.c.parentNode.appendChild(ne);
      f.c.style.display = 'none';
    }
  }
}

function getPreMix(f,id){
  var r;
  for (var c=f.firstChild;c;c=c.nextSibling)
    if (c.getAttribute('id')==id)
      return c;
}

function extractValue(e){
  var s='';
  var t='';
  for (var c=e.firstChild;c;c=c.nextSibling){
    s += (c.nodeName=='INPUT')?c.value:c.nodeValue;
    t += (c.nodeName=='INPUT')?('Q(Q'+c.value+'Q)Q'):c.nodeValue;
  }
  return {run:s,record:t};
}

function grayForms(lang,gray){
  for (var i=1;document.forms['f'+lang+i];i++){
    var f = document.forms['f'+lang+i];
    if (f.c){
      f.c.style.color = gray?'gray':'black';
      f.c.style.cursor = gray?'wait':'auto';
    }
  }
}

function wikiPreFill(){
  var lang=getFirstLang();
  grayForms(lang,1);
  //redoForms(lang);
  //wpfRe.onreadystatechange = function() {
  var orsc = function(transport) {
      var txt = transport.responseText;
      var r;
      if (!txt) return;
      //try{
        r = eval("("+txt+")");
      //}catch(e){
      //  alert("Bad response from server: "+txt.substring(txt.length-100));
      //}
      for (var i in r){
        if (i=='progress'){
          showDice(r[i]);
          continue;
        }
        if (r[i].qNum &&
            document.forms["f"+lang+r[i].qNum] &&
            document.forms["f"+lang+r[i].qNum].c){
          showScore(lang,r[i],r.difficulty);
          document.forms["f"+lang+r[i].qNum].c.value = r[i].txt;
        }
      }
      redoForms(lang);
    };
  var tList = document.getElementsByTagName("div");
  //sList is the list of related tutorials. We want to show the progress
  var sList = new Array();
  for (var i=0;i!=tList.length;i++)
    if (tList[i].className=="tutlist"){
      var dList = tList[i].getElementsByTagName("a");
      var xList = tList[i].getElementsByTagName("strong"); 
      for (var j=0;j<dList.length+xList.length;j++){
        var elem = (j<dList.length)?dList[j]
                                    :xList[j-dList.length];
        var href = elem.getAttribute('href')?decodeURIComponent(elem.getAttribute('href'))
                                            :wgPageName;
        if (href.indexOf("/")>=0)
          href = href.substring(1+href.lastIndexOf('/'));
        var p = elem.parentNode;
        p.removeChild(elem);
        var progressBoxList = (p.className == 'fc')?[]:
              [nn('div',{style:'width:24px;height:6px;padding:0px;'+
                                  'background-color:black;font-size:6pt;'+
                                  'border:white solid 1px', 'id':href,
                            title:'You have completed none of these questions.'},[]
                             )];
        //alert(p.getAttribute('class'));
        p.appendChild(
          nn("table",{width:'100%',style:'background-color:transparent'},
              [nn("tbody",{},[nn("tr",{},
               [nn("td",{style:'border-style:none;padding:0px'},[elem]),
                nn("td",{style:'border-style:none;padding:0px;'+
                               'align:right;width:30px'},progressBoxList
                    )])])]));
        if (href.indexOf('action=edit')==-1)
          sList.push(href);
      }
    }
  var params = 'page='+encodeURIComponent(wgPageName)+'&uid='+uid+'&lang='+lang+
             '&wgUserName='+encodeURIComponent(wgUserName)+
             '&progress='+sList.join(' ')+ //uriEncoding has already happened
             '&rnd='+Math.random();
  var httpRequest = mkNewHttpRequest();
  httpRequest.onreadystatechange = function() {
      if (httpRequest.readyState==4){
        if (httpRequest.status==200)
          orsc(httpRequest)
        grayForms(lang,0);
      }
    };
  httpRequest.open('POST', '/w/extensions/getAttempts.cgi', true);
  httpRequest.setRequestHeader('Content-Type',
                               'application/x-www-form-urlencoded');
  httpRequest.send(params);
/*
  httpRequest.send('page='+wgPageName+'&uid='+uid+'&lang='+lang+
                   '&progress='+sList.join(',')+'&rnd='+Math.random());
  new Ajax.Request('/w/extensions/getAttempts.cgi',{
           method:'post',
           onSuccess:onreadystatechange,
           onComplete:function(){
               grayForms(lang,0);
           },
           parameters:{'page':wgPageName,'uid':uid,'lang':lang
                      ,'wgUserName':wgUserName
                      ,'progress':sList.join(',')
                      ,'rnd':Math.random()
           }
         });
*/
}

function showDice(h){ //TODO The bar for the current page does not come through
  var iList = document.getElementsByTagName('div');
  var s = 'x';
  for (var i=0;i!=iList.length;i++){
    var id = iList[i].getAttribute('id');
    var did = decodeURIComponent(id);
    if (h && h[did]){
      s+=did+", ";
      var e =  iList[i];
      if (!h[did]['count']) h[did]['count'] = 0;
//      while (iList[i].firstChild) iList[i].removeChild(iList[i].firstChild);
//      iList[i].appendChild(document.createTextNode(h[id]['count']+'of'+h[id]['max']));
      var x = h[did]['count']*24/h[did]['max'];
      e.title='You have completed '+h[did]['count']+
                     ' of the '+h[did]['max']+' questions in this tutorial.';
      try {
        var ax = x+1;
        e.style.borderLeftWidth = ax+"px";
        e.style.width = (24-x)+"px";
      } catch (e) {
        alert('exception: '+e);
      }
    }
  }
}

function maxLen(la){
  var r=0;
  for (var i=0;i<la.length;i++)
    r=Math.max(r,la[i].length);
  return r;
}

function resizeTA(n,lang){
  var c = document.forms['f'+lang+n].c;
  var la = c.value.split('\n');
  var rows = la.length;
  var cols = maxLen(la);
  c.rows = rows+2;
  c.cols = cols+2;
}

function doAll(){
  var i =1;
  while (document.forms['fjava'+i]){
    var f=document.forms['fjava'+i].c.value += "//"+Math.random()+"\n";
    setTimeout('goBaby('+i+',"java")',3000*Math.random());
    i++;
  }
}

function openHistory(n,lang){
  window.open('http://progzoo.net/manage.pl?tut=' + wgPageName+
              '&quest='+n+'&lang='+lang,
  'history');
}

function openProfile(n,lang){
  window.open('http://progzoo.net/manage.pl?profile=' + encodeURIComponent(wgPageName)+
              '&quest='+n+'&lang='+lang,
  'history');
}

