function requestURL ( URL, el ) {
 var req = getXMLHTTPRequest();

 req.onreadystatechange = function () {
  if ( req.readyState == 4 && req.status == 200 ) {
   var res = req.responseXML.documentElement;
  }
 };

 with ( req ) {
  open( "GET", URL, true );
  setRequestHeader( "Content-type", "application/x-www-form-urlencoded" );
  send( null );
 }

}


var layers_visible = [],
    top_interface = '0',
    copy_from_formid = "",
    DEBUG_MODE = false && confirm('Ativar modo de debug?'), // Exclusivo para debug.
    DEFAULT_TIMEOUT = 60 * 1000,
    requestURLdone = [],
    requestURLold  = [],
    LEFT,RIGHT,moz,
    POST,GET,XML,TEXT,tip;





function requestURL (meth, myURL, params, el, once, timeout, quiet) {

 if (timeout == undefined) timeout = DEFAULT_TIMEOUT;

 var unique   = el.id + '@' + myURL,
     reqNum, req, oldHTML, timedout, t;

 if ( el.nodeName == "TR" && el.childNodes.length == 1 )
  el = el.childNodes[0];

 // Se requisicao ja tiver sido feita
 if ( once == 1 && requestURLdone.include(unique) && el.innerHTML.length != 0 ) {
  return;

 // Requisiçãoo usa cache
 } else if ( once == 2 ) {
  // Se encontrou entrada no cache, retorna
  if ( getUltraCache(meth+'$'+myURL+'?'+params) != null ) {
   Element.update( el, getUltraCache(meth+'$'+myURL+'?'+params) );
   return;
  }

 // Vamos precisar fazer a requisição
 } else {
//   requestURLdone.push(unique);
 }

 reqNum = requestURLdone.length - 1;

 el.lastRequest = myURL;

 req = new AJAX(meth, myURL, params);

 oldHTML = String( el.innerHTML );

 timedout = false;

 if (timeout !== false) {
  t = setTimeout(function () {
   timedout = true;
 
   alert("Requisição foi cancelada porque atingiu o tempo limite("+(timeout / 1000)+" segundos). Por favor, Tente novamente.");
 
   Element.update(el, oldHTML);
 
//    requestURLdone.splice( reqNum, 1 );
  }, timeout);
 }

 req.events.success = function(res) {
  clearTimeout(t);

  if (timedout) return;

  try {
   if ( once == 2 ) setUltraCache( meth+'$'+myURL+'?'+params, res );
   if(Element.update(el, res)){
   calculapagina('');
   }
   requestURLdone.push(unique);

  } catch (e) {
   alert('Não pode atualizar elemento '+el.nodeName+': '+e.description+ ' - O HTML pode estar desconforme?');
    
   if (DEBUG_MODE) {
    // Debug for IE
    if (!moz) {
     if (confirm(e.description+"\n\nDeseja ver o conteúdo da resposta?")) {
      var win = open(),
          txt = win.document.createElement('textarea');

      txt.value        = res;
      txt.style.width  = "100%";
      txt.style.height = "100%";

      win.document.body.appendChild(txt);
     }
    }
   }
  }
 };

 oldHTML = String( el.innerHTML );

 req.events.error = function (message) {
  // Quando a janela é fechada e há uma requisição AJAX, ocorre erro. Por isso o try.
  try {
   clearTimeout(t);
   
   AJAX.events.error(message);
 
   Element.update( el, oldHTML );
 
//    requestURLdone.splice( reqNum, 1 );
  } catch (e) {}
 };

 if (quiet) req.events.fail=new Function;

 req.events.loading = function (reqNum, URL) {
  AJAX.events.loading(reqNum, URL);

  var realEl = el,i,b;
  // Se elemento for pequeno, tenta ver se não há alguma child dele que seja maior (position absolute)
  if ( realEl.innerHTML.length > 100 && ( realEl.clientWidth <= 200 || realEl.clientHeight <= 70 ) ) {
   for ( i = 0; i < el.childNodes.length; i++ ) {
    if ( el.childNodes[i] && ( el.childNodes[i].nodeType == 1 && el.childNodes[i].style.position == 'absolute') && ( el.childNodes[i].clientWidth > el.clientWidth || el.childNodes[i].clientHeight > el.clientHeight ) ) {
     realEl = el.childNodes[i];
    }
   }
  }

  // Decide como mostrar que elemento está em releitura
  // Elemento grande com dados dentro (desfoca conteudo)
  if ( realEl.nodeName == 'TR' || ( realEl.innerHTML.length > 100 && realEl.clientWidth > 200 && realEl.clientHeight > 50 ) ) {
   // b é a div que ofusca o conteúdo
   b = document.createElement("div");
   b.style.position = 'absolute';
   if ( realEl.style.position == 'absolute' ) {
    b.style.top  = realEl.style.top;
    b.style.left = realEl.style.left;
   }
   b.style.width  = realEl.clientWidth  + 'px';
   b.style.height = realEl.clientHeight + 'px';
   b.style.background = 'url( /t/default/img/loading_bg.gif )';
   b.style.zIndex = 1000;
   b.innerHTML = "<table width='100%' height='100%' border=0><tr><td valign=middle align=center><p class='loading_inside'><img src=/img/loading.gif border=0> Carregando...</p></td></tr></table>";

   // Insere a div
   el.insertBefore( b, el.firstChild );

  // Se elemento for grande o suficiente (exibe a rodinha mais o texto "Carregando...")
  } else if (realEl.clientWidth > 200 && realEl.clientHeight > 50) {
   realEl.innerHTML = "<p class=loading><img src=/t/default/img/loading.gif border=0 align=absmiddle> Carregando...</p>";

  // Se elemento for pequeno, apenas a bolinha giratoria
  } else {
//   realEl.innerHTML = "<b class=loading_small><img src=/t/default/img/loading.gif border=0 align=absmiddle></b>";
   realEl.innerHTML = "<img aclass=loading_small src=/t/default/img/loading.gif border=0 align=absmiddle alt=loading>";
  }
 };

 req.request()
}


