//validation function and events
//come in pairs:
//the event calls the function with the event source as param
//
/*
new addition:
	uniqueData  - you can now check if a list of input's all contain
			unique values. simply insert uniqueData parameter to the 
			html input line <input id=... uniqueData>. 
			in order to use this on several lists simply assign a diffrent
			value to the uniqueData for each list
	validType=protectedFiles - protected files attribute checks if the string
			inside the element ends with .asp, .htm, .html
*/
//======================================================================
//	messages 
//======================================================================


        var MSG_BAD_CHARS=new Array(" can't contain chars:\n") ;
        var MSG_UNIQUE = new Array(" already exists")
        
        var MSG_REQUIRED=new Array(" must be assigned a value");
        var MSG_VALID_NUM=new Array(" must be a valid number");
        var MSG_VALID_IP=new Array(" must be a valid ip");
        var MSG_HOLE_NUM=new Array(" must be a whole number");
        var MSG_VAL_BETWEEN=new Array(" must contain values between ");
        var MSG_DATE_BETWEEN=new Array(" must contain dates between ");
        var MSG_STRING_LENGTH_BETWEEN=new Array(" length must be between ");
        var MSG_STRING_MAXLENGTH1=new Array(" must be no longer then ");
        var MSG_STRING_MAXLENGTH2=new Array(" characters.");
        var MSG_STRING_MAXLENGTH3=new Array(".\nIt is currently ");
              
       var MSG_BETWEEN=new Array(" And ");
	var MSG_INVALID_DATE=new Array(" isn't a valid date");
	var MSG_INVALID_TIME=new Array(" isn't a valid time");
	var MSG_INVALID_DATETIME=new Array(" isn't a valid time or date");
	var MSG_FULL_YEAR=new Array(" must have a four char year");
	var MSG_INVALID_SEP=new Array(" has an invalid seperator");
	var MSG_INVALID_EMAIL=new Array(" must be a valid email address");
        var MSG_INVALID_IMAGE=new Array (" must have a valid file extension");
	var MSG_INVALID_PATTERN=new Array(" isn't well formated");
       var MSG_FIELD_NAME=new Array ("Field");
    var MSG_INVALID_FRACTION=new Array(" has to be a legal fraction");
	var MSG_DENIED_FILE=new Array(".asp, .html, .htm extentions are not allowed");
   
//======================================================================
//	Regular expressions
//======================================================================
	var REG_EXP_EMAIL="^(^[a-zA-Z][a-zA-Z0-9\._-]+[a-zA-Z]@[a-zA-Z][a-zA-Z0-9\._]+[a-zA-Z])?$";
    var REG_EXP_IMAGE=".[jJ][pP][eE]?[gG]$|.[gG][iI][fF]$|^\s?$";
    var REG_EXP_FRACTION1="^\\d*[.]?" + "\\d{0,1}$";
	var REG_EXP_FRACTION2="^\\d*[.]?" + "\\d{0,2}$";
	var REG_EXP_FRACTION3="^\\d*[.]?" + "\\d{0,3}$";
      
       




//======================================================================

//	utilities

//======================================================================
function lngItem(item) { 
  var retValue = 0;
if (item.form != null)
  if (item.form.getAttribute("MsgLn") == "He") retValue = 1;

  if (item.getAttribute("MsgLn") == "He") retValue = 1;
  if (item.getAttribute("MsgLn") == "En") retValue = 0;
  return retValue;
}
//======================================================================
function newAlert(str,item) { 
  var msg=item.getAttribute("Msg");
  if (msg==null) alert(str); 
  else if (msg !="Silence") alert(msg);
}
//======================================================================
function display_name(item){
	var strDisplay=item.getAttribute("DisplayName");
	if(strDisplay==null||strDisplay=="")
	strDisplay=MSG_FIELD_NAME[lngItem(item)];
	return strDisplay;
}

//======================================================================

function default_value(item){
	var strDefault=item.defaultValue;
	if(strDefault==null||strDefault=="")
		strDisplay="";
	return strDefault;
}

//======================================================================

function trim_string(){
	var ichar, icount;
	var strValue=this;
	ichar=strValue.length-1;
	icount=-1;
	while(strValue.charAt(ichar)==' ' && ichar>icount)
		--ichar;
	if(ichar!=(strValue.length-1))
		strValue=strValue.slice(0,ichar+1);
	ichar=0;
	icount=strValue.length-1;
	while(strValue.charAt(ichar)==' ' && ichar<icount)
		++ichar;
	if(ichar!=0)
		strValue=strValue.slice(ichar,strValue.length);
	return strValue;
}

//======================================================================

