/*
http://isohunt.com Interface Javascript
by Gary Fung - email: gary{REPLACE_WITH_THE_AT_SIGN}isohunt.com

Feel free to use / mod this to your heart's content,
but keep these lines to acknowledge where this code originated.
Comments, mods or additions you'd like add to this script can be posted here:
http://isohunt.com/forum/viewforum.php?f=1

Tip popup functions adapted from AWStats: http://awstats.sourceforge.net/
*/
var smooth_timer;
function go2(selID, link) {
  var selOBJ = (document.getElementById) ? document.getElementById(selID) : eval("document.all['" + selID + "']");
  window.location=link + selOBJ.options[selOBJ.selectedIndex].value;
}
function toclip(string) { window.clipboardData.setData('Text', string); }
function ShowTip(fArg) {
  var tooltipOBJ = (document.getElementById) ? document.getElementById('ih' + fArg) : eval("document.all['ih" + fArg + "']");
  if (tooltipOBJ != null) {
    var tooltipLft = (document.body.offsetWidth?document.body.offsetWidth:document.body.style.pixelWidth) - (tooltipOBJ.offsetWidth?tooltipOBJ.offsetWidth:(tooltipOBJ.style.pixelWidth?tooltipOBJ.style.pixelWidth:$TOOLTIPWIDTH)) - 5;    var tooltipTop = 10;

    if (navigator.appName == 'Netscape') {
      if (parseFloat(navigator.appVersion) >= 5) tooltipTop = (document.body.scrollTop>=0?document.body.scrollTop+10:event.clientY+10);
      tooltipOBJ.style.left = tooltipLft; tooltipOBJ.style.top = tooltipTop;
    }
    else {
      tooltipLft -= 30;
      tooltipTop = (document.body.scrollTop?document.body.scrollTop:document.body.offsetTop) + event.clientY - (tooltipOBJ.scrollHeight?tooltipOBJ.scrollHeight:tooltipOBJ.style.pixelHeight) - 30;
      if (tooltipTop < (document.body.scrollTop?document.body.scrollTop:document.body.offsetTop) + 10) {
        if (event.clientX > tooltipLft) tooltipTop = (document.body.scrollTop?document.body.scrollTop:document.body.offsetTop) + event.clientY + 30;
        else tooltipTop = (document.body.scrollTop?document.body.scrollTop:document.body.offsetTop) + 10;
      } 
      tooltipOBJ.style.pixelLeft = tooltipLft; tooltipOBJ.style.pixelTop = tooltipTop;
    }
    tooltipOBJ.style.visibility = "visible";
  }
}
function HideTip(fArg) {
  var tooltipOBJ = (document.getElementById) ? document.getElementById('ih' + fArg) : eval("document.all['ih" + fArg + "']");
  if (tooltipOBJ != null) tooltipOBJ.style.visibility = "hidden";
}
function smoothHeight(id, curH, targetH, stepH, mode) {
  diff = targetH - curH;
  if (diff != 0) {
    newH = (diff > 0) ? curH + stepH : curH - stepH;
    ((document.getElementById) ? document.getElementById(id) : eval("document.all['" + id + "']")).style.height = newH + "px";
    if (smooth_timer) window.clearTimeout(smooth_timer);
    smooth_timer = window.setTimeout( "smoothHeight('" + id + "'," + newH + "," + targetH + "," + stepH + ",'" + mode + "')", 16 );
  }
  else if (mode != "o") ((document.getElementById) ? document.getElementById(mode) : eval("document.all['" + mode + "']")).style.display="none";
}
function rowOver(i, nColor) {
  if (!nColor) nColor = "#ECECD9";
  var nameObj = (document.getElementById) ? document.getElementById('name' + i) : eval("document.all['name" + i + "']");
  if (nameObj != null) nameObj.style.background=nColor;
}

