/**
 * Function para crear una function js getElementsByClass
 */
function getElemByClass(){
  if(null==document.getElementsByClass) {
    document.getElementsByClass = function(searchClass,node,tag) {
           var classElements = new Array();
           if ( node == null )
                   node = document;
           if ( tag == null )
                   tag = '*';
           var els = node.getElementsByTagName(tag);
           var elsLen = els.length;
           var pattern = new RegExp("(^|\\s)"+searchClass+"(\\s|$)");
           for (i = 0, j = 0; i < elsLen; i++) {
                   if ( pattern.test(els[i].className) ) {
                           classElements[j] = els[i];
                           j++;
                   }
           }
           return classElements;
      }
  } 
}
getElemByClass();

/**
 * Manejador de formularios y validaci?n.
 * @class FormManager
 */
var FormManager = Class.create({
  
  /* Propiedades **************************************************************/
  
  /**
   * Identificador del elemento DOM de formulario.
   * @var string id
   */
  id: null,
  
  /**
   * Elemento DOM de formulario.
   * @var Element formElement
   */
  formElement: null,
  
  /**
   * Elementos del formulario que manejar? FormManager.
   * @var array elements
   */
  elements: null,

  /**
   * Valores por defecto en el formulario.
   * @var array defaults
   */
  defaults: {},
  
  /* Ejecutiva ****************************************************************/
  
  /**
   * Inicializa el formulario cuyo identificador se enterga.
   * @param string elementId - Identificador de formulario.
   * @return void
   */
  initialize: function(elementId) {

    // Inicialización.
    this.id = elementId;
    this.formElement = $(elementId);
    this.elements = document.getElementsByClassName('regexp', this.formElement);
    if(this.formElement.className && this.formElement.className.indexOf('appendable') >= 0)
      this.defaults = this.getDefaults();

    // Actualiza los elementos del formulario.
    for(var i = 0; i < this.elements.length; i++) {
      var element = this.elements[i];
      
      try {
        var attribute  = element.getAttribute('constraint');
        var constraint = attribute.replace('?',  '');
        var optional   = attribute.indexOf('?') > -1;
        // Recupera la constraint.
        for(var j = 0; j < FormManager.regidz.length; j++) {
          if(constraint == FormManager.regidz[j]) {
            element._regfn  = FormManager.regfn[j];
            element._regexp = '^' + (optional? '(' : '') 
              + FormManager.regexp[j]
              + (optional? ')?' : '')  + '$';
            element._regerr = j;
            element._optional = optional;
            break;
          }
        }
      } catch(e) {
      	alert(e);
      }
    }

    // Actualiza el formulario.
    this.formElement._manager = this;
    this.formElement.onsubmit = function() {
      return this._manager.validate();
    };
  },
  
  stripHTML: function(oldString) {
    var newString = "";
    var inTag = false;
    for(var i = 0; i < oldString.length; i++) {
      if(oldString.charAt(i) == '<') inTag = true;
      if(oldString.charAt(i) == '>') {
        if(oldString.charAt(i+1)=="<") {
          //dont do anything
        } else {
          inTag = false;
          i++;
        }
      }
      if(!inTag) newString += oldString.charAt(i);
    }
   
   return newString;
  },
  
  /**
   * Valida el contenido del formulario.
   * @return boolean - Verdadero si el formulario valid? correctamente, falso
   *   en caso contrario.
   */
  validate: function() {
    this.clearErrors();
    var isValid = true;
    for(var i = 0; i < this.elements.length; i++) {
      var val = null, elem = this.elements[i];
      if(elem.nodeName == 'TEXTAREA') {
        if(elem.className.indexOf('mce-editor') == -1) {
          val = this.stripHTML(elem.innerHTML);
        } else {
          var ifr = document.getElementById(elem.name + '_ifr');            
          val = this.stripHTML(ifr.contentWindow.document.body.innerHTML).replace(/\n/g,'');

          if(val === '&nbsp;'){
          	val = '';
          }          
        }
      } else { 
        if(elem.type == 'checkbox'){
          val = elem.checked;
          if(val==false){
          	val='';
          } else {
          	val='true';
          }
        } else {
          val = elem.value;	
  
        }
      }
      var thisIsValid = true;
      
      if(!elem._optional || (elem._optional && val)) {
        if(elem._regexp) thisIsValid &= (val.match(elem._regexp) !== null);
        if(elem._regfn ) thisIsValid &= elem._regfn(val);
      } 
      if(!thisIsValid) this.renderError(elem);
      isValid &= thisIsValid;
        
    }
    return isValid? true : false;    
  },
  
  /**
   * Elimina todos los mensajes de error en el formulario.
   * @return void
   */
  clearErrors: function() {
    var elements = document.getElementsByClass('error', this.formElement );
    for(var i = 0; i < elements.length; i++) {
      elements[i].parentNode.removeChild(elements[i]);
      //Miramos si existe otros elementos con una clase error                  
    }
    //this.initialize(this.id);    
  },
  
  /**
   * Dibuja el mensaje de error adecuado para el elemento dado.
   * @param Element element - Elemento DOM cuyo error se mostrar?.
   * @return void
   */
  renderError: function(element) {
    var error = document.createElement('div');
    error.className = 'error';
    error.innerHTML = FormManager.regerr[element._regerr];
    if(element.nodeName == 'TEXTAREA'){
     	var span = document.getElementById(element.name + '_container'); 
      element.parentNode.insertBefore(error, span.nextSibling);      	
    } else {
      element.parentNode.insertBefore(error, element.nextSibling);      	
    }

     
  },
  
  getDefaults: function() {
    var ez = this.formElement.elements;
    var defaults = {};
    for(var i = 0; i < ez.length; i++) {
      var element = ez[i], value = null;
      if(!element.className || element.className.indexOf('keep-value') < 0) {
        if(element.nodeName == 'INPUT') {
          if(element.type) {
            if(element.type == 'checkbox') value = element.checked;
              else value = element.value;
          }
        } else if(element.nodeName == 'TEXTAREA') value = element.innerHTML;
        defaults[element.name] = value;
      }
    }
    return defaults;
  },

  append: function() {
    var ez = document.getElementsByClass('appendable', this.formElement, 'DIV');
    if(ez.length) {
      element = ez[0];
      if(element.style.display) this.reset();
      element.style.display = 'block';
    } else this.reset();
    var ez = document.getElementsByClass('append', this.formElement, 'BUTTON'), element = null;
    if(ez.length) {
      element = ez[0];
      element.innerHTML = element.innerHTML.replace('Crear', 'Limpiar');
      element.childNodes[0].src = '/img/clear.gif';
    }
  },
  
  reset: function() {
    var ez = his.formElement.elements;
    for(var i = 0; i < ez.length; i++) {
      var element = ez[i];
      try {
        if(element.nodeName == 'INPUT') {
          if(element.type == 'checkbox') element.checked = this.defaults[element.name];
            else element.value = this.defaults[element.name];
        } else if(element.nodeName == 'TEXTAREA') element.innerHTML = this.defaults[element.name];
      } catch(e) { alert(e); }
    }
  }
});