function putPoint( value ) {
 var c = 0,
     r = "";

 for( var x = value.length - 1; x >= 0 ; x-- ) {
  c++;
  r = value.charAt(x) + r;
  if( c % 3 == 0 && x > 0 ) {
   r = "."+ r;
  }
 }
 return r;
}

function valEmail( email, flag ) {

  var expReg = /^ *.+@.+(\..+)+ *$/i;
  
  var result = expReg.test( email.value );

  if ( ( email.value && result ) || ( email.value && flag ) ) {

    expReg = /^ *[_a-z0-9]+((\.|\-)?[_a-z0-9]+)*@[_a-z0-9]+(\-?[_a-z0-9]+)*(\.[_a-z0-9]+(\-?[_a-z0-9]+)?)* *$/i;
  
    result = expReg.test( email.value );  
    
    if ( !result ) {
    
      email.style.borderColor = email.style.color = '#9A1010';
      email.style.backgroundColor = '#FFE5E5';
    
    } else {
    
      email.style.backgroundColor = email.style.borderColor = email.style.color = '';    
    
    }
    
  } else {
  
    email.style.backgroundColor = email.style.borderColor = email.style.color = '';
  
  }

}

function verData() {

 var select = document.composeform.type;
 
 var data = document.composeform.data;
 
 if ( select.value == 'noticia' ) {
 
   var erro;
 
   if ( data.value ) {      
   
      var expReg = /^\d{2}\/\d{2}\/\d{4}$/;
 
      var result = expReg.test( data.value );
      
      if ( !result ) {
      
        erro = 'Formato de data inválido';
      
      }
    
    } else {
    
      erro = 'Uma página do tipo noticia precisa ter uma data';     
    
    }
    
    if ( erro ) {
 
      alert( erro );
      
      data.select();
   
      return false;      
 
    }
    
 } 
 
 return true;
 
}

