
var searchLayer;
var searchLayerOrder = new Array();
var searchLayerState = new Object();
var searchLayerLabels = new Object();
var searchData = new Object();
var searchTemplates = new Object();
var searchAJAXInProgress = 0;
var searchResultsShown = 0;
var searchAJAXKeywords = '';
var searchAJAXUrl = '/search/ajax.edo';

function searchSwitchLayer(lid)
{
   searchLayer = lid;
   if (!searchLayerLabels[lid])
      searchLayerLabels[lid] = $('#label_'+lid);
   if (searchLayerLabels[lid])
      searchLayerLabels[lid].click();
   return;
}

/*

Layers have a name ID. This references components in the main document:
   results_ID     - The region to hold the results output
   label_ID       - The region/link holding the title for the search category
   matches_ID     - The region to hold the number of matches (or an indication of searching)

There are also some special IDs:
   default        - The results_default region is visible by default, typically stating "search in progress"
   none           - The results_none region is hidden by default, and shown if NO categories have matches.
   block          - The results_block region is a single container around all results divs.

*/


function searchInitCategory(lid,matches)
{
   var labmatch = $('#matches_'+lid);
   var titleob = $('#label_'+lid);
   if (labmatch)
      labmatch.html('('+matches+')');
   else if (titleob)
      titleob.append('('+matches+')');
   if (!searchLayer)
   {
      searchSwitchLayer(lid);
   }
}

function searchHideCategory(lid)
{
   return;
   var titleob = document.getElementById('label_'+lid);
   if (searchLayer==lid)
      searchLayer=false;
   if (titleob)
   {
      titleob.style.display = 'none';
   }
}

function searchSetTemplate(tmplid,tmpl)
{
   searchTemplates[tmplid] = tmpl;
}

function searchCheckWaitClass()
{
   if (searchAJAXInProgress>0 && searchResultsShown==0)
      $(document.body).addClass("wait")
   else
      $(document.body).removeClass("wait")
}

function searchResizeResults()
{
   // Set a max-height for our Results block to make efficient use of window size.
   var rb = document.getElementById('results_block');
   if (rb)
   {
      var winheight = window.innerHeight || (document.documentElement && document.documentElement.clientHeight);

      var pw = rb;
      var divofs = rb.offsetTop;
      while (pw.offsetParent)
      {
         pw = pw.offsetParent;
         if (pw.offsetTop)
            divofs+=pw.offsetTop;
      }
      //alert(winheight);
      //alert(divofs);
      var maxht = winheight-divofs-25;
      if (maxht<200)
         maxht=200;

      rb.style.maxHeight=maxht+'px';

      if (!window.onresize)
         window.onresize = function() { searchResizeResults() };
   }
}

function searchPageChange(sect,page,filter)
{
   var keywords = searchAJAXKeywords;
   if (!keywords)
      return true;

   searchResultsShown = 0;
   searchAJAXGetResults(sect,keywords,page,filter);
   return false;
}

function searchAJAXMulti(lids,keywords,page,sect)
{
   searchAJAXKeywords = keywords;
   searchLayerOrder=lids;
   if (sect)
   {
      // Shuffle things around so our section is first.
      searchLayerOrder = new Array();
      searchLayerOrder[0] = sect;
      for (var i=0; i<lids.length; i++)
         if (lids[i]!=sect)
            searchLayerOrder.push(lids[i]);
   }
   for (var i=0; i<lids.length; i++)
      searchAJAXGetResults(lids[i],keywords,page);
}

// Look at the search results, and generate HTML for a "see also", for people
// who don't notice the MASSIVE TABS up the top.
function searchSeeAlso(lid)
{
   var salso = new Array();
   for (var i=0; i<searchLayerOrder.length; i++)
   {
      if (searchLayerOrder[i] != lid && searchData[searchLayerOrder[i]] && searchData[searchLayerOrder[i]].matches > 0)
         salso.push('<a href="#" onClick="searchSwitchLayer(\''+searchLayerOrder[i]+'\'); return false;">'+searchData[searchLayerOrder[i]].matches+' results in '+searchData[searchLayerOrder[i]].title+'</a>');
   }
   var salsohtml = '';
   if (salso.length)
      return salso.join(', ');
}