/**
 * Lista de expresiones regulares para el validador.
 * @var array FormManager.regexp
 */
FormManager.regexp = [
  '\\d\\d\\-\\d\\d\\-\\d\\d\\d\\d', // date
  '.+',                             // text
  '\\w',                            // char
  '[0-9]+',                         // absint
  '[+-]?[0-9]+',                    // int
  '[0-9]+((\\.)?[0-9]+)?',          // absfloat
  '[+-]?\\d+([,.]\\d+)?',           // float
  '[1]?[0-9]{1,2}(\\.[0-9]+)?',     // abspercent
  '[+-]?[1]?[0-9]{1,2}(\\.[0-9]+)?',// percent
  '.+',                             // path
  '.+',                             // filename
  '.+',                             // credential
  '.+',                             // zipcode
  '.+',                             // phone
  '(ftp|http|https):\\/\\/(\\w+:{0,1}\\w*@)?(\\S+)(:[0-9]+)?(\\/|\\/([\\w#!:.?+=&%@!\\-\\/]))?', // url
  '[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,4}', // email
  '[a-zA-Z0-9_.-]{6,12}',           // password
  '.+',                               // checkbox
];

FormManager.regfn  = [
  null, // date
  null, // text
  null, // char
  null, // absint
  null, // int
  null, // absfloat
  null, // float
  null, // abspercent
  null, // percent
  null, // path
  null, // filename
  function valid(cif) {	/*credential*/
    // Based on php function of David Vidal Serra.
    //Returns: 1 = NIF ok, 2 = CIF ok, 3 = NIE ok, -1 = NIF bad, -2 = CIF bad, -3 = NIE bad, 0 = ??? bad
    //cif = inpt.value;
    num = new Array();
    cif = cif.toUpperCase();
    for (i = 0; i < 9; i ++) {
      num[i] = cif.substr(i, 1);
    } 
    //si no tiene un formato valido devuelve error    
    if (!cif.match('((^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$|^[T]{1}[A-Z0-9]{8}$)|^[0-9]{8}[A-Z]{1}$)')) {
      return false;
    }
    //comprobacion de NIFs estandar
    if (cif.match('(^[0-9]{8}[A-Z]{1}$)')){
      if (num[8] == 'TRWAGMYFPDXBNJZSQVHLCKE'.substr(cif.substr(0, 8) % 23, 1)){
        return true;
      } else {
        return false;
      }
    }
    //algoritmo para comprobacion de codigos tipo CIF
    sumaB = new Number(0);
    sumaC = new Number(0);
    sumaA = new Number(parseInt(num[2]) + parseInt(num[4]) + parseInt(num[6]));

    for (i = 1; i < 8; i += 2) {
    	if(num[i]!=0 && num[i]!='0' && num[i]!=null){
    	  numb1 = new Number((2 * num[i]).toString().substr(0,1));
        numb2 = new Number((2 * num[i]).toString().substr(1,1));  
        sumaB = new Number(sumaB + numb1 + numb2);
    	}
    }
    sumaC = Number(parseInt(sumaA) + parseInt(sumaB));     
    n = Number(10 - sumaC.toString().substr( sumaC.toString().length - 1, 1));
    //comprobacion de NIFs especiales (se calculan como CIFs)
    if (cif.match('^[KLM]{1}')) {
      if (num[8] == String.fromCharCode(64 + n)){
        return true;
      } else {
        return false;
      }
    }
    //comprobacion de CIFs
    if (cif.match('^[ABCDEFGHJNPQRSUVW]{1}')) {
      if (num[8] == String.fromCharCode(64 + n) || num[8] == n) {
        return true;
      } else {
        return false;
      }      	
    }
    //comprobacion de NIEs
    //T
    if (cif.match('^[T]{1}')) {
      if (num[8] == cif.match('^[T]{1}[A-Z0-9]{8}$')) {
        return true;
      } else {
        return false;
      }
    }
    //XYZ
    if (cif.match('^[XYZ]{1}')) {
      tmpstr = cif.replace('X', '0');
      tmpstr = tmpstr.replace('Y', '1');
      tmpstr = tmpstr.replace('Z', '2');
      if (num[8] == 'TRWAGMYFPDXBNJZSQVHLCKE'.substr( tmpstr.substr(0, 8) % 23, 1)) {
        return true;
      } else {
        return false;
      }
    }
    //si todavia no se ha verificado devuelve error
    return false;
  },   
  null, // zipcode
  null, // phone
  null, // url
  null, // email
  null, // password
  function validCheck(checkbox){
    if(checkbox=='true'){
    	return true;
    } else {
      return false;    	
    }
  },
  null
];