function hideData() {
 
  var divData = document.getElementById( 'data' );
  
  var select = document.composeform.type;
  
  if ( isNaN( select.value ) ) {
  
    divData.style.display = '';
  
  } else {
  
    divData.style.display = 'none';
  
  }

}

function selCat( obj, pag ) {
 var val = document.getElementById( obj ).value; 
 if ( val ) {
  document.location.href = '/cgi-bin/'+pag+'?id='+val;
 }
}

// Em desuso
function ___setArray( id, arrName ) {

 var obj = document.getElementById( id ); 
 
 if ( arrName ) {
 
 var actArray = eval( arrName );
 
 if ( actArray.length > 0 ) {
 
  for ( var i = 1; i <= actArray.length; i ++ ) {
  
   obj.options[i] = eval( actArray[i-1] );
   
  }
  
  obj.options.length = actArray.length + 1;
  
 } 
 
 } else {
 
  obj.options.length = 1;
 
 }
 
}

function setArray ( elId     // id do elemento
                  , opts ) { // array de opções
 var el = document.getElementById( elId ); // array

 el.options.length = 1; // Limpa a combo.

 if ( el != null ) { // Se elemento existir
  if ( opts != null       // Se array existir
   && opts.length > 0 ) { // E possuir itens
   
   // Percorre o array.
   for ( var pos = 0, last = opts.length; pos < last; pos ++ ) {
    var optVals = opts[pos]                                  // Item do array
      , optEl   = new Option( optVals.text, optVals.value ); // e elemento option.

    el.options.add( optEl ); // Adiciona a opção à combo.
   }
  }
 } else {                        // Se não
  throw "elemento inexistente."; // gera excessão.
 }
}

// 3 funções para limitar o número de caracteres digitados em um textarea e ao mesmo tempo, tem um contador de caracteres visual
var ns6 = document.getElementById && !document.all

// 1
function RestringeInput( maxlength, e, placeholder ) {
 if ( window.event && event.srcElement.value.length >= maxlength ) {
  return false;
 } else if ( e.target && e.target == eval( placeholder ) && e.target.value.length >= maxlength ) {
  var PressTecla = /[a-zA-Z0-9\.\,\/]/; //detecta caracteres alfanuméricos
  if ( PressTecla.test ( String.fromCharCode ( e.which ) ) ) {
   e.stopPropagation();
  }
 }
}

// 2
function ContaLimite( maxlength, e, placeholder ) {
 var theform = eval( placeholder );
 var lengthleft = maxlength-theform.value.length;
 var placeholderobj = document.all ? document.all[placeholder] : document.getElementById( placeholder );
 if ( window.event || e.target && e.target == eval( placeholder ) ) {
  if ( lengthleft < 0 )
   theform.value = theform.value.substring( 0, maxlength );
   placeholderobj.innerHTML = lengthleft;
 }
}

// 3
function MostraLimite( theform, thelimit ) {
 var limit_text = '<span id="'+theform.toString()+'" style="font-family:Verdana, Arial, Helvetica, sans-serif; font-size:11px; color:#555555">'+thelimit+'</span><span style="font-family:Verdana, Arial, Helvetica, sans-serif; font-size:11px; color:#555555"> caracteres restantes.</span>';
 if ( document.all || ns6 )
 document.write( limit_text );
 if ( document.all ) {
  eval( theform ).onkeypress = function() { return RestringeInput( thelimit, event, theform ) }
  eval( theform ).onkeyup = function() { ContaLimite( thelimit, event, theform ) }
 } else if ( ns6 ) {
  document.body.addEventListener( 'keypress', function( event ) { RestringeInput( thelimit, event, theform ) }, true );
  document.body.addEventListener( 'keyup', function( event ) { ContaLimite( thelimit, event, theform ) }, true );
 }
}

function showStateDescription ( StateId ) {
 document.getElementById( StateId ).style.display = "block";
}