function getBrowser(){
var BrowserDetect = {
  init: function () {
    this.browser = this.searchString(this.dataBrowser) || "An unknown browser";
    this.version = this.searchVersion(navigator.userAgent)
            || this.searchVersion(navigator.appVersion)
            || "an unknown version";
    this.OS = this.searchString(this.dataOS) || "an unknown OS";
  },
  searchString: function (data) {
    for (var i=0;i<data.length;i++) {
      var dataString = data[i].string;
      var dataProp = data[i].prop;
      this.versionSearchString = data[i].versionSearch || data[i].identity;
      if (dataString) {
        if (dataString.indexOf(data[i].subString) != -1)
          return data[i].identity;
      }
      else if (dataProp)
      return data[i].identity;
    }
    
    return false;
  },
  searchVersion: function (dataString) {
    var index = dataString.indexOf(this.versionSearchString);
    if (index == -1) return false;
    return parseFloat(dataString.substring(index+this.versionSearchString.length+1));
  },
  dataBrowser: [
          {       string: navigator.userAgent,
                  subString: "OmniWeb",
                  versionSearch: "OmniWeb/",
                  identity: "OmniWeb"
          },
          {
                  string: navigator.vendor,
                  subString: "Apple",
                  identity: "Safari"
          },
          {
                  prop: window.opera,
                  identity: "Opera"
          },
          {
                  string: navigator.vendor,
                  subString: "iCab",
                  identity: "iCab"
          },
          {
                  string: navigator.vendor,
                  subString: "KDE",
                  identity: "Konqueror"
          },
          {
                  string: navigator.userAgent,
                  subString: "Firefox",
                  identity: "Firefox"
          },
          {
                  string: navigator.vendor,
                  subString: "Camino",
                  identity: "Camino"
          },
          {               // for newer Netscapes (6+)
                  string: navigator.userAgent,
                  subString: "Netscape",
                  identity: "Netscape"
          },
          {
                  string: navigator.userAgent,
                  subString: "MSIE",
                  identity: "Explorer",
                  versionSearch: "MSIE"
          },
          {
                  string: navigator.userAgent,
                  subString: "Gecko",
                  identity: "Mozilla",
                  versionSearch: "rv"
          },
          {               // for older Netscapes (4-)
                  string: navigator.userAgent,
                  subString: "Mozilla",
                  identity: "Netscape",
                  versionSearch: "Mozilla"
          }
  ],
  dataOS : [
          {
                  string: navigator.platform,
                  subString: "Win",
                  identity: "Windows"
          },
          {
                  string: navigator.platform,
                  subString: "Mac",
                  identity: "Mac"
          },
          {
                  string: navigator.platform,
                  subString: "Linux",
                  identity: "Linux"
          }
  ]
};
  BrowserDetect.init();
  return BrowserDetect.browser;
}

function rowOut(i, nColor) {
  var trObj = (document.getElementById) ? document.getElementById('ihtr' + i) : eval("document.all['ihtr" + i + "']");
  var nameObj = (document.getElementById) ? document.getElementById('name' + i) : eval("document.all['name" + i + "']");
  if (trObj == null || trObj.style.display=="none") nameObj.style.background=nColor;
}

function servOC(i, href, nColor, triangleID) {
  var trObj = (document.getElementById) ? document.getElementById('ihtr' + i) : eval("document.all['ihtr" + i + "']");
  var nameObj = (document.getElementById) ? document.getElementById('name' + i) : eval("document.all['name" + i + "']");
  var ifObj = (document.getElementById) ? document.getElementById('ihif' + i) : eval("document.all['ihif" + i + "']");

  var ageID = document.getElementById('row_6_' + i);
  var browser = getBrowser(); 

  if (browser == "Firefox" || browser == "Mozilla" || browser == "Netscape" || browser == "Gecko" || browser == "Seamonkey"){
    ageID.addEventListener("click", stopEvent, false);
    trObj.addEventListener("click", stopEvent, false);
    nameObj.addEventListener("click", stopEvent, false);
    nameObj.addEventListener("click", stopEvent, false);
  }
  else {
    window.event.cancelBubble = true;
  }; 
 if (trObj != null) {
    if (trObj.style.display=="none") {
      ifObj.style.height = "0px";
      trObj.style.display="";
      nameObj.style.background="#ECECD9";
      if (browser == "Safari" || browser == "Konquerors"){
         setTimeout("toggleDownUp('triangle_"+i+"','down');",1);
      }   else {
        toggleDownUp('triangle_'+i,'down');
      }
      if (!ifObj.src) ifObj.src = href;
      smoothHeight('ihif' + i, 0, 210, 42, 'o');
    }
    else {     
      nameObj.style.background=nColor;
      smoothHeight('ihif' + i, 210, 0, 42, 'ihtr' + i);
      if (browser == "Safari" || browser == "Konquerors"){
      setTimeout("toggleDownUp('triangle_"+i+"','up');",1);
      } else {
        toggleDownUp('triangle_'+i,'up');
      }
     /* triangleID.setAttribute('src', '/img/serp-toggle-up.gif');*/
    }
  }
}

