/**********************************************************************************************
** Validador de formulario, por Freddy Urbina, 2005.                                         **
** =================================================                                         **
**                                                                                           **
** Para usar este validador:                                                                 **
** 1. Se debe agregar onsubmit="return funcion_que_valida(this);" en el tag del              **
**    formulario de tu página.                                                               **
** 2. Definir en la página funcion_que_valida(elForm) y desde esta función:                  **
** 3. Llamar al validador como sigue:                                                        **
**                                                                                           **
**    if (!validaCampo(elForm.nomCampo, tipoCampo, requerido, longMax, longMin, nomMostrado) **
**    {                                                                                      **
**        return (false);                                                                    **
**    }                                                                                      **
**                                                                                           **
** Donde,                                                                                    **
**  - nomCampo, es el nombre del campo de formulario a validar.                              **
**  - tipoCampo, es el tipo de campo: <string>, <numero>, <decimal>, <fecha>,                **
**    <email>, <checkbox> ó <radiobutton>.                                                   **
**  - requerido, Si es <0>, NO es requerido, <1> es requerido.                               **
**    NOTA: si se especifica otro valor, se tomará como <0>                                  **
**  - longMax, es la longitud máxima para un campo de texto ya sea string o                  **
**    numérico (esto es útil cuando se requieren años, y evitar que el año sea               **
**    por ejemplo 123213412513465435632456.                                                  **
**  - longMin, es la longitud mínima para un campo de texto o numérico.                      **
**  - nomMostrado, es el nombre del campo en la página, no en el formulario.                 **
**    Esto es útil para los mensajes de alerta emitidas por este validador.                  **
**                                                                                           **
** Ejemplo:                                                                                  **
**    if (validaCampo(elForm.edad, 'numero', '1', '3', '0', 'Edad del paciente'))            **
**    {                                                                                      **
**        return (false);                                                                    **
**    }                                                                                      **
**  Si en la página llenamos el campo edad con un string saltará un alert con lo siguiente:  **
**                                                                                           **
** <No se puede realizar esta acción porque el campo "Edad del paciente" debe ser numérico.> **
**                                                                                           **
**********************************************************************************************/

/*Esta es una funcion que valida las fechas*/
function validaFecha(campoFecha)
{
	var caja = campoFecha.value;
	if (caja) 
	{ 
		borrar = caja;
		if ((caja.substr(2,1) == "/") && (caja.substr(5,1) == "/")) 
		{
			for (i=0; i<10; i++) 
			{	
				if (((caja.substr(i,1)<"0") || (caja.substr(i,1)>"9")) && (i != 2) && (i != 5)) 
				{
					borrar = '';
					break;  
				}  
			}
			if (borrar) 
			{ 
				a = caja.substr(6,4);
				m = caja.substr(3,2);
				d = caja.substr(0,2);
				if((a < 1900) || (a > 3050) || (m < 1) || (m > 12) || (d < 1) || (d > 31)) 
				{
					borrar = '';
				}else{
					if((a%4 != 0) && (m == 2) && (d > 28)) 
					{ 
						borrar = ''; // Año no bisiesto y es Febrero. El día es mayor a 28.
						return (false);
					}else{
						if ((((m == 4) || (m == 6) || (m == 9) || (m==11)) && (d>30)) || ((m==2) && (d>29))) 
						{
							borrar = '';
							return (false);
						}else{
							return (true);
						}
					} // fin else
				} // if (error)
			}else{
				borrar = '';
				return (false);
			}
		}
	} // if (caja) 
}//fin de función validaFecha