function hideStateDescription ( StateId ) {
 document.getElementById( StateId ).style.display = "none";
}

function getXMLHTTPRequest () {
 var req;

 if ( window.XMLHttpRequest ) {
  req = new XMLHttpRequest;

  if ( req.overrideMimeType )
   req.overrideMimeType( "text/xml" );
 } else if ( window.ActiveXObject ) {
  try {
   req = new ActiveXObject( "Msxml2.XMLHTTP" );
  } catch (e) {
   try {
    req = new ActiveXObject( "Microsoft.XMLHTTP" );
   } catch (e) {
    alert( "Seu browser não dá suporte a esta operação." );

    return;
   }
  }
 }

 return req;
}

// Muda a qtd de dias, conforme mês selecionado na combo
function monthChanged( e, ano ) {
  Impares = /01|03|05|07|08|10|12/;
  Pares   = /04|06|09|11/;
  Fev     = /02/;


  var ok = Impares.exec(e.value);
  if (ok) { var i = 31; }

  var ok = Pares.exec(e.value);
  if (ok) { var i = 30; }

 // Verifica se o mês é fevereiro e se o ano é bissexto
  var ok = Fev.exec(e.value);
  if ((ok) && ((ano % 4) == 0) && ((ano % 100) != 0) || ((ano % 400) == 0) ) { var i = 29; }
  else if (ok) { var i = 28; }


  var Feb = document.forms[1].elements.day;
  document.forms[1].elements.day.length = 0;

   for( var c = 01; c <= i; c++ ) {
    Feb.options[c] = new Option(c);
   }

}

// Ao mudar o ano da combo, verifica se ele é bissexto e se o mês é fevereiro
// Caso seja, refaz a combo de dias com 29 weekdays
// Caso não seja bissexto, escreve a combo com 28 dias.
function yearChanged(e) {

  var CYvalue = document.forms[1].elements.year.value;
  var CMvalue = document.forms[1].elements.month.value;
  var CD      = document.forms[1].elements.day;

  if ( ((CYvalue % 4) == 0) && ((CYvalue % 100) != 0) || ((CYvalue % 400) == 0) ) {
    if ( CMvalue == 02 ) {
     var CDvalue = CD.value;
     CD.length = 0;

     for( var c = 01; c <= 29; c++ ) {
      CD.options[c] = new Option(c);
     }

    }

  } else { 
     CD.length = 0; 
     for( var c = 01; c <= 28; c++ ) {
      CD.options[c] = new Option(c);
     }
    }

}






















function QueryString () {
 this.reset();
 // se não for passado parametros, pega a querystring atual da página.
 var p = 0 in arguments ? arguments[0] : document.location.search,
    i,j,k,pairs,pair;

 if (!p)
  return;

 // se for um objeto...
 if (typeof p == "object") {
  // Converte elementos do tipo form para objetos (em geral DIVs).
  if (typeof p.childNodes == "object" && p.nodeName != "FORM") {
   p = elformToObj(p);
  }

  // se for um formulário...
  if (typeof p.elements == "object" && p.nodeName == "FORM")
   // percorre os elementos do formulário
   for (i = 0; i < p.elements.length; i ++)
    // com base no elemento atual...
    with (p.elements[i]) {
     // se não possuir nome ou estiver desativado, passa para o proximo elemento.
     if (name == undefined || disabled == true)
      continue;

     // se for um radio ou um checkbox e estiver checado, ou for um hidden, ou texto, ou textarea, ou select-one ou password, adiciona o valor e o nome a estrutura da instancia.
     if ((["radio", "checkbox"].include(type) && checked) ||
         ["hidden", "text", "textarea", "select-one", "password"].include(type))
      this.append(name, value)
      // se for um select-multiple, adiciona o nome e os valores selecionados a estrutura.
     else if (type == "select-multiple")
      for (j = 0; j < childNodes.length; j ++)
       if (childNodes[j].selected)
        this.append(name, childNodes[j].value)
    }
  // se não for um formulário
  else
   // percorre as chaves do objeto, adicionando chave/valor a estrutura da instancia.
   for (var k in p) {
    if ( typeof p[k] == 'object' ) {
     var _this = this;
     $A(p[k]).map(function(e){ _this.append( k, e ) });
    } else {
     this.append(k, p[k]);
    }
   }
 
 // se for uma string...
 } else if (typeof p == "string") {
  // retira possivel URL e ponto de interrogação do inicio da querystring, dividindo-a por '&' ou ';'.
  pairs = p.replace(/^.*\?/, "").split(/[&;\n]/);

  // percorre a string dividida.
  for (i = 0; i < pairs.length; i ++) {
   // subdivide por '='.
   pair = pairs[i].split("=");

   // a primeira posição é a chave e a segunda é o valor.
   this.append(pair[0], unescape(pair[1]))
  }
 }
}