function toggleDownUp(ele,pos){
var _ele = document.getElementById(ele);
_ele.setAttribute('src', '/img/serp-toggle-'+pos+'.gif');
}

function stopEvent(ev) {
  // this ought to keep t-daddy from getting the click.
  ev.stopPropagation();
//return false;
// alert("event propagation halted.");
//  ev.cancelBubble = true;
}
function trOC(idHL, idOC, idArrow) {
  var trObj = (document.getElementById) ? document.getElementById(idOC) : eval("document.all['" + idOC + "']");
  var hlObj = (document.getElementById) ? document.getElementById(idHL) : eval("document.all['" + idHL + "']");
  var arrowObj = (document.getElementById) ? document.getElementById(idArrow) : eval("document.all['" + idArrow + "']");
  if (trObj != null && hlObj != null) {
    if (trObj.style.display=="none") {
      trObj.style.display="";
      hlObj.style.background="#003366";
      hlObj.style.color="#EDF6F9";
      arrowObj.innerHTML="v";
    }
    else {
      trObj.style.display="none";
      hlObj.style.background="#ECECD9";
      hlObj.style.color="#000000";
      arrowObj.innerHTML="^";
    }
  }
}
function firstFocus()
{
   if (document.forms.length > 0)
   {
      var TForm = document.forms[0];
      for (i=0;i<TForm.length;i++)
      {
         if ((TForm.elements[i].type=="text")||
           (TForm.elements[i].type=="textarea")||
           (TForm.elements[i].type.toString().charAt(0)=="s"))
         {
            document.forms[0].elements[i].focus();
            break;
         }
      }
   }
}
function HighlightAll(theField) {
  var tempval=eval("document."+theField);
  tempval.focus();
  tempval.select();
  if (document.all) {
    therange=tempval.createTextRange();
    therange.execCommand("Copy");
    window.status="Contents highlighted and copied to clipboard!";
    setTimeout("window.status=''",5000);
  }
}
function NewWindow(mypage, myname, w, h, scroll) {
  var winl = (screen.width - w) / 2;
  var wint = (screen.height - h) / 2;
  winprops = 'height='+h+',width='+w+',top='+wint+',left='+winl+',scrollbars='+scroll+',resizable'
  win = window.open(mypage, myname, winprops)
  if (parseInt(navigator.appVersion) >= 4) { win.window.focus(); }
}
startList = function() {
  if (document.all&&document.getElementById) {
    navRoot = document.getElementById("nav");
    for (i=0; i<navRoot.childNodes.length; i++) {
      node = navRoot.childNodes[i];
      if (node.nodeName=="LI") {
        node.onmouseover=function() {
          this.className+=" navOver";
        }
        node.onmouseout=function() {
          this.className=this.className.replace(" navOver", "");
        }
      }
    }
  }
}
function setImageDimensions(gotImage) {
  if(gotImage.width > 600) gotImage.width = 600;
}
function changeImageDimensions(gotImage, type) {
  if(gotImage.width > 600 && type == 'out') {
	  gotImage.width = 600;
    return;
  }
  if(type == 'over') gotImage.removeAttribute('width');
}