function validaCampo(nomCampo, tipoCampo, requerido, longMax, longMin, nomMostrado)
{
	/*
	alert('Datos:\n'+
		'nomCampo     : '+nomCampo+
		'\ntipoCampo  : '+tipoCampo+
		'\nrequerido  : '+requerido+
		'\nlongMax    : '+longMax+
		'\nlongMin    : '+longMin+
		'\nnomMostrado: '+nomMostrado);
	*/
	
	var mit;
	((nomMostrado == '') ? nomMostrado = nomCampo:mit=0);
	((longMax == '') ? longMax = 0:mit=0);
	((longMin == '') ? longMin = 0:mit=0);
	
	if (requerido == '1')
	{
		//El campo es requerido
		switch (tipoCampo)
		{
			case "radiobutton":
				selecciona = false;
				for (var i = 0; i < nomCampo.length; i++) 
				{
					if (nomCampo[i].checked) 
					{
						selecciona = true;
						break;
					}
				}
				if (!selecciona) 
				{
					alert("No se puede realizar esta acción porque debe seleccionar una opción en '"+nomMostrado+"'.");
					return (false);
				}
				break;
			////////////////////////////////////////////////////////////////////////////////////////////////////////
			case "checkbox":
				if (!nomCampo.checked)
				{
					alert("No se puede realizar esta acción porque debe marcar una casilla en '"+nomMostrado+"'.");
					return (false);
				}
				break;
			////////////////////////////////////////////////////////////////////////////////////////////////////////
			default : 
				if (eval(nomCampo).value == '')
				{
					alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' es requerido.");
					nomCampo.focus();
					nomCampo.style.background='#FFEC66';
					return (false);
				}
			////////////////////////////////////////////////////////////////////////////////////////////////////////
		}
	}
	
	if (tipoCampo == 'string' || tipoCampo == 'numero' || tipoCampo == 'decimal')
	{
		if (eval(nomCampo).value.length > longMax && longMax !=='0' && longMax !== '')
		{
			alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' supera los "+longMax+" caracteres.");
			nomCampo.focus();
			nomCampo.style.background='#FFEC66';
			return (false);
		}
		
		if (eval(nomCampo).value.length < longMin && longMin !=='0' && longMin !== '' && requerido !== '0')
		{
			alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' es inferior a los "+longMin+" caracteres.");
			nomCampo.focus();
			nomCampo.style.background='#FFEC66';
			return (false);
		}
	}
	
	switch (tipoCampo)
	{
		case "numero":
			var checkOK = "0123456789-";
			var checkStr = eval(nomCampo).value;
			var allValid = true;
			var decPoints = 0;
			var allNum = "";
			for (i = 0;  i < checkStr.length;  i++)
			{
				ch = checkStr.charAt(i);
				for (j = 0;  j < checkOK.length;  j++)
					if (ch == checkOK.charAt(j))
						break;
					if (j == checkOK.length)
					{
						allValid = false;
						break;
					}
					allNum += ch;
			}
			if (!allValid)
			{
				alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' debe ser numérico.");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
				return (false);
			}
			break;
		////////////////////////////////////////////////////////////////////////////////////////////////////////
		case "fecha":
			if (eval(nomCampo).value !== "")
			{
				if (!validaFecha(eval(nomCampo))) 
				{
					alert("No se puede realizar esta acción porque la fecha de '"+nomMostrado+"' no es válida: "
						+"\n - La fecha debe tener el formato dia/mes/año (DD/MM/AAAA)."
						+"\n - El año no debe ser menor a 1900."
						+"\n - El día de febrero no debe ser mayor a 28 y en año bisiesto, 29.");
					nomCampo.focus();
					nomCampo.style.background='#FFEC66';
					return (false);
				}
			}
			break;
		////////////////////////////////////////////////////////////////////////////////////////////////////////
		case "decimal":
			var checkOK = "0123456789-,";
			var checkStr = eval(nomCampo).value;
			var allValid = true;
			var decPoints = 0;
			var allNum = "";
			for (i = 0;  i < checkStr.length;  i++)
			{
				ch = checkStr.charAt(i);
				for (j = 0;  j < checkOK.length;  j++)
					if (ch == checkOK.charAt(j))
						break;
					if (j == checkOK.length)
					{
						allValid = false;
						break;
					}
					if (ch == ",")
					{
						allNum += ".";
						decPoints++;
					}
					else
						allNum += ch;
			}
			if (!allValid)
			{
				alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' debe ser numérico decimal.");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
				return (false);
			}
			
			if (decPoints > 1)
			{
				alert("No se puede realizar esta acción porque el campo '"+nomMostrado+"' no es válido como número decimal.");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';	
				return (false);
			}
			break;
		////////////////////////////////////////////////////////////////////////////////////////////////////////
		case "email":
			// validación de Email. Chequea la sintaxis como caracteres no válidos y la
			// ausencia del @
			emailStr = eval(nomCampo).value;
			
		        var emailPat=/^(.+)@(.+)$/;
		        var specialChars="\\(\\)<>@,;:\\\\\\\"\\.\\[\\]";
		        var validChars="\[^\\s" + specialChars + "\]";
		        var quotedUser="(\"[^\"]*\")";
		        var ipDomainPat=/^\[(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})\]$/;
		        var atom=validChars + '+';
		        var word="(" + atom + "|" + quotedUser + ")";
		        var userPat=new RegExp("^" + word + "(\\." + word + ")*$");
		        var domainPat=new RegExp("^" + atom + "(\\." + atom +")*$");
		
		        var matchArray=emailStr.match(emailPat);
		        
		        if (matchArray==null) {
		                alert("La dirección de correo electrónico parece ser errónea (revise @ y puntos)");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
		                return (false);
		        }
		        
		        var user=matchArray[1]
		        var domain=matchArray[2]
		        
		        if (user.match(userPat)==null) {
				alert("El nombre de usuario de la dirección de correo no parece ser válida");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
				return (false);
		        }
		
		        var IPArray=domain.match(ipDomainPat)
		        
		        if (IPArray!=null) {
		                  for (var i=1;i<=4;i++) {
		                    if (IPArray[i]>255) {
		                        alert("La dirección IP de la dirección de correo no es válida.");
					nomCampo.focus();
					nomCampo.style.background='#FFEC66';
		                        return (false);
		                    }
		            }
		            return (true);
		        }
		
		        var domainArray=domain.match(domainPat)
		        
		        if (domainArray==null) {
		                alert("El nombre del dominio de la dirección de correo parece no ser válida.");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
				return (false);
		        }
		
		        var atomPat=new RegExp(atom,"g")
		        var domArr=domain.match(atomPat)
		        var len=domArr.length
		        
		        if (domArr[domArr.length-1].length<2 || 
		            domArr[domArr.length-1].length>3) {
				alert("La dirección de correo debe finalizar con tres letras (dominio) o dos letras (código de país).");
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
				return (false);
		        }
		
		        if (len<2) {
				var errStr="El dominio del correo no puede estar ausente (.com, .cl, etc.)";
				alert(errStr);
				nomCampo.focus();
				nomCampo.style.background='#FFEC66';
		           return (false);
		        }
			break;
		////////////////////////////////////////////////////////////////////////////////////////////////////////
	}
	return (true);
}