/*

2 Manipulação de parametros

  2.1 A Função 'param'
  
      Está função seta valores aos parametros da query string.
      
      2.1.1 Parametros
      
            - k : trata-se do nome do parametro
            - v : trata-se do valor do parametro
            
      2.1.2 Retorno
      
            A função retorna o parametro setado

*/
QueryString.prototype.param = function (k, v) {
 if (k == undefined) {
  return this.parameters
 } else if (v != undefined) {
  this.reset(k);
  this.append(k, v)
 }

 return this.parameters[k]
}

/*

2.2 A Função 'append'

    Está função adiciona valores aos parametros da querystring. Quando o parametro não existe, é criado.
    
    2.2.1 Parametros
    
          Assim como a função 'param', esta também recebe chave e valor.
          
    2.2.2 Retorno
    
          Assim como a função 'param', esta também retorna o parametro que recebeu valores.

*/
QueryString.prototype.append = function (k, v) {
 if (!this.param(k))
  this.parameters[k] = [];
 else if (!(this.parameters[k] instanceof Array))
  this.parameters[k] = [this.parameters[k]];

 if (v instanceof String) {
  this.parameters[k].push(v);
 } else if (v != null && typeof v == "object") {
  for (var i = 0; i < v.length; i ++) {
   this.parameters[k].push(v[i]);
  }
 } else {
  this.parameters[k].push(v);
 }
   
 return this.parameters[k]
}

/*

2.3 A Função 'reset'

    Está função realiza operações de acordo com os parametros passados.
    
    2.3.1 Nenhum Parametro
    
          Quando a função não recebe parametros, ela limpa toda a estrutura da instancia.
          
    2.3.2 Apenas a Chave
    
          Quando é passado o primeiro parametro, referente ao nome do parametro query string, este possui seu valor resetado.
          
    2.3.3 Sâo passados chave e índice do valor.
    
          Quando os dois parametros são passados, o valor contido no índice informado, é retirado do parametro.

*/
QueryString.prototype.reset = function (k, i) {
 if (k == undefined)
  this.parameters = {};
 else if (i == undefined)
  delete this.parameters[k];
 else
  this.param(k).splice(i < 0 ? this.param(k).length + i : i, 1)
}

/*

3 Saída

  3.1 A Função 'toString'
  
        Esta função monta uma string no formato query string com os parametros contidos na estrutura da instancia.
        
        var q = new QueryString({ id: 5, name: 'foo' });
        
        document.write(q.toString()); // irá retornar 'id=5&name=foo'
        
        Ainda é possível passar um endereço URL para completar o resultado:
        
        document.write(q.toString('http://mysite.com')); // irá retornar 'http://mysite.com?id=5&name=foo'

*/
QueryString.prototype.toString = function (URL) {
 var QueryString = [],k,i;

 for (k in this.param())
  for (i = 0; i < this.param(k).length; i ++)
   //QueryString.push(escape(k)+"="+escape(this.param(k)[i]));
   QueryString.push(escape(k)+"="+escape(this.param(k)[i]).replace(/\+/g, encodeURIComponent('+')));

 QueryString = QueryString.join("&");

 if (!URL)
  return QueryString
 else if (!/[?&]$/.test(URL))
  URL += /\?/.test(URL) ? "&" : "?";

 return URL + QueryString
}