function searchAJAXGetResults(lid,keywords,page,filter)
{
   var url = searchAJAXUrl+'?name='+HTTPescape(lid)+'&keywords='+HTTPescape(keywords)+'&page='+HTTPescape(page)+'&filter='+HTTPescape(filter);

   searchLayerState[lid]='wait';

   searchGetXMLChunk(url, function(req)
   {
      var data = new Object();
      var srchob = req.responseXML.getElementsByTagName('search')[0];

      if (!srchob)
         return; // Error! Just bail for now...

      for (var j=0; j<srchob.childNodes.length;j++)
      {
         var elm = srchob.childNodes[j];
         if (elm.nodeName && elm.nodeName!='#text')
         {
            //alert(elm.nodeName+' = '+searchGetXMLNodeContent(elm));
            data[elm.nodeName] = searchGetXMLNodeContent(elm);
         }
      }

      searchLayerState[lid].matches = data.matches || 0;
      data.keywords = keywords;

      searchData[lid] = data;

      var labmatch = $('#matches_'+lid);
      var resdiv = $('#results_'+lid);
      if (!data.matches || data.matches==0)
      {
         if (labmatch)
            labmatch.html('');
         searchHideCategory(lid);
         searchLayerState[lid] = 'empty';
      }
      else
      {
         // Find our Label
         if (labmatch)
            labmatch.html('('+data.matches+')');
         if (resdiv)
            resdiv.html(searchParseTemplate('match',data));
         searchLayerState[lid] = 'done';
      }

      // Can we reveal one yet?
      for (var i=0; !searchLayer && i<searchLayerOrder.length && searchLayerState[searchLayerOrder[i]]!='wait'; i++)
         if (searchLayerState[searchLayerOrder[i]] == 'done')
            searchSwitchLayer(searchLayerOrder[i]);

      // Are they ALL no matches??
      var nonecount = 0;
      for (var i=0; i<searchLayerOrder.length; i++)
         if (searchLayerState[searchLayerOrder[i]]=='empty')
            nonecount++;
      if (nonecount == searchLayerOrder.length)
         searchSwitchLayer('none');

      // Are they all done?
      if (!searchAJAXInProgress && nonecount!=searchLayerOrder.length)
         for (var i=0; i<searchLayerOrder.length; i++)
            if (searchLayerState[searchLayerOrder[i]] == 'done')
            {
               var resdiv = document.getElementById('seemore_'+searchLayerOrder[i]);
               var seealso = searchSeeAlso(searchLayerOrder[i]);
               if (resdiv && seealso)
               {
		  var OldNode = document.getElementById('seealsospan' + searchLayerOrder[i]);
		  var NewNode=document.createElement('span');
		  
		  // Set id on element so it can be easily replaced
		  // by a new node (rather than continually appending)
		  NewNode.setAttribute('id', 'seealsospan' + searchLayerOrder[i]);
                  NewNode.innerHTML = seealso;
		  
		  OldNode ? resdiv.replaceChild(NewNode,OldNode) : resdiv.appendChild(NewNode);
                  resdiv.style.display = '';
               }
            }
   } );
}

function searchParseTemplate(tmplid,data)
{
   var tmpl = searchTemplates[tmplid] || '<h2>[title]</h2>[results]';

   for (var i in data)
   {
      // alert('Using '+tmpl+', replacing '+i+' with '+data[i]);
      tmpl = tmpl.replace(eval('/\\['+i+'\\]/g'),data[i]);
   }
   return tmpl;
}

function dumpProps(obj, parent) {
   for (var i in obj) {
      if (parent) { msg = parent + "." + i + "\n" + obj[i]; } else { var msg = i + "\n" + obj[
i]; }
      if (!confirm(msg)) { return; }
      if (typeof obj[i] == "object") {
         if (parent) { dumpProps(obj[i], parent + "." + i); } else { dumpProps(obj[i], i); }
      }
   }
}

function searchGetXMLChunk(url,callback)
{
   var httpRequest = NewHTTPRequest();
   if (!httpRequest)
      return false;
   httpRequest.onreadystatechange = function()
   {
      var req = httpRequest;
      //alert('Callback State: '+req.readyState);
      if (req.readyState == 4)
      {
         searchAJAXInProgress--;
         searchCheckWaitClass();
         //alert('Status: '+req.status);
         if (req.status == 200)
         {
            //alert(req.responseText);
//            document.getElementById(container).innerHTML = req.responseText;

            if (callback)
               callback(req);
         }
//              else
//              {
//                 alert('Failed! Oops! ('+req.status+')');
// //                 AJAX_DEBUG('Async failed response:'+HTMLescape(req.responseText));
//              }
      }
   };
   try
   {
      httpRequest.open("GET", url, true);
      //httpRequest.overrideMimeType('text/xml');
      searchAJAXInProgress ++;
      searchCheckWaitClass();
   }
   catch(err)
   {
      //window.clearTimeout(timeout);
      alert('Failed! Oops! ('+(err.message?err.message:'Possible permissions problem? '+url+'?'+data)+')');
   }
   //httpRequest.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
   httpRequest.send(null);
}

function NewHTTPRequest()
{
   if (window.XMLHttpRequest)
   {
      return new XMLHttpRequest();
   }
   else
   if (window.ActiveXObject)
   {
      var xmlhttp=false;
      /*@cc_on @*/
      /*@if (@_jscript_version >= 5)
      // JScript gives us Conditional compilation, we can cope with old IE versions.
      // and security blocked creation of the objects.
      try {
         xmlhttp = new ActiveXObject("Msxml2.XMLHTTP");
      } catch (e) {
      try {
         xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
      } catch (E) {
         xmlhttp = false;
      }
      }
      @end @*/
      return xmlhttp;
   }
}

function HTTPescape(msg)
{
   var escp = escape(msg);
   escp = escp.replace(/\+/g,'%2B');
   escp = escp.replace(/%20/g,'+');
   return escp;
}

function HTMLescape(msg)
{
   var escp = msg;
   escp = escp.replace(/&/g,'&amp;');
   escp = escp.replace(/"/g,'&quot;');
   escp = escp.replace(/\</g,'&lt;');
   escp = escp.replace(/\>/g,'&gt;');
   return escp;
}

function searchGetFromXML(odata,tagid)
{
   if (!odata)
   {
      alert('Oops! Problem getting response. (Is the data XML compliant?)');
      return;
   }
   var out = odata.getElementsByTagName(tagid);
   var outtxt = '';
   for (var i=0; i<out.length;i++)
   {
//      if (out[i].firstChild)
//         outtxt+=out[i].firstChild.nodeValue;
      // Firefox spreads content over multiple child nodes.
      for (var j=0; j<out[i].childNodes.length;j++)
         if (out[i].childNodes[j].nodeValue)
            outtxt+=out[i].childNodes[j].nodeValue;
   }
 //  alert(tagid+': '+outtxt);
   return outtxt;
}

function searchGetXMLNodeContent(obj)
{
   var outtxt = '';
   for (var j=0; j<obj.childNodes.length;j++)
      outtxt+=obj.childNodes[j].nodeValue;
   return outtxt;
}