function toggleprob(obj) {
  var el = document.getElementById(obj);
  el.style.display = (el.style.display != 'none' ? 'none' : '' );
  el.style.display = '';  
}

function jqtoggle(obj) {
  $(obj).toggle();
}

startTabList = function(tab) {
   if (document.all&&document.getElementById) {
     navRoot = document.getElementById("detailsTabs");
     for (i=0; i<navRoot.childNodes.length; i++) {
		node = navRoot.childNodes[i];
		if (node.nodeName=="LI") {
		  node.onmouseover=function() {
		    this.className+=" detailsTabsOver";
		  }
		  node.onmouseout=function() {
		    this.className=this.className.replace(" detailsTabsOver", "");
		  }
		}
     }
   }
}

startCachedTorrentList = function(tab) {
   if (document.all&&document.getElementById) {
     navRoot = document.getElementById("cached_torrents");
     for (i=0; i<navRoot.childNodes.length; i++) {
		node = navRoot.childNodes[i];
		if (node.nodeName=="LI") {
		  node.onmouseover=function() {
		    this.className+=" navOver";
		  }
		  node.onmouseout=function() {
		    this.className=this.className.replace(" navOver", "");
		  }
		}
     }
   }
}


function cancelReply(reply,current_user_id,btid){
  var replyForm = document.getElementById(reply);
  replyForm.innerHTML = '';
}


function showQuotedReply(comment){
  $.get("/getcomment.php",
  { id: comment },
    function(data){
    $("#reply").val('**Quoting [Comment #'+comment+'](#commentanch_'+comment+')**\n> '+data.replace(/\n/g,"\n> ")+'\n\n');
  }
  );
}

function randomString() {
  var chars = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXTZabcdefghiklmnopqrstuvwxyz";
  var string_length = 8;
  var randomstring = '';
  for (var i=0; i<string_length; i++) {
    var rnum = Math.floor(Math.random() * chars.length);
    randomstring += chars.substring(rnum,rnum+1);
    }
  return randomstring;
}

function toMarkdown(text){
  var converter = new Showdown.converter();
  var html = converter.makeHtml(text);
  return html;
}

function countdown(secs, commentid, hash, classification) {
  countdownele = "#countdown"+commentid;
  $(countdownele).html("<b>You have "+secs+"s to <a href=\"#\" onClick=\"editcomment("+commentid+",'"+hash+"','"+classification+"');return false;\">edit</a> your comment.</b><br><br>");
  secs--;
  if (secs<1) {
    $(countdownele).remove();
    canceleditcomment(commentid)
    } else
  setTimeout("countdown("+secs+","+commentid+",'"+hash+"','"+classification+"')",1000);
};


function editcomment(id,hash,classification){  
  var commentele = '#comment_'+id;
 // var currentComment = getComment(id);//$('#mdcomment_'+id).text();
  $.get("/getcomment.php",
    { id: id },
    function(data){
  $(commentele).html("<textarea id=\"content_"+id+"\" class=\"commentTextarea\">"+data+"</textarea>&nbsp;<br><select name=\"classification\" id=\"classification_"+id+"\"><option value=\"none\">Flag this torrent as:</option><option value=\"none\">None</option><option value=\"misnamed\">Misnamed</option><option value=\"pwed\">Passworded</option><option value=\"spam\">Spam / Malware</option><option value=\"fake\">Fake</option></select>&nbsp;&nbsp;&nbsp;<input type=\"submit\" onClick=\"updatecomment("+id+",'"+hash+"')\" value=\"Update\" class=liteoption>&nbsp;<a href=\"#\" onClick=\"canceleditcomment("+id+");return false;\">cancel</a>");
  $("#classification_"+id).val(classification);
    }
  );
}

function canceleditcomment(id){
  var commentele = '#comment_'+id;
  $.get("/getcomment.php",
    { id: id , tohtml: "yes"},
    function(data){
      $(commentele).html(data);
      }
  );
}

function getComment(id){
  var _content;
  $.get("/getcomment.php",
    { id: id, tohtml: "no" },
    function(data){
      _content = data;
     return _content;
    }
  );
  return _content;
}

