//Función para cargar varios onload
function addLoadEvent(func) {
  var oldonload = window.onload;
  if (typeof window.onload != 'function') {
    window.onload = func;
  } else {
    window.onload = function() {
      oldonload();
      func();
    }
  }
}

//Introducimos los eventos de onload
addLoadEvent(attachFormHandlers);
addLoadEvent(function() {
   document.forms[0].elements[0].focus();
});

//En las clases de los formularios se pone
//required para comprobar que no está en blanco
//string para comprobar sólo caracteres
//number para comprobar numeros
//email para comprobar mails
//date para comprobar fechas (si obligatorio, antes required)
//hour para comprobar horas en formato hh:mm o hh:mm:ss (si obligatorio, antes required)
//isChecked para comprobar que un radio/checkbox sea seleccionado (poner en el primero de los check/radio)
//between 1_30 para comprobar que un campo valga entre 1 y 30
//numberOfChecks 3_5 para comprobar que se seleccionen entre 3 y 5 opciones (3_3 exige tres opciones) Basta con ponerlo en el primero
//checkPass pass2 comprueba que el contenido del campo coincide con el campo pass2
//euro para euros (comas y numeros)
//cp para codigo postal
//ip comprueba que se introduzca una ip
//dns si concuerda con un servidor dns
//nif (sin guion)
//validDomain comprueba que sea un dominio registrable
//telefono comprueba que sea un telefono de 9 cifras
//or campo comprueba que estén rellenos este o el campo "campo". Por ejemplo, para requerir telefono o movil en el campo telefono ponermos class="or movil"
//notFirst en un desplegable debe estar seleccionado cualquiera menos el primero

function attachFormHandlers()
{
  // Ensure we're working with a 'relatively' standards compliant browser
  if (document.getElementsByTagName)
  {
    var objForm = document.getElementsByTagName('form');
    for (var iCounter=0; iCounter<objForm.length; iCounter++) {
	  objForm[iCounter].onsubmit = function(){return checkForm(this);}
  	}
  }
}