/*

3.2 A Função 'location'

    Está função serve de redirecionamento de página, utilizando o mecanismo da função 'toString' para montar a URL.
    
    3.2.1 O parametro URL
    
          Assim como a função 'toString', esta também pode receber uma URL para completar a querystring.

*/
QueryString.prototype.location = function (URL) {
 document.location.href = this.toString(URL)
}


// Constantes representantes dos métodos disponiveis.
POST = "POST", GET  = "GET",
// Constantes representantes dos tipos de resposta.
XML  = "responseXML", TEXT = "responseText";

// Método construtor/inicializador da classe.
function AJAX (method, URL, vars, handler, type) {
 // Seta o método passado.
 this.method = method || GET;
 // Seta a URL passada.
 this.URL = URL || "Class.cgi";
 // Se for uma instancia da classe QueryString, seta o valor. Se não, cria uma instancia da classe QueryString com base no valor.
 if (vars != null && typeof vars == "object" && vars.tagName == "FORM") vars = $(vars).serialize(true);
 this.vars = vars instanceof QueryString ? vars : new QueryString(vars);
 // Seta eventos. O Evento success pode ser o valor passado ou o handler padrão. O evento fail é o handler padrão.
 this.events = { success     : handler || AJAX.events.success,
                 fail        : AJAX.events.fail,
                 loading     : AJAX.events.loading,
                 loaded      : AJAX.events.loaded,
                 interactive : AJAX.events.interactive,
                 complete    : AJAX.events.complete,
                 error       : AJAX.events.error };
 // Tipo de retorno. Default é texto.
 this.type = type || TEXT;
 var i = 1;
 while (i in AJAX.requests) {
  i ++;
 }
 AJAX.lastRequest = i;
 this.id = AJAX.requests[i] = this;
 this.actions = [];
}

//
// Executa JS depois que determidado AJAX completar (ou que o último AJAX completar)
//
AJAX.wait = function (code, id) {
 id = id || this.lastRequest;
 var request = this.requests[id];
//  if (!id || !request) alert(new Ultra.Error("não há uma requisição em espera"));

 // Se não há nenhum AJAX pendente, executa agora
 if (!id) {
  code();
 // Se tem ajax pendente, coloca na fila
 } else {
  request.actions.push(code);
 }
};

AJAX.prototype = { method : null,
                   URL    : null,
                   vars   : null,
                   events : null,
                   type   : null };

AJAX.requests = {};

// Tradução de alguns status da requisição.
AJAX.status = { 1   : "Não foi possível instanciar objeto XMLHTTP.",
                2   : "URL não especificada.",
                3   : "Método de submissão desconhecido.",
                4   : "Tipo de resposta inválido.",
                403 : "Você não tem permissão para esta requisição.",
                404 : "Página não encontrada.",
                500 : "Erro interno do servidor.",
                503 : "Página requisitada não pode ser carregada." };


// Contador de requisições incompletas.
AJAX.counter = 0;

// Eventos padrões da requisição.
AJAX.events = new Object;

AJAX.events.loading = function (reqNum, URL) {
 window.status = "["+ reqNum +"] Carregando URL "+ URL +"..."
};

AJAX.events.complete = function (reqNum, status) {
 if (status == 200)
  window.status = window.AJAX && window.AJAX.counter ? "Requisição n.º "+ reqNum +" concluída. Carregando (resta(m) "+ window.AJAX.counter +")..." : "Concluído.";
 else
  window.status = "Request #"+ reqNum +" falhou. Mensagem de erro"+ (status in AJAX.status ? ": "+ AJAX.status[status] : " desconhecida.")
};

AJAX.events.success = eval;