function updatecomment(id,hash){
  var contentele = '#content_'+id;
  var classele = '#classification_'+id;
  var content = $(contentele).val();
  var classification = $(classele).val();
  $.post("/updatecomment.php",
  { commentid: id, content: content, hash: hash, classification: classification });
  if (content!=''){
  $('#mdcomment_'+id).text(content);
  $('#comment_'+id).html(toMarkdown(content));
  }
}

function postComment(hash){
  var content = $('#reply').val();
  var classification = $('#classification').val();
  $("#reply").val('');
  $.post("/comment.php",
  { hash: hash, classification: classification, content: content },
  function(data){
    if (data.indexOf("more_than_50") != -1){
      $("#error").slideDown("slow");
    }
    else if (data.indexOf("<___no_comment___>") == -1){ 
      $("#commentsList").append(data);
      var latestid = $('#latest').text();
      $('#latest').remove();
      countdown(900,latestid,hash,classification);
    }
  }  
  );
}

function deletecomment(id,hash,group,poster_ip,context){
  var deleteBool = confirm('Are you sure you want to delete this comment?');
  if (deleteBool==true){
    $.post("/deletecomment.php",
    { commentid: id, hash: hash, group: group, poster_ip: poster_ip, context: context});
    $('.row_'+id).each(function(){$(this).remove()});
    $('.spacerow_'+id).each(function(){$(this).remove()});
  }
}

function deleteAllCommentsBy(type,posterip,user){
  var deleteBool = confirm('Are you sure you want to delete these comments?');
  if (deleteBool==false){return false;}
  else{
    $.get("/deleteallcomment.php",
        { delete_by: type, ip: posterip, user: user});
   return setTimeout("window.location = \"/comments-mod.php\";",2000);
  }
}

function massdelete(hash, context, group){
  var cbs = new Array();
  cbs = $("input[@name^=commentbox]:checked");//.each(function() { cbs.push($(this).val);  });
  all = $(".commentsBody");
  var deleteBool = confirm('Are you sure you want to delete these comments?');
  if (deleteBool==true){  
    var comments = new Array();
    var hashes = new Array();
    var qty = all.length;  
    for (x=0; x<cbs.length; x++){
      if(cbs[x].value!='')
        { var chash = $("#hash_"+cbs[x].value).val();
          comments.push(cbs[x].value)
          hashes.push(chash);
          //alert(chash);
  if (qty<50){
    $('.row_'+cbs[x].value).each(function(){$(this).remove()});
    $('.spacerow_'+cbs[x].value).each(function(){$(this).remove()});
    $('.chash_'+cbs[x].value).each(function(){$(this).remove()});
    $('.ctitle_'+cbs[x].value).each(function(){$(this).remove()});
    }
    }
    }
    $.post("/deletecomment.php",
    { commentid: comments.join(), hash: hash, hashes: hashes.join(), context: context, group: group });
  if(qty>50){setTimeout("location.reload(true);",2000)}
  }
}  

function voteTorrent(vote,hash){
  $('#saythanks').html('Processing...');
  $.post("/votetorrent.php",
  { hash: hash, vote: vote },
    function(data){
      if(data=="ok"){
        $('#saythanks').html('You\'ve said Thanks to this torrent.');
      } 
      else if(data=="more_than_100"){
        $('#saythanks').html('Sorry, you voted too many times today. If you did not, stop using a proxy server with your internet connection and try again.');
        }
      else if(data==""){$('#saythanks').html('Sorry, you\'re vote could not be counted');}
      else if(data=="already"){$('#saythanks').html('Sorry, you\'ve already said thanks to this comment.')  
      }  
  
 }); 
}

function plusOneTorrent(vote,hash){
  $('#plusone_'+hash).html('Processing...');
  $.post("/votetorrent.php",
  { hash: hash, vote: vote },
    function(data){
      $('#plusone_'+hash).html('done');
  }); 
  return false;
}