function checkForm(objForm)
{
  var arClass, bValid, txtError, nombreCheck, iCheck, cuentaChecks;
  var objField = objForm.getElementsByTagName('*');

  for (var iFieldCounter=0; iFieldCounter<objField.length; iFieldCounter++)
  {
    // Allow for multiple values being assigned to the class attribute
    arClass = objField[iFieldCounter].className.split(' ');
    for (var iClassCounter=0; iClassCounter<arClass.length; iClassCounter++)
    {
      switch (arClass[iClassCounter])
      {
        case 'required':
           bValid = isRequired(objField[iFieldCounter].value);
           txtError=objField[iFieldCounter].name+" no puede dejarse en blanco.";
		   break;
		
		case 'string':
           bValid = isString(objField[iFieldCounter].value.replace(/^\s*|\s*$/g, ''));
           txtError=objField[iFieldCounter].name+" solo puede contener caracteres.";
		   break;   
        
		case 'number' :
           bValid = isNumber(objField[iFieldCounter].value);
		   txtError=objField[iFieldCounter].name+" debe ser un numero.";
           break;
        
		case 'email' :
           bValid = isEmail(objField[iFieldCounter].value);
		   txtError="Introduzca una direccion de correo electronico valida";
           break;
		
		case 'date' :
		   if (objField[iFieldCounter].value!="") {
		   	txtError=isDate(objField[iFieldCounter].value);
		   	bValid=(txtError=="");
		   } else bValid=true;	
		   break;   
		
		case 'hour' :
           	if (objField[iFieldCounter].value!="") {
		   		bValid = isHour(objField[iFieldCounter].value);
		   		txtError="Introduzca la hora en un formato correcto.";
			} else bValid=true;	
		break;
		   
		case 'isChecked' :
			nombreCheck=objField[iFieldCounter].name;
		   	bValid=false;
			iCheck=0;
			while (iCheck<objField.length) {
				if (objField[iCheck].name==nombreCheck) {
					if (objField[iCheck].checked) bValid=true;
		   		}
				iCheck++;
			}
			txtError="Debe seleccionar un valor para "+nombreCheck;
		break; 
		
		case 'numberOfChecks' :
			iClassCounter++;
			rango=arClass[iClassCounter].split('_');
			nombreCheck=objField[iFieldCounter].name;
			cuentaChecks=0;
			iCheck=0;
			while (iCheck<objField.length) {
				if (objField[iCheck].name==nombreCheck) {
					if (objField[iCheck].checked) {cuentaChecks++;}
				}
				iCheck++;
			}
			bValid=isBetween(cuentaChecks,parseInt(rango[0]),parseInt(rango[1]));
			if (rango[0]==rango[1]) {
				txtError="Debe seleccionar "+rango[0]+" opciones";
			} else {
				txtError="Debe seleccionar entre "+rango[0]+" y "+rango[1]+" opciones";
			}
		   break;  
		   
		case 'between' :
		   iClassCounter++;
		   rango=arClass[iClassCounter].split('_');
		   bValid = isBetween(parseInt(objField[iFieldCounter].value),parseInt(rango[0]),parseInt(rango[1]));
		   txtError="El valor debe estar comprendido entre "+rango[0]+" y "+rango[1];
		break;
				
		case 'euro' :
           bValid = isEuro(objField[iFieldCounter].value);
		   txtError="Introduzca el valor en formato euro (números y coma).";
		break;
		
		case 'cp' :
			bValid=isNumber(objField[iFieldCounter].value);
			if (bValid) {bValid=isBetween(parseInt(objField[iFieldCounter].value),1000,53000);}
			txtError="Introduzca un código postal válido."; 	
		break;
		
		case 'ip' :
           bValid = isValidIp(objField[iFieldCounter].value);
		   txtError="Introduzca una IP correcta.";
		break;

		case 'dns' :
           bValid = isDns(objField[iFieldCounter].value);
		   txtError="Introduzca un dns correcto.";
		break;

		case 'nif' :
           bValid = isNif(objField[iFieldCounter].value);
		   txtError="Introduzca un nif/cif correcto. Ejemplos: \n12345678V \nA12345678";
		break;		
		
		case 'validDomain' :
           bValid = isValidDomain(objField[iFieldCounter].value);
		   txtError="Sólo se aceptan letras, números y guiones.";
		break;	
		
		case 'checkPass' :
			iClassCounter++;
			iCheck=0;
			bValid=false;
			while (iCheck<objField.length) {
				if (objField[iCheck].name==arClass[iClassCounter]) {
					bValid=(objField[iCheck].value==objField[iFieldCounter].value);
					iCheck=objField.length;
		   		}
				iCheck++;
			}
			txtError="Las contraseñas no coinciden.";
		break;
		
		case 'or' :
			iClassCounter++;
			iCheck=0;
			bValid=false;
			while (iCheck<objField.length) {
				if (objField[iCheck].name==arClass[iClassCounter]) {
					isRequired(objField[iFieldCounter].value);
					if (isRequired(objField[iCheck].value) || isRequired(objField[iFieldCounter].value)) {
						bValid=true;
						iCheck=objField.length;
					}
		   		}
				iCheck++;
			}
			txtError="Debe introducir algún valor en el campo "+objField[iFieldCounter].name+" o en el campo "+arClass[iClassCounter]+".";
		break;
		
		case 'telefono' :
           bValid = isTelefono(objField[iFieldCounter].value);
		   txtError="Introduzca un número de teléfono válido (9 cifras).";
		break;
		
		case 'notFirst' :
		   (objField[iFieldCounter].selectedIndex>0)?bValid=true:bValid=false;
		   txtError="Debe seleccionar un valor en el campo "+objField[iFieldCounter].name+".";
		break;		
		
        default:
          	bValid = true;
        }

      if (bValid == false)
      {
        // If this field is invalid, leave the tesing early, and alert the visitor to this error
		txtError=txtError.replace('_',' ');
        alert(txtError);
        //objField[iFieldCounter].select();
        objField[iFieldCounter].focus();
        return false;
      }
    }
  }
  return true;
}

//--------------------
//Función para comprobar introduccion obligatorias
//--------------------
function isRequired(strValue)
{
  return (strValue != '');
}


//--------------------
//Función para comprobar textos
//--------------------
function isString(strValue)
{
  return (typeof strValue == 'string' && strValue != '' && isNaN(strValue));
}

//--------------------
//Función para comprobar números
//--------------------
function isNumber(strValue)
{
  return (!isNaN(strValue) || strValue=='');
}