/*
isDate function.
input: date as string in format DDMMYYYY
output: date object for valid input
		null for invalid input
*/
function checkDate(theDate){
	theDate = theDate.Trim()
	if(isNaN(Date.parse(theDate))){
		return;
	}
	else{
		//parse date as text
		//sepetarors can be '-' / '/'
		var seps = new Array('-','/');
		var sep = 'none';
		var pos;
		for(var i in seps){
			pos = theDate.indexOf(seps[i]);
			if (pos >-1){
				//sepetaror is found, search once more
				if(theDate.indexOf(seps[i],pos+1)>-1){
					sep = seps[i];
				}
				break;
			}
		}
		if (sep != 'none'){
			var arr = new Array();
			arr = theDate.split(sep);
			//check for YYYY
			if (arr[2].length != 4) return;
			//build a MMDDYYYY date
			var builtDate = arr[1] + '/' + arr[0] + '/' + arr[2];
		}
		else return;				
		var tmpDate=new Date(builtDate);
		//handle year diff due to auto date conversion
		var yearDiff=tmpDate.getFullYear()-arr[2];
		if(yearDiff!=0)tmpDate.setFullYear(tmpDate.getFullYear()-yearDiff);	
		//check month & day				
		if(tmpDate.getDate()!= arr[0] || tmpDate.getMonth()!= arr[1]-1){
			return;
		}
		else{
			//build date object
			return tmpDate;
		}
	}
}

//======================================================================

/*
isDate function.
input: date as string in format DDMMYYYY
output: date object for valid input
		null for invalid input
*/
function checkDateTime(theDateTime){
	if(isNaN(Date.parse(theDateTime))){
		return;
	}
	else{
		theDateTime = trim(theDateTime)
		theDateTime = theDateTime.split(" ")
		var theDate = theDateTime[0]
		//parse date as text
		//sepetarors for date can be '-' / '/'
		var seps = new Array('-','/');
		var dsep = 'none';
		var tsep = 'none';
		var pos;
		for(var i in seps){
			pos = theDate.indexOf(seps[i]);
			if (pos >-1){
				//sepetaror is found, search once more
				if(theDate.indexOf(seps[i],pos+1)>-1){
					dsep = seps[i];
				}
				break;
			}
		}
		var theTime = theDateTime[1]
		pos = theTime.indexOf(":");
		if (pos >-1){
			//sepetaror is found, search once more
			if(theTime.indexOf(":",pos+1)>-1){
				tsep = 'found';
			}
		}
		if ((dsep != 'none') && (tsep != 'none')){
			var arr = new Array();
			arr = theDate.split(dsep);
			//check for YYYY
			if (arr[2].length != 4) return;
			//build a MMDDYYYY date
			var builtDate = arr[1] + '/' + arr[0] + '/' + arr[2] + '/' + theDateTime[1];
		}
		else return;				
		var tmpDate=new Date(builtDate);
		//handle year diff due to auto date conversion
		var yearDiff=tmpDate.getFullYear()-arr[2];
		if(yearDiff!=0)tmpDate.setFullYear(tmpDate.getFullYear()-yearDiff);	
		//check month & day				
		if(tmpDate.getDate()!= arr[0] || tmpDate.getMonth()!= arr[1]-1){
			return;
		}
		else{
			//build date object
			return tmpDate;
		}
	}
}

//======================================================================

function formatShortDate(theDate){
	if(theDate.constructor==String)theDate=checkDate(theDate);
	var day=theDate.getDate();
	var month=theDate.getMonth() + 1;
	var year=theDate.getFullYear();
	year = new String('0000' + year);
	year = year.substring(year.length-4);
	day = new String(day);
	day = (day.length==1) ? '0'+ day : day;
	month = new String(month);
	month = (month.length==1) ? '0'+ month : month;
	var shortDate = day + '/' + month + '/' + year;
	return shortDate;
}

//======================================================================

//format date (DD/MM/YYYY string or Date object) as MM/DD/YYYY
function formatUSDate(theDate){
	if(theDate.constructor==String)theDate=checkDate(theDate);
	var day=theDate.getDate();
	var month=theDate.getMonth() + 1;
	var year=theDate.getFullYear();
	year = new String('0000' + year);
	year = year.substring(year.length-4);
	day = new String(day);
	day = (day.length==1) ? '0'+ day : day;
	month = new String(month);
	month = (month.length==1) ? '0'+ month : month;
	var shortDate = month + '/' + day + '/' + year;
	return shortDate;
}

//======================================================================