function init_table_links(){
  $(document).ready(
    function() {
      $('#serps tr').gt(0).each(
        function(){
          var summury_link = $(this).children('td').eq(1).children('a').eq(1).attr('href');
          $(this).children('td:eq(0), td:gt(1):lt(3)').click(
            function(){
              window.location=summury_link;
            }
          )
        }
      )
   }
  )
}

function voteComment(vote,comment_id,hash,cvotes,user_id,posterid){
$('#commentvote_'+comment_id).html('Processing...');

  if(user_id!=posterid){
    $.post("/votecomment.php",
    { comment_id: comment_id, vote: vote, hash: hash },
    function(data){
      if(data=="ok"){
        $('#commentvote_'+comment_id).html('Thanks for voting.');
        $('#current_score_'+comment_id).html(vote+cvotes || '0');
      } 
      else if(data=="more_than_100"){
        $('#commentvote_'+comment_id).html('Sorry, you voted too many times today. If you did not, stop using a proxy server with your internet connection and try again.');}
      else if(data=="error"){$('#commentvote_'+comment_id).html('Sorry, you\'re vote could not be counted');}
      else if(data=="already"){$('#commentvote_'+comment_id).html('Sorry, you\'ve already voted for this comment');}

    });
 } else {
    $('#commentvote_'+comment_id).html('Sorry, you can\'t vote on your own comment.');
  }
}

function toggleMods(ele,img,deletelink){
  var current = $("#"+img).attr("src");
  if (current=='/img/serp-toggle-up.gif'){
    $('#'+img).attr("src","/img/serp-toggle-down.gif");
  } else {
    $('#'+img).attr("src","/img/serp-toggle-up.gif");
  }
  $('#'+ele).slideToggle('slow');
  $('.'+deletelink).each(function(){$(this).toggle()});
}


function searchComment(){
  $('.delete_searched_link').each(function(){$(this).hide()});
  $("#searchComments").hide();
  var q = $('#'+'ihcq').val();
  //alert(q);
  if(q!=''){
  $.post("/ajaxhandler.php",
  { action: 'comment_search', q: q },
  function(data){
    if (data.indexOf("<___no_comment___>") == -1){
      $("#commentsListSearch").html(data);
      $("#searchComments").slideToggle('slow');
      $('.delete_searched_link').each(function(){$(this).toggle()});
    }
  }
  );
  }
}


function createInvitation(){
  var emails = $('#invites_emails').val();
  var personal_msg = $('#personal_msg').val();
  if(emails!=''){
  $("#send_invitations").attr("value", "Sending..."); 
  //alert(q);
  if(emails!=''){
    $.post("/createinvitations.php",
    { 'emails': emails, 'personal_msg': personal_msg },
    function(data){
      if (data.indexOf("<___error___>") == -1){
        $("#invitation_response").parent().show();
        $("#invitation_response").show().html(data);
      $("#send_invitations").attr("value", "Send");
        $('#invites_emails').val('');
        $('#personal_msg').val('');
      }
    }
    );
  }
  }
}

function updateInvite(code,action){
 //alert(q);
 $("#"+action+"_"+code).html('processing...');
 $.post("/updateinvites.php",
  { 'code': code, 'action': action },
  function(data){
    if (data.indexOf("<___error___>") == -1){
      $("#"+action+"_"+code).html(data);
      if(action=='recall'){
        $("#recall_"+code).parent().hide();
      }
  }
  }
  );
  
}

function showInvites(user_id){
//  $('#inviter_'+user_id).parent().after('<tr><td>lol</td></tr>');
$.get("/getinvites.php",
  { 'user_id': user_id },
  function(data){
    if (data.indexOf("<___error___>") == -1){
      $('#inviter_'+user_id).parent().after(data);
  }
  }
  );

}

function deleteAllVotes(sign, hash){
var confirm_delete = confirm('Are you sure you want to delete all '+sign+' votes?')
if (confirm_delete){
  $('#deleteall'+sign+'votes_'+hash).html('Processing');
  $.post("/deleteallvotes.php",
    { 'sign': sign, 'hash': hash },
    function(data){
      if (data.indexOf("<___error___>") == -1){
        $('#deleteall'+sign+'votes_'+hash).text('Done');
      }
  }
  );
  }
  return false;
}