AJAX.events.fail = function (status) {
 var message =
  "Não foi possível fazer requisição.\n\nErro "+status+":\n"+(status in AJAX.status ? AJAX.status[status] : "<Desconhecido>");
 alert( message );
};

AJAX.events.error = function (message) {
 AJAX.counter --;
 if(message.constructor!=Event)
    alert(window.status = message || "A requisição AJAX foi interrompida!");
}


// Método que realiza a requisição.
AJAX.prototype.request = function () {
 var onSuccess,onFail,onLoading,onLoaded,onInteractive,onComplete,onError,
    XMLHTTP,type,vars,URL,method,reqNum,
    currentState,_this,__fail__;
 // Define variáveis com base nos eventos da instancia.
 with (this.events) {
  onSuccess     = success,
  onFail        = fail,
  onLoading     = loading,
  onLoaded      = loaded,
  onInteractive = interactive,
  onComplete    = complete,
  onError       = error
 }

 XMLHTTP; // Instancia do objeto XMLHTTP.
 type = new String(this.type);
 
 // Tenta instanciar objeto XMLHTTP com base no browser.
 if (window.XMLHttpRequest) {
  XMLHTTP = new XMLHttpRequest;
  
  if (type == XML && XMLHTTP.overrideMimeType)
   XMLHTTP.overrideMimeType("text/xml")
 } else if (window.ActiveXObject) {
  try {
   XMLHTTP = new ActiveXObject("Msxml2.XMLHTTP")
  } catch (e) {
   try {
    XMLHTTP = new ActiveXObject("Microsoft.XMLHTTP")
   } catch (e) {
    return onFail(1)
   }
  }
 }

 vars = this.vars,
 URL  = this.URL;

 if (!URL)
  return onFail(2);

 // Método em uppercase.
 method = this.method.toUpperCase();

 // Se método for GET, seta a URL com as variáveis concatenadas como querystring.
 if (method == GET && vars) {
  URL = vars.toString(URL);

  // Faz conversão do método se URL passar dos 1024 caracteres.
  if (URL.length > 1024) {
   URL    = this.URL;
   method = POST
  }
 }

 reqNum;

 if (window.XMLHttpRequest)
  XMLHTTP.onerror = onError;

 currentState = 1;
 _this = this, __fail__ = this.events.fail;
 // Método executado durante a requisição
 XMLHTTP.onreadystatechange = function () {
  switch (XMLHTTP.readyState) {
   // Level 1. Executa se tiver handler.
   case 1:
    if (currentState != 1)
     break;
    reqNum = ++ AJAX.counter;

    if (onLoading)
     onLoading(reqNum, URL);

    currentState = 2
   break;
   // Level 2. Executa se tiver handler.
   case 2:
    if (currentState != 2)
     break;
   
    if (onLoaded)
     onLoaded();

    currentState = 3
   break;
   // Level 3. Executa se tiver handler.
   case 3:
    if (currentState != 3)
     break;
   
    if (onInteractive)
     onInteractive();

    currentState = 4
   break;
   // Level 4. Trata a resposta.
   case 4:
    if (currentState != 4)
     break;
   
    try { AJAX.counter -- } catch (e) {}

    var status = XMLHTTP.status,res,header=XMLHTTP.getResponseHeader("PluneException"); // Status da requisição.
    if(header)header=unescape(header);

    if (onComplete) onComplete(reqNum, status);

    // Se teve sucesso, manipula a resposta.
    if (status == 200 && !header) {
     if (![window.XML, window.TEXT].include(type))
      return __fail__(4);

     res = XMLHTTP[type];

     onSuccess(res);
    // Se não, falha.
    } else if(header && onError) {
     return onError(header);
    } else {
     /*var message =
      "não foi possível fazer requisição.\n\nErro "+status+":\n"+(status in AJAX.status ? AJAX.status[status] : "<Desconhecido>");
     alert(new Ultra.Error(message));*/
     return __fail__(status);
    }

    currentState = null;
    _this.actions.invoke("call", _this, XMLHTTP);
    delete AJAX.requests[_this.id];
  }
 };

 // Abre a requisição.
 XMLHTTP.open(method, URL, true);

 // Se método for POST, seta o cabeçalho necessário.
 if (method == POST)
  XMLHTTP.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");

 XMLHTTP.setRequestHeader("Referer", document.location);

 // Testa valor do método
 switch (method) {
  // POST. Envia as variáveis.
  case POST:
   XMLHTTP.send(vars.toString());
  break;
  // GET. Envia nulo, pois as variáveis já estão concatenadas à URL.
  case GET:
   XMLHTTP.send(null);
  break;
  // Outro. Falha.
  default:
   return onFail(3)
 }
 return this.id;
};