function checkNumericRange(item, lowEnd, HighEnd){
	//error mgs
	var strErrMsg=display_name(item)+ MSG_VAL_BETWEEN[lngItem(item)] + lowEnd 
        + MSG_BETWEEN[lngItem(item)] + HighEnd;
	var ItemVal=parseFloat(item.value);
	if (ItemVal<lowEnd||ItemVal>HighEnd){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;
}

//======================================================================

function checkDateRange(item, lowEnd, HighEnd){
	//error mgs
	var strErrMsg=display_name(item)+ MSG_DATE_BETWEEN[lngItem(item)];
	strErrMsg+=formatShortDate(lowEnd) + MSG_BETWEEN[lngItem(item)];
	strErrMsg+=formatShortDate(HighEnd);
	var ItemVal=checkDate(item.value);
	//check date
	var max=checkDate(HighEnd);
	var min=checkDate(lowEnd);	
	if (ItemVal<min||ItemVal>max){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;
}

//======================================================================

function checkRegExp(pattern,value){
        var re=new RegExp(pattern);
        return re.test(value);	
}

//======================================================================

function selectItem(item){
	try{
		item.focus();
		item.select();
	}
	catch(e){}
}
//======================================================================

//  item validation

//======================================================================

function es_validate_item(){
	var i=event.srcElement;
	event.returnValue=vs_validate_item(i);
}

function vs_validate_item(i) {
	var validType;
	if (null!=i.getAttribute("required")){
	 	if(!vs_non_blank(i)){
	 		return false;
	 	}
	 }
	    
	 if (null!=i.getAttribute("maxlength")){
	 	if(!vs_string_maxlength(i)){
	 		return false;
	 	}
	 }

	    	    
	 //handle other validations
	 validType=i.getAttribute("ValidType");
	 if (null!=validType){
	 	switch (validType) {
	 		case 'date' :
	 			if(!vs_valid_date(i)){
	 				return false;
	 			}
	 			break;
	 		case 'datetime' :
	 			if(!vs_valid_datetime(i)){
	 				return false;
	 			}
	 			break;
	 		case 'number' :
	 			if(!vs_valid_number(i)){
	 				return false;
	 			}
	 			break;
	 		case 'integer' :
	 			if(!vs_valid_int(i)){
	 				return false;
	 			}
	 			break;
	 		case 'ip' :
	 			if(!vs_valid_ip(i)){
	 				return false;
	 			}
	 			break;
	 		case 'email' :
	 			if(!vs_valid_email(i)){
	 				return false;
	 			}
	 			break;
	 		//ranges
	 		case 'NumericRange' :
	 			if(!vs_valid_numeric_range(i)){
	 				return false;
	 			}
	 			break;
	 		case 'DateRange' :
	 			if(!vs_valid_date_range(i)){
	 				return false;
	 			}
	 			break;	
             case 'StringLengthRange' :
	 			if(!vs_valid_string_length_range(i)){
	 				return false;
	 			}
	 			break;					
	 		case 'BadChars' :
	 			if(!vs_non_bad_chars(i)){
	 				return false;
	 			}
	 			break;	
	 		case 'protectedFiles' :
	 			if(!vs_protected_files(i)){
	 				return false;
	 			}
	 			break;				
	 	} 
	}
	 //handle data types validation
	 if (null!=i.getAttribute("DataType")){
	 	if(!vs_valid_datatype(i)){
	 		return false;
	 	}
	 }
	 //handle Regular expressions validation
	 if (null!=i.getAttribute("RegExp")){
	 	if(!vs_valid_regexp(i)){
	 		return false;
	 	}
	 }
	
	return true;
}
//======================================================================

//  form validation

//======================================================================

function es_validate_form(){
	var f=event.srcElement;
	event.returnValue=vs_validate_form(f);
}

var uniqueList;
function vs_validate_form(f) {
	
	var validType;
	uniqueList = new Array;
	for (var intLoop = 0; intLoop<f.elements.length; intLoop++){
		//handle required
	    if (null!=f.elements[intLoop].getAttribute("required")){
			if(!vs_non_blank(f.elements[intLoop])){
				return false;
			}
	    }
	    
	    if (null!=f.elements[intLoop].getAttribute("maxlength")){
			if(!vs_string_maxlength(f.elements[intLoop])){
				return false;
			}
	    }
	    
	    if (null!=f.elements[intLoop].getAttribute("uniqueData")){
			if(!vs_unique_data(f.elements[intLoop])){
				return false;
			}
	    }
	    
	       	
	    //handle other validations
	    validType=f.elements[intLoop].getAttribute("ValidType");
	    if (null!=validType){
			switch (validType) {
				case 'date' :
					if(!vs_valid_date(f.elements[intLoop])){
						return false;
					}
					break;
				case 'datetime' :
					if(!vs_valid_datetime(f.elements[intLoop])){
						return false;
					}
					break;
				case 'number' :
					if(!vs_valid_number(f.elements[intLoop])){
						return false;
					}
					break;
				case 'integer' :
					if(!vs_valid_int(f.elements[intLoop])){
						return false;
					}
					break;
				case 'ip' :
					if(!vs_valid_ip(f.elements[intLoop])){
						return false;
					}
					break;
				case 'email' :
					if(!vs_valid_email(f.elements[intLoop])){
						return false;
					}
					break;
				//ranges
				case 'NumericRange' :
					if(!vs_valid_numeric_range(f.elements[intLoop])){
						return false;
					}
					break;
				case 'DateRange' :
					if(!vs_valid_date_range(f.elements[intLoop])){
						return false;
					}
					break;	
                case 'StringLengthRange' :
					if(!vs_valid_string_length_range(f.elements[intLoop])){
						return false;
					}
					break;		
				case 'BadChars' :
					if(!vs_non_bad_chars(f.elements[intLoop])){
						return false;
					}
					break;	
				case 'protectedFiles' :
	 				if(!vs_protected_files(f.elements[intLoop])){
	 					return false;
	 				}
	 				break;							
			} 
	   }
		//handle data types validation
	    if (null!=f.elements[intLoop].getAttribute("DataType")){
			if(!vs_valid_datatype(f.elements[intLoop])){
				return false;
			}
	    }
		//handle Regular expressions validation
	    if (null!=f.elements[intLoop].getAttribute("RegExp")){
			if(!vs_valid_regexp(f.elements[intLoop])){
				return false;
			}
	    }
	}
	return true;
}
//======================================================================

//	specific validations

//======================================================================

//======================================================================

//	bad chars validations
//	checks for non existanse of specific chars

//======================================================================

function es_non_bad_chars(){
	var item=event.srcElement;
	event.returnValue=vs_non_bad_chars(item);
}

//======================================================================

function vs_non_bad_chars(item){
	//get strBad from item
	var strBad=item.getAttribute("BadChars");
	if(null==strBad||strBad.length==0)return false;
	//error mgs
	var strErrMsg=display_name(item)+ MSG_BAD_CHARS[lngItem(item)] + "'" + strBad + "'";
	for(var intLoop=0;intLoop<item.value.length;intLoop++){
		if((strBad.indexOf(item.value.charAt(intLoop))!= -1)){
			selectItem(item);
			newAlert(strErrMsg,item);
			return false;
		}
		
	}
	return true;
}

//======================================================================

//	non blank validations

//======================================================================

function es_non_blank(){
	var item=event.srcElement;
	event.returnValue=vs_non_blank(item);
}

//======================================================================

function vs_non_blank(item){
	//error mgs
	var strErrMsg= display_name(item) + MSG_REQUIRED[lngItem(item)];
	item.value = item.value.Trim();
	if(item.value.length==0){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	else return true;
}

//======================================================================

//	unique data validations

//======================================================================

function es_unique_data(){
	var item=event.srcElement;
	event.returnValue=vs_non_blank(item);
}

//======================================================================

function vs_unique_data(item){
	//error mgs
	var index,val,strErrMsg
	
	index = item.getAttribute("uniqueData").toString().Trim()
	val = item.value
	val = val.toString().Trim()
	
	if (item.tagName == "SELECT")
		strErrMsg = display_name(item) + " '" + item.options[item.selectedIndex].innerText + "'" + MSG_UNIQUE[lngItem(item)];
	else strErrMsg = display_name(item) + " '" + val + "'" + MSG_UNIQUE[lngItem(item)];
	
	val = val.toLowerCase()
	
	if (!(uniqueList[index]))
		uniqueList[index] = new Array
	if (uniqueList[index][val])
	{
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	else {
		uniqueList[index][val] = "1"
		return true;
	}
}



//======================================================================

//	string maximum length validations

//======================================================================

function es_string_maxlength(){
	var item=event.srcElement;
	event.returnValue=vs_string_maxlength(item);
}

//======================================================================

function vs_string_maxlength(item){
	//get range
	var length=item.getAttribute("maxlength");
	if(null==length||length.length==0)return false;
	
	//error mgs
	var strErrMsg=display_name(item)+ MSG_STRING_MAXLENGTH1[lngItem(item)] + 
				length + MSG_STRING_MAXLENGTH2[lngItem(item)] + 
				MSG_STRING_MAXLENGTH3[lngItem(item)] + item.value.length + 
				MSG_STRING_MAXLENGTH2[lngItem(item)];
	var ItemVal=item.value.length;
	length = parseInt(length)
	if (ItemVal>length){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;

}


//======================================================================

//	string maximum length validations

//======================================================================

function es_protected_files(){
	var item=event.srcElement;
	event.returnValue=vs_protected_files(item);
}

//======================================================================

function vs_protected_files(item){
	var four_last_chars;
	var five_last_chars;
	var value;
	var strErrMsg=MSG_DENIED_FILE[lngItem(item)];
	
	value = item.value.toString().Trim();
	
	if (value.length<4) return true;
	four_last_chars = value.substr(value.length-4).toLowerCase();
	five_last_chars = value.substr(value.length-5).toLowerCase();
	if ((four_last_chars == ".asp") || (four_last_chars == ".htm") ||
		(five_last_chars == ".html"))
	{
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	else return true;
	
}








//======================================================================

//	numeric validations

//======================================================================

function es_valid_number(){
	var item=event.srcElement;
	event.returnValue=vs_valid_number(item);
}

//======================================================================

function vs_valid_number(item){
	//error mgs
	var strErrMsg=display_name(item)+ MSG_VALID_NUM[lngItem(item)];
	
	item.value = item.value.Trim();
	if (item.value.length==0) return true;
	
	var num="-.0123456789";
	for(var intLoop=0;intLoop<item.value.length;intLoop++){
		if((num.indexOf(item.value.charAt(intLoop))==-1)||
			(item.value.indexOf('.') != item.value.lastIndexOf('.'))){
			selectItem(item);
			newAlert(strErrMsg,item);
			return false;
		}
	}
	return true;
}

//======================================================================

//	numeric integer validations

//======================================================================

function es_valid_int(){
	var item=event.srcElement;
	event.returnValue=vs_valid_int(item);
}

//======================================================================

function vs_valid_int(item){
	//error mgs
	var strErrMsg=display_name(item)+ MSG_HOLE_NUM[lngItem(item)];
	item.value = item.value.Trim();
	if (item.value.length==0) return true;
	
	if (item.value!=Math.floor(item.value)){
			selectItem(item);
			newAlert(strErrMsg,item);
			return false;
		}
	else return true;
}

//=========================================================================

//	numeric range vallidation (get the edges fro user and including them)

//=========================================================================
	
function es_valid_numeric_range(){
	var item=event.srcElement;
	event.returnValue=vs_valid_numeric_range(item);
}

//======================================================================

function vs_valid_numeric_range(item){
	//get range
	var lowEnd=item.getAttribute("RangeFrom");
	var HighEnd=item.getAttribute("RangeTo");
	if(null==lowEnd||lowEnd.length==0||null==HighEnd||HighEnd.length==0)return false;

	//check that it is a number b4 checking range
	if (!vs_valid_number(item)){
		return false;
	}
	//error mgs
	var strErrMsg=display_name(item)+ MSG_VAL_BETWEEN[lngItem(item)] + lowEnd
        + MSG_BETWEEN[lngItem(item)] + HighEnd;
	var ItemVal=parseFloat(item.value);
	if (ItemVal<lowEnd||ItemVal>HighEnd){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;
}

//======================================================================

//	ip validations

//======================================================================

function es_valid_ip(){
	var item=event.srcElement;
	event.returnValue=vs_valid_ip(item);
}

//======================================================================

function vs_valid_ip(item)
{
	var index;
	var pointPosition = new Array;
	var ItemVal=item.value.Trim();
	var strErrMsg = display_name(item) + MSG_VALID_IP[lngItem(item)]
	
	if (ItemVal == "")
		return true;
	
	for(index=0; index < ItemVal.length ; index++)
	{
		if (ItemVal.charAt(index) == '.')
			pointPosition[pointPosition.length] = index;
		if (ItemVal.charAt(index) == '-')
		{
			newAlert(strErrMsg,item);
			return false;
		}
	}
	if (pointPosition.length != 3)
	{
		newAlert(strErrMsg,item);
		return false;
	}
	if ((pointPosition[0] == 0) || (pointPosition[0]+1 == pointPosition[1]) ||
		(pointPosition[1]+1 == pointPosition[2]) ||
		(pointPosition[2]+1 == ItemVal.length) ||
		(isNaN(Math.abs(ItemVal.substring(0,pointPosition[0])))) ||
		(isNaN(Math.abs(ItemVal.substring(pointPosition[0]+1,pointPosition[1])))) ||
		(isNaN(Math.abs(ItemVal.substring(pointPosition[1]+1,pointPosition[2])))) ||
		(isNaN(Math.abs(ItemVal.substring(pointPosition[2]+1,ItemVal.length)))) ||
		(parseInt(ItemVal.substring(0,pointPosition[0])) > 255) ||
		(parseInt(ItemVal.substring(pointPosition[0]+1,pointPosition[1])) > 255) ||
		(parseInt(ItemVal.substring(pointPosition[1]+1,pointPosition[2])) > 255) ||
		(parseInt(ItemVal.substring(pointPosition[2]+1,ItemVal.length)) > 255))
	{
		newAlert(strErrMsg,item);
		return false;
	}
	
	item.value = parseInt(ItemVal.substring(0,pointPosition[0])) + "." +
			parseInt(ItemVal.substring(pointPosition[0]+1,pointPosition[1])) + "." +
			parseInt(ItemVal.substring(pointPosition[1]+1,pointPosition[2])) + "." +
			parseInt(ItemVal.substring(pointPosition[2]+1,ItemVal.length));
	return true;
}


//======================================================================

//	email validations

//======================================================================

function es_valid_email(){
	var item=event.srcElement;
	event.returnValue=vs_valid_ip(item);
}

//======================================================================

function vs_valid_email(item)
{
	var index;
	var pointPosition = new Array;
	var ItemVal=item.value.Trim();
	var strErrMsg = display_name(item) + MSG_VALID_IP[lngItem(item)]
	
	if (emailCheck(ItemVal) == false)
	{
		item.focus();
		return false;
	}
	else return true;
	
}

//======================================================================

//	date range vallidation (get the edges fro user and including them)
//	input params are date strings formated DD/MM/YYYY

//=========================================================================
	
function es_valid_date_range(){
	var item=event.srcElement;
	event.returnValue=vs_valid_date_range(item);
}

//======================================================================

function vs_valid_date_range(item){
	//get range
	var lowEnd=item.getAttribute("RangeFrom");
	var HighEnd=item.getAttribute("RangeTo");
	if(null==lowEnd||lowEnd.length==0||null==HighEnd||HighEnd.length==0)return false;
	//check that it is a date b4 checking range
	if (!vs_valid_date(item)){
		return false;
	}
	//error mgs
	var strErrMsg=display_name(item)+ MSG_DATE_BETWEEN[lngItem(item)];
	strErrMsg+=formatShortDate(lowEnd) + MSG_BETWEEN[lngItem(item)];
	strErrMsg+=formatShortDate(HighEnd);
	var ItemVal=checkDate(item.value);
	var max=checkDate(HighEnd);
	var min=checkDate(lowEnd);	
	if (ItemVal<min||ItemVal>max){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;
}
//=========================================================================
	
function es_valid_string_length_range(){
	var item=event.srcElement;
	event.returnValue=vs_valid_date_range(item);
}

//======================================================================

function vs_valid_string_length_range(item){
	//get range
	var lowEnd=item.getAttribute("RangeFrom");
	var HighEnd=item.getAttribute("RangeTo");
	if(null==lowEnd||lowEnd.length==0||null==HighEnd||HighEnd.length==0)return false;
	
	//error mgs
	var strErrMsg=display_name(item)+ MSG_STRING_LENGTH_BETWEEN[lngItem(item)];
	strErrMsg+=lowEnd + MSG_BETWEEN[lngItem(item)];
	strErrMsg+=HighEnd;
	var ItemVal=item.value.length;
		
	if (ItemVal<lowEnd||ItemVal>HighEnd){
		selectItem(item);
		newAlert(strErrMsg,item);
		return false;
	}
	return true;
}


//======================================================================

//	data types validations (for SQL Server 7.0)
//	assumes a numeric / date validation is performed first

//======================================================================

function es_valid_datatype(){
	var item=event.srcElement;
	event.returnValue=vs_valid_datatype(item);
}

//======================================================================

function vs_valid_datatype(item){
	switch(item.getAttribute("DataType")){
		case "int":
			if(!vs_valid_int(item))return false;
			if(!checkNumericRange(item,-2147483648,2147483647))return false;
			break;
		case "smallint":
			if(!vs_valid_int(item))return false;		
			if(!checkNumericRange(item,-32768,32767))return false;
			break;
		case "tinyint":
			if(!vs_valid_int(item))return false;		
			if(!checkNumericRange(item,0,255))return false;
			break;
		case "money":
			if(!vs_valid_number(item))return false;
			//val range:-922337203685477.5808,922337203685477.5807
			//rounded inside because of system inaccuracy
			if(!checkNumericRange(item,-922337203685477.5,922337203685477.5))return false;
			break;
		case "smallmoney":
			if(!vs_valid_number(item))return false;		
			if(!checkNumericRange(item,-214748.3648,214748.3647))return false;
			break;
		case "float":
			if(!vs_valid_number(item))return false;		
			if(!checkNumericRange(item,-1.79E+308,1.79E+308))return false;
			break;
		case "real":
			if(!vs_valid_number(item))return false;	
			if(!checkNumericRange(item,-3.40E+38,3.40E+38))return false;
			break;
		case "numeric":
			if(!vs_valid_number(item))return false;		
			var percision=item.getAttribute("DataPrecision");
			var scale=item.getAttribute("DataScale");
			if(null==percision||percision.length==0)percision=0;
			if(null==scale||scale.length==0)scale=0;
			var upBound=Math.pow(10,percision-scale)-Math.pow(10,-1*scale);
			var lowBound=-1*upBound;
			if(!checkNumericRange(item,lowBound,upBound))return false;
			break;
		case "date":
			if(!vs_valid_date(item))return false;		
			if(!checkDateRange(item,"1/1/1753","31/12/9999"))return false;
			break;
		case "smalldate":
			if(!vs_valid_date(item))return false;				
			if(!checkDateRange(item,"1/1/1900","6/7/2079"))return false;
			break;
	}
	return true;
}

//======================================================================

//	regular expressions validations

//======================================================================

function es_valid_regexp(){
	var item=event.srcElement;
	event.returnValue=vs_valid_regexp(item);
}

//======================================================================


function vs_valid_regexp(item){
	//alert("here1");
	var regExp=item.getAttribute("RegExp");
	//error mgs
	var strErrMsg=display_name(item);
	
	if(regExp!="email"){
	
		if(regExp.search(regExp)!=-1){
			var strSplit=regExp.split(",");
			switch(strSplit[1]){
				case "1":
					regExp=REG_EXP_FRACTION1;
					strErrMsg+=MSG_INVALID_FRACTION[lngItem(item)];
					strErrMsg+=" with one digit after point";
					break;
					
				case "3":
					regExp=REG_EXP_FRACTION3;
					strErrMsg+=MSG_INVALID_FRACTION[lngItem(item)];
					strErrMsg+=" with 3 digit after point";
					break;
				default:
					regExp=REG_EXP_FRACTION2;
					strErrMsg+=MSG_INVALID_FRACTION[lngItem(item)];
					strErrMsg+=" with 2 digit after point";
					break;
					
					
			}
		}
	}
	else{
	
		switch(item.getAttribute("RegExp")){
			case "email":
				alert("here" & REG_EXP_EMAIL);
				regExp=REG_EXP_EMAIL;
				strErrMsg+=MSG_INVALID_EMAIL[lngItem(item)];
				break;
			
			default:
				strErrMsg+=MSG_INVALID_PATTERN[lngItem(item)];
				break;
		}
	}
	
	alert("regExp is : " + regExp);
	alert("item.value is : " + item.value);
	
	if(!checkRegExp(regExp,item.value)){
		selectItem(item);
		alert(strErrMsg);
		return false;
	}
	return true;
}


function emailCheck (emailStr) {
	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 +")*$")


	if(emailStr.length == 0){
//		alert("in if");
		return true;	 
	}


	
	var matchArray=emailStr.match(emailPat)
	if (matchArray==null) {
		alert("Email address seems incorrect (check @ and .'s)")
		return false
	}
	var user=matchArray[1]
	var domain=matchArray[2]

	// See if "user" is valid 
	if (user.match(userPat)==null) {
	    // user is not valid
	    alert("The username doesn't seem to be valid.")
	    return false
	}

	/* if the e-mail address is at an IP address (as opposed to a symbolic
	   host name) make sure the IP address is valid. */
	var IPArray=domain.match(ipDomainPat)
	if (IPArray!=null) {
	    // this is an IP address
		  for (var i=1;i<=4;i++) {
		    if (IPArray[i]>255) {
		        alert("Destination IP address is invalid!")
			return false
		    }
	    }
	    return true
	}

	// Domain is symbolic name
	var domainArray=domain.match(domainPat)
	if (domainArray==null) {
		alert("The domain name doesn't seem to be valid.")
	    return false
	}

	/* domain name seems valid, but now make sure that it ends in a
	   three-letter word (like com, edu, gov) or a two-letter word,
	   representing country (uk, nl), and that there's a hostname preceding 
	   the domain or country. */

	/* Now we need to break up the domain to get a count of how many atoms
	   it consists of. */
	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) {
	   // the address must end in a two letter or three letter word.
	   alert("The address must end in a three-letter domain, or two letter country.")
	   return false
	}

	// Make sure there's a host name preceding the domain.
	if (len<2) {
	   var errStr="This address is missing a hostname!"
	   alert(errStr)
	   return false
	}

	// If we've gotten this far, everything's valid!
	return true;
}







//======================================================================

//	date validations

//======================================================================

function es_valid_date(){
	var item=event.srcElement;
	event.returnValue=vs_valid_date(item);
}

//======================================================================

function vs_valid_date(item){
	//error mgs
	var strErrMsg=display_name(item);
	//get input date as string
	item.value = item.value.Trim()
	var inputDate = new String(item.value);
	//if empty
	if (inputDate==null || inputDate=='') return true;
	//check if numeric
	if(isNaN(Date.parse(inputDate))){
		selectItem(item);
		newAlert(strErrMsg + MSG_INVALID_DATE[lngItem(item)],item);
		return false;
	}
	else{
		// convert to MMDDYYYY format
		//===========================
		//parse date as text
		//seperators can be '-' / '/'
		var seps = new Array('-','/');
		var sep = 'none';
		var pos;
		for(var i in seps){
			pos = inputDate.indexOf(seps[i]);
			if (pos >-1){
				//seperator is found, search once more
				if(inputDate.indexOf(seps[i],pos+1)>-1){
					sep = seps[i];
				}
				break;
			}
		}
		if (sep != 'none'){
			var arr = new Array();
			arr = inputDate.split(sep);
			//check for YYYY
			if (arr[2].length != 4){
				selectItem(item);
				newAlert(strErrMsg + MSG_FULL_YEAR[lngItem(item)],item);
				return false;
			}
			//build a MMDDYYYY date
			var builtDate = arr[1] + '/' + arr[0] + '/' + arr[2];
		}
		else{
			selectItem(item);
			newAlert(strErrMsg + MSG_INVALID_SEP[lngItem(item)],item);
			return false;
		}
		
		// compare with a Date built on builtDate
		//=======================================
		var tmpDate=new Date(builtDate);
		//handle year diff due to auto date conversion
		var yearDiff=tmpDate.getFullYear()-arr[2];
		if(yearDiff!=0)tmpDate.setFullYear(tmpDate.getFullYear()-yearDiff);
		//check month & day	
		if(tmpDate.getDate()!= arr[0] || tmpDate.getMonth()!= arr[1]-1){
			selectItem(item);
			newAlert(strErrMsg + MSG_INVALID_DATE[lngItem(item)],item);
			return false;
		}
		else{
			//return DD/MM/YYYY formated date
			item.value = formatShortDate(tmpDate);
			return true;
		}
	}
}

//======================================================================

//======================================================================

//	date time validations

//======================================================================

function es_valid_datetime(){
	var item=event.srcElement;
	event.returnValue=vs_valid_datetime(item);
}

//======================================================================

function vs_valid_datetime(item){
	//error mgs
	var strErrMsg=display_name(item);
	//get input date as string
	var inputDateTime = new String(item.value);
	var inputDate
	
	//if empty
	if (inputDateTime==null || inputDateTime=='') return true;
	
	inputDateTime = trim(inputDateTime)
	inputDateTime = inputDateTime.split(" ")
	if (inputDateTime.length != 2)
	{
		selectItem(item);
		newAlert(strErrMsg + MSG_INVALID_DATETIME[lngItem(item)],item);
		return false;
	}
	inputDate = inputDateTime[0];
	//check if numeric
	if(isNaN(Date.parse(inputDate))){
		selectItem(item);
		newAlert(strErrMsg + MSG_INVALID_DATE[lngItem(item)],item);
		return false;
	}
	else{
		// convert to MMDDYYYY format
		//===========================
		//parse date as text
		//seperators can be '-' / '/'
		var seps = new Array('-','/');
		var sep = 'none';
		var pos;
		for(var i in seps){
			pos = inputDate.indexOf(seps[i]);
			if (pos >-1){
				//seperator is found, search once more
				if(inputDate.indexOf(seps[i],pos+1)>-1){
					sep = seps[i];
				}
				break;
			}
		}
		if (sep != 'none'){
			var arr = new Array();
			arr = inputDate.split(sep);
			//check for YYYY
			if (arr[2].length != 4){
				selectItem(item);
				newAlert(strErrMsg + MSG_FULL_YEAR[lngItem(item)],item);
				return false;
			}
			//build a MMDDYYYY date
			var builtDate = arr[1] + '/' + arr[0] + '/' + arr[2];
		}
		else{
			selectItem(item);
			newAlert(strErrMsg + MSG_INVALID_SEP[lngItem(item)],item);
			return false;
		}
		
		// compare with a Date built on builtDate
		//=======================================
		var tmpDate=new Date(builtDate);
		//handle year diff due to auto date conversion
		var yearDiff=tmpDate.getFullYear()-arr[2];
		if(yearDiff!=0)tmpDate.setFullYear(tmpDate.getFullYear()-yearDiff);
		//check month & day	
		if(tmpDate.getDate()!= arr[0] || tmpDate.getMonth()!= arr[1]-1){
			selectItem(item);
			newAlert(strErrMsg + MSG_INVALID_DATE[lngItem(item)],item);
			return false;
		}
		else{
			//return DD/MM/YYYY formated date
			
		}
	}
	if (vs_valid_time(item,inputDateTime[1]) == false)
		return false;
	//return DD/MM/YYYY HH:mm:SS formated datetime
	item.value = formatShortDate(tmpDate) + " " + inputDateTime[1];
	return true;
	
}

function vs_valid_time(item,value){
	
	//error mgs
	var strErrMsg=display_name(item);
	//get input date as string
	var inputTime = value;
	//if empty
	if (inputTime==null || inputTime=='') return true;
	
	//parse date as time
	//seperators can be :
	var arr = inputTime.split(":")
	
	if (arr.length != 3)
	{
		selectItem(item);
		newAlert(strErrMsg + MSG_INVALID_TIME[lngItem(item)],item);
		return false;
	}
	else if ((isNaN(arr[0]) == true) || (isNaN(arr[1]) == true) || (isNaN(arr[2]) == true) ||
			(arr[0] < 0) || (arr[1] < 0) || (arr[2] < 0) ||
			(arr[0] > 23) || (arr[1] > 59) || (arr[2] > 59) ||
			(arr[0] == "") || (arr[1] == "") || (arr[2] == ""))
	{
		selectItem(item);
		newAlert(strErrMsg + MSG_INVALID_TIME[lngItem(item)],item);
		return false;
	}
	else return true;
}

function trim(inputString) {
   // Removes leading and trailing spaces from the passed string. Also removes
   // consecutive spaces and replaces it with one space. If something besides
   // a string is passed in (null, custom object, etc.) then return the input.
   if (typeof inputString != "string") { return inputString; }
   var retValue = inputString;
   var ch = retValue.substring(0, 1);
   while (ch == " ") { // Check for spaces at the beginning of the string
      retValue = retValue.substring(1, retValue.length);
      ch = retValue.substring(0, 1);
   }
   ch = retValue.substring(retValue.length-1, retValue.length);
   while (ch == " ") { // Check for spaces at the end of the string
      retValue = retValue.substring(0, retValue.length-1);
      ch = retValue.substring(retValue.length-1, retValue.length);
   }
   while (retValue.indexOf("  ") != -1) { // Note that there are two spaces in the string - look for multiple spaces within the string
      retValue = retValue.substring(0, retValue.indexOf("  ")) + retValue.substring(retValue.indexOf("  ")+1, retValue.length); // Again, there are two spaces in each of the strings
   }
   return retValue; // Return the trimmed string back to the user
} // Ends the "trim" function



//======================================================================


//======================================================================

//	build the validation object

//======================================================================

function validation_setup(){

	this.eventValidateForm=es_validate_form;	
	this.ValidateForm=vs_validate_form;
    this.eventValidateItem=es_validate_item;
    this.ValidateUniqueData=vs_unique_data;
    this.eventUniqueData=es_unique_data;   
    
    this.eventValidateMaxLength=es_string_maxlength;
    this.ValidateMaxLength=vs_string_maxlength
	
	this.ValidateItem=vs_validate_item;
	this.eventValidBadChars=es_non_bad_chars;
	this.ValidBadChars=vs_non_bad_chars;
	this.eventNonBlank=es_non_blank;
	this.NonBlank=vs_non_blank;
	this.eventProtectedFile=es_protected_files;
	this.ProtectedFile=vs_valid_number;
	this.eventValidNumber=es_valid_number;
	this.ValidNumber=vs_valid_number;
	this.eventValidIP=es_valid_ip;
	this.ValidIP=vs_valid_ip;
	this.eventValidEmail=es_valid_email;
	this.ValidEmail=vs_valid_email;
	this.eventValidInteger=es_valid_int;
	this.ValidInteger=vs_valid_int;
	this.eventValidNumericRange=es_valid_numeric_range;
	this.ValidNumericRange=vs_valid_numeric_range;
	this.eventValidDateRange=es_valid_date_range;
	this.ValidDateRange=vs_valid_date_range;
       this.eventValidSrtingLengthRange=es_valid_string_length_range;
	this.ValidStringLengthRange=vs_valid_string_length_range;
	this.eventValidDataType=es_valid_datatype;
	this.ValidDataType=vs_valid_datatype;
	this.eventValidRegExp=es_valid_regexp;
	this.ValidRegExp=vs_valid_regexp;
	//this.Validemail=vs_valid_email;
	this.eventValidDate=es_valid_date;
	this.ValidDate=vs_valid_date;
	this.eventValidDateTime=es_valid_datetime;
	this.ValidDateTime=vs_valid_datetime;
	return this;
}
//======================================================================

//	object extention and creation

//======================================================================


//extend string and date objects
String.prototype.Trim=trim_string;

//create validation object
var validation=new validation_setup();