function getVoters(hash, context){
$('.torrent_voters_'+hash).remove();
$.get("/getvoters.php",
  { 'hash': hash },
  function(data){
    if (context == 'mod'){
      $('#display_voters_'+hash).parent().after(data);
  } else if (context == 'comment'){
    $('#commentsContainer').before('<table>'+data+'</table>');
    }
  }
  );

  
}

/*
function toggleInvitationMessage(){
$('#invite_msg_td').toggle( function(){$('#invites_options').text('Less Options')},function(){$('#invites_options').text('More Options')}
);

}*/

// this is provided with newer version of jQuery
// I don't know how exactly backwards (browser) compat checking object
// constructors are, but it should be fine up to and including IE6
function _isArray (a) {
  return typeof(a) == 'object' && a.constructor == Array;
}

function _isUndef (v) {
  return typeof(v) == 'undefined';
}

/*
 Function: getBreadBreakerFeeds( url, query, render )
 Parameters:
            url - single string url
            query - the search term to pass to breakbreaker
            renderTo - array of "jquery selectors" or DOM nodes to render to
 Synopsis:
  Simply pass this function a url to fetch breakbreaker ad's.
  This function will validate url output to ensure that it validates
  as proper breakbreaker json output
*/

{
  var _bb_ads_cache;
  function getBreadBreakerAds () {
    return _bb_ads_cache? _bb_ads_cache : false;
  }

  function setBreadBreakerAds (ads) {
    return _bb_ads_cache = ads;
  }
}

function _parseBBrkrGet( data, status, callback, failure ) {
  var success = status == 'success' && data &&
                data.response && data.response.success == 1? true : false;
  if (success) {
    var ads = data.response.ads? data.response.ads : false;
    if (typeof(ads) == 'object') {
      setBreadBreakerAds(ads);
      if (typeof(callback) == 'function') {
        return callback();
      } else {
        return false;
      }
    } else {
      if (typeof(failure) == 'function') {
        return failure();
      } else {
        return false;
      }
    }
  } else {
    if (typeof(failure) == 'function') {
      return failure();
    } else {
      return false;
    }
  }
}


function getBreadBreakerFeeds( url, query, callback, failure ) {
  if(getBreadBreakerAds())
    return false;
  
  var req = {
    q: query
  };
  
  var call = {
    type: 'GET',
    url: url,
    processData: true,
    data: req,
    dataType: 'json',
    async: true,
    success: function (data, status) {
      return _parseBBrkrGet(data, status, callback, failure);
    },
    error: function(request, settings) {
      return _parseBBrkrGet({}, 'failure', callback, failure);
    }
  };
  
  return $.ajax(call);
}

/*
  Function: renderBreadBreakerAds( start, end, renderTo )
  Parameters:
            start - index of ads array to start from
            end - index of ads array to finish at (please see Array.slice)
            renderTo - array of "jquery selectors" or DOM nodes to render to
  Synposis:
    Renders cached ads to array of jquery selectors or DOM nodes/elements
    Returns false if ads cache is empty
    Return true if rendering to ads
    Warning: start and end indexes are passed directly to Array.slice.
    
*/
function renderBreadBreakerAds( start, end, renderTo ) {
  var ads = getBreadBreakerAds();
  
  if (!ads || ads.length <= start) return false;
  
  var oDiv = document.createElement('DIV');
  $(oDiv).attr('class','adbox');
  $(oDiv).append(
    "<span id='SL_Desc'>Sponsored Links</span>"
  );
  
  var pos = start + 1;
  
  // iterate over ads data and build "listing" div's for the txt ads
  $.each( ads.slice(start, end), function() {
    var item = this;
    try {
      if (item && item.text && item.title && item.url && item.link && item.provider) {
        var d = document.createElement('DIV');
        $(d).attr('class','ad');
        $(d).append(
          '<a href="/js/click.php?'+pos+'+'+item.provider+'+'+item.link+'" class="adblock" rel="nofollow" target="_blank">'+
          '<span class="Title">'+item.title+'</span>'+
          '<span class="Abstract">'+item.text+'</span>'+
          '<div class="BaseURI">'+item.url+'</div></a>'
        );
        oDiv.appendChild(d);
      }    
    } catch(e) {
        /* just skip if we run into errors since it's most likely
           a undef error - TODO: better exception handling for this stuff
        */
    }
    pos++;
  });
  
  /*
    iterate over the renderTo array attempt to locate append object
    if found append
  */
  $.each( renderTo, function () {
    var o = $(this);
    if (o) {
      o.empty();
      o[0].appendChild(oDiv.cloneNode(true));
    }
  });
  
  return true;
}