function calculapagina(h3){
   var h = ($('conteudo'))?parseInt($('conteudo').getHeight()):parseInt($('conteudo2').getHeight());
   h = ($('localizacao'))?h + parseInt($('localizacao').getHeight()):h
   h = ($('topo'))?h + parseInt($('topo').getHeight()):h;
   h = ($('menu_segundario'))?h + parseInt($('menu_segundario').getHeight()):h;
   h = $('banner')?h + parseInt($('banner').getHeight()):h;
   h = $('menu_segundario2')?h + parseInt($('menu_segundario2').getHeight()):h;
   h = h + 12;//padding do rodape
   var h2 = parseInt($('info').getHeight()) + 134;

   $('rodape2').setAttribute('style','top:' + ((h>h2)?h:h2) + 'px');
}         

function img(elemento,iddiv,content){
 var html;
 var top;
  if(elemento != 'fecha'){
    //document.getElementById("divfloat2").style.top = elemento.screenY;
    document.getElementById("divfloat").style.indexOf = 0;
    document.getElementById("divfloat2").style.indexOf = 0;
    var tudo = $('tudo').getHeight();
    var rodape2 = $('rodape2').getHeight();
    var topo = $('topo').getHeight();
    var info = $('info').getHeight();
    h = (tudo>(info+topo))?(tudo+rodape2):(info+topo+rodape2);
    if(document.height){
      document.getElementById("divfloat").style.height = h + 'px';
    }else{ 
      document.getElementById("divfloat").style.height  = h + 'px';
    }
    
    html = '<div style="margin:10px 10px 10px 10px;">'+
	      '<div style="display:block; text-align:right; margin-bottom:5px">'+
		  '<a onclick="img(\'fecha\')">'+
		      '<img src="/img2/closelabel.gif" style="position:relative;z-index:9; float:none; cursor:pointer">'+
		  '</a>'+
              '</div>'+
	      '<div class="zoom">'+
		  ((typeof content == 'undefined')?document.getElementById(iddiv).innerHTML:content) + 
	      '</div>'+
          '</div>';

            
    $("divfloat2").innerHTML = html;

    document.getElementById("divfloat2").style.top = '15px';
    Effect.toggle('divfloat', 'appear' , {to: 0.45, duration: 0.5});
    Effect.toggle('divfloat2', 'appear', {duration: 0.5});

  }else{
    Effect.toggle('divfloat', 'appear', {duration: 0.5});
    Effect.toggle('divfloat2', 'appear', {duration: 0.5});
  }
} 


//
// Inicializa variável de Cache, sempre procurandi atingir a janela parent (raiz de todos os frames) ou mesmo a janela opener.
//
var UltraAJAXCache;

function initUltraCache (force) {

 try {
  UltraAJAXCache = window.Ultra.AJAXCache;
 } catch (e) {
 }
}

// Inicializa o Cache
initUltraCache();

function getUltraCache (key) {
 return key ? UltraAJAXCache[key] : UltraAJAXCache;
}

function setUltraCache (key,value) {
 UltraAJAXCache[key] = value;
}

function resetUltraCache () {
 initUltraCache(true);
// UltraAJAXCache.each( function (e) { setUltraCache(e.key,null) } );
}