/**
 * Lista de identificadores para las expresiones regulares del validador.
 * @var array FormManager.regidz
 */
FormManager.regidz = [
  'date',
  'text',
  'char',
  'absint',
  'int',
  'absfloat',
  'float',
  'abspercent',
  'percent',
  'path',
  'filename',
  'credential',
  'zipcode',
  'phone',
  'url',
  'email',
  'password',
  'checkbox'
];

/**
 * Lista de mensajes de error para las expresiones regulares del validador.
 * @var array FormManager.regerr
 */
FormManager.regerr = [
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Fecha inv&aacute;lida.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Campo obligatorio.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Car&aacute;cter inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Valor inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Valor inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Valor inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Valor inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Porcentaje inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Porcentaje inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Ruta inv&aacute;lida.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Archivo inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">DNI, NIF o CIF inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">C&oacute;digo postal inv&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">N&uacute;mero de tel&eacute;fono no v&aacute;lido.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Direcci&oacute;n URL inv&aacute;lida.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Direcci&oacute;n de correo electr&oacute;nico inv&aacute;lida.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Contrase&ntilde;a inv&aacute;lida.</span>',
  '<img src="img/exclamation.gif" alt="Error" title="Error" />&nbsp;<span class="error">Usted tiene que acceptar las condiciones de uso.</span>'
];


function initFormManager(id){
	if(id=='registroUsuario'){
	  forml = document.getElementById('accesoUsuario');	
	} else {
    forml = document.getElementById('registroUsuario');    
	}
  for(i=0; i<forml.elements.length; i++){
    if(forml.elements[i].className=='accesoInput regexp'){
      forml.elements[i].className = forml.elements[i].className.replace('regexp', '');  
    }
  } 	
	formId = document.getElementById(id);
  for(i=0; i<formId.elements.length; i++){
  	if(formId.elements[i].className=='accesoInput'){
      formId.elements[i].className += ' regexp';	
  	}
  }
  new FormManager(id);
  
  if(id=='accesoUsuario'){
  	
  }
  
}