// render iframe ads
// render <iframe allowTransparency="true" src="'+spec.src+'" width=spec.width height=spec.height frameborder=0 marginheight=0 marginwidth=0 scrolling="no"></iframe>

function _renderFrame(elm, spec) {
  if (
      typeof(spec) != 'object' || _isUndef(spec.src) ||
      _isUndef(spec.height) || _isUndef(spec.width)
  ) return false;
  
  var oDiv = $(elm);
  var src = spec.src;
  var height = spec.height;
  var width = spec.width;
    
  oDiv.empty();
  return oDiv.append(
    '<br><iframe allowTransparency="true" frameborder="0" marginheight="0"'+
    ' marginwidth="0" scrolling="no" '+
    'width="' + width  +'" '+
    'height="'+ height +'" '+
    'src="'+    src    +'"></iframe><br><br>'
  );
}

function renderIframeAds ( to, spec ) {
  if (!_isArray(to) && !_isArray(frames))
    return false;
  
  return $.each( to, function () {
    if (_isArray(this)) {
      return $.each(this, function () {
        _renderFrame(this, spec);
      });
    } else {
      return _renderFrame(this, spec);
    }
  });
}


/* wrapper function for ad rendering
 if text ads fail - use iframes (banners)
 renderAds(
   <async url>, <search query>, <array of object slices>,
   <elements to write>, <iframe specs as backup>,
   <debug callback>
 );
 Usage example:
  
  renderAds(
    '/js/textads.php?test',
    'dogs',
    [
      {start: 0, end: 3},
      {start: 3, end: 7}
    ],
    [
      [firstDiv],
      [secondDiv]
    ],
    [
      {
        src: 'iframeAd.php?mode=top&source=ih-search&ihq=dogs',
        width: 768,
        height: 90
      },
      {
        src: 'iframeAd.php?mode=side&source=ih-search&ihq=dogs',
        width: 160,
        height: 600
      }
    ]
  );
*/

function renderAds (url, query, slices, elements, frames, debug_cb ) {

  var success_pairing = [];
  var failure_pairing = [];
  var d_cb = typeof(debug_cb) == 'function'? debug_cb : function () {};
  
  for(var i = 0; elements.length > i; i++) {
    success_pairing.push(
      [ slices[i], elements[i] ]
    );
  }

  for(var i = 0; elements.length > i; i++) {
    var s = frames[i] || {};
    failure_pairing.push(
      [ s, elements[i] ]
    );
  }

  var failure_cb = function () {
    var ret = $.each( failure_pairing, function () {
      var p = this;
      renderIframeAds( p[1], p[0] )
    });
    d_cb(false);
    return ret;
  };
  
  var success_cb = function () {
    if (getBreadBreakerAds()) {
      var ret = $.each( success_pairing, function () {
        var p = this;
        var s = p[0];
        var e = p[1];
        return renderBreadBreakerAds( s.start, s.end, e );
      });
      d_cb(true);
      return ret;
    } else {
      // if for some reason the BB ads cache gets deleted after it's been
      // populated but before rendering happens call our failure callback
      return failure_cb();
    }
  };
  
  return getBreadBreakerFeeds( url, query, success_cb, failure_cb );
}