//--------------------
//Función para comprobar correo electrónico
//--------------------
function isEmail(strValue)
{
  if (strValue!="") {
  	var objRE = /^(?:[\w\!\#\$\%\&\'\*\+\-\/\=\?\^\`\{\|\}\~]+\.)*[\w\!\#\$\%\&\'\*\+\-\/\=\?\^\`\{\|\}\~]+@(?:(?:(?:[a-zA-Z0-9](?:[a-zA-Z0-9\-](?!\.)){0,61}[a-zA-Z0-9]?\.)+[a-zA-Z0-9](?:[a-zA-Z0-9\-](?!$)){0,61}[a-zA-Z0-9]?)|(?:\[(?:(?:[01]?\d{1,2}|2[0-4]\d|25[0-5])\.){3}(?:[01]?\d{1,2}|2[0-4]\d|25[0-5])\]))$/;
	return (objRE.test(strValue));
  } else {
	return true;	
  }
}

//--------------------
//Función para comprobar euros
//Acepta separadores de miles(punto) y solo dos decimales
//--------------------
function isEuro(strValue)
{
  var objRE = /^\s*-?((\d{1,3}(\.(\d){3})*)|\d*)(,\d{1,2})?\s?(\u20AC)?\s*$/;
  return (objRE.test(strValue));
}

//--------------------
//Función para comprobar una ip
//--------------------
function isValidIp(strValue)
{
	if (strValue!="") {
  		var objRE = /(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)/;
  		return (objRE.test(strValue));
	} else {
		return true;
	}
}

//--------------------
//Función para comprobar la hora
//--------------------
function isHour(strValue)
{
	if (strValue!="") {
  		var objRE =/^(([0-1]?[0-9])|([2][0-3])):([0-5]?[0-9])(:([0-5]?[0-9]))?$/;
  		return (objRE.test(strValue));
	} else {
		return true;
	}
}

//--------------------
//Función para comprobar un servidor DNS
//--------------------
function isDns(strValue)
{
	if (strValue!="") {
  		var objRE =/^([a-zA-Z0-9]([a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z]{2,6}$/
;
  		return (objRE.test(strValue));
	} else {
		return true;
	}
}

//--------------------
//Función para comprobar un NIF/CIF
//Acepta letra y numeros o numeros y letra (sin guiones)
//--------------------
function isNif(strValue)
{
  var objRE = /^[A-Za-z]?[0-9]{1,8}[A-Za-z]?$/;
  return (objRE.test(strValue));
}

//--------------------
//Función para comprobar que sea un nombre de dominio registrable
//--------------------
function isValidDomain(strValue)
{
  var objRE = "$_%&/()áéíóúñÁÉÍÓÚ¡¿?!";
  resultado=true;
  for (x=0;x<objRE.length;x++) {
  	if (strValue.indexOf(objRE.substring(x,1))>0) resultado=false;
  }
  return resultado;
}


//--------------------
//Función para comprobar si está entre dos valores
//--------------------
function isBetween(intValue,lower,upper) {
	resultado=true;
	if (intValue<lower) resultado=false;
	if (intValue>upper) resultado=false;
	return resultado;
}

//--------------------
//Función para comprobar teléfonos
//--------------------
function isTelefono(strValue)
{
  return (!isNaN(strValue) && strValue.length==9);
}

//--------------------
//Función para comprobar fechas
//--------------------
function isDate(dateStr) {
//Se introducen fechas con el formato dd/mm/yyyy o dd-mm-yyyy
    var datePat = /^(\d{1,2})(\/|-)(\d{1,2})(\/|-)(\d{4})$/;
    var matchArray = dateStr.match(datePat); // is the format ok?
	var respuesta = "";
    if (matchArray == null) {
        respuesta+="Por favor, introduzca la fecha con formato dd/mm/yyyy o dd-mm-yyyy. \n";
		return respuesta;
    }
    month = matchArray[3]; // parse date into variables
    day = matchArray[1];
    year = matchArray[5];

    if (month < 1 || month > 12) { // check month range
        respuesta+="El mes debe tener un valor entre 1 y 12. \n";
		return respuesta;
    }

    if (day < 1 || day > 31) {
        respuesta+="Día debe tener un valor entre 1 y 31. \n";
		return respuesta;
    }

    if ((month==4 || month==6 || month==9 || month==11) && day==31) {
        respuesta+="El mes "+month+" no tiene 31 días! \n";
		return respuesta;
    }

    if (month == 2) { // check for february 29th
        var isleap = (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
        if (day > 29 || (day==29 && !isleap)) {
            respuesta+="Febrero " + year + " no tiene " + day + " días! \n";
			return respuesta;
        }
    }
	return respuesta;
}

//---------------------------------------------------------

