// Variable Declarations

var digits = "0123456789";

var lowercaseLetters = "abcdefghijklmnopqrstuvwxyz";

var uppercaseLetters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";

// whitespace characters (Reg Ex)
var whitespace = " \t\n\r";

// decimal point character differs by language and culture
var decimalPointDelimiter = ".";

// non-digit characters which are allowed in phone numbers
var phoneNumberDelimiters = "()- ";

// characters which are allowed in US phone numbers
var validUSPhoneChars = digits + phoneNumberDelimiters;

// characters which are allowed in international phone numbers
// (a leading + is OK)
var validWorldPhoneChars = digits + phoneNumberDelimiters + "+";

// non-digit characters which are allowed in 
// Social Security Numbers
var SSNDelimiters = "- ";

// characters which are allowed in Social Security Numbers
var validSSNChars = digits + SSNDelimiters;

// U.S. Social Security Numbers have 9 digits.
// They are formatted as 123-45-6789.
var digitsInSocialSecurityNumber = 9;

// U.S. phone numbers have 10 digits.
// They are formatted as 123 456 7890 or (123) 456-7890.
var digitsInUSPhoneNumber = 10;

// non-digit characters which are allowed in ZIP Codes
var ZIPCodeDelimiters = "-";

// our preferred delimiter for reformatting ZIP Codes
var ZIPCodeDelimeter = "-";

// characters which are allowed in Social Security Numbers
var validZIPCodeChars = digits + ZIPCodeDelimiters;

// U.S. ZIP codes have 5 or 9 digits.
// They are formatted as 12345 or 12345-6789.
var digitsInZIPCode1 = 5;
var digitsInZIPCode2 = 9;

var defaultEmptyOK = false;

function LeapYear(year) {
	if ((year/4) != Math.floor(year/4)) return false;
	if ((year/100) != Math.floor(year/100)) return true;
	if ((year/400) != Math.floor(year/400)) return false;
	return true;
}

function stripZeros(inputStr) {
	var result = inputStr;
	while (result.substring(0, 1) == "0") {
		result = result.substring(1, result.length);
	}
	return result;
}

// general purpose function to see if an input value has been entered at all
function isEmpty(s) {
	return ((s == null) || (s.length == 0))
}

// general purpose function to see if a suspected numeric input is a positive integer
function isNumber(inputStr) {
	for (var i = 0; i < inputStr.length; i++) {
		var oneChar = inputStr.substring(i, i + 1);
		if (oneChar < "0" || oneChar > "9") {
			return false;
		}
	}
	return true;
}

// function to determine if value is in acceptable range for this application
function inRange(inputStr, lo, hi) {
	var num = parseInt(inputStr)
	if (num < lo || num > hi) {
		return false;
	}
	return true;
}

function validateMonth(field) {
	var input = stripZeros(field.value); //
	if (isEmpty(input)) {
		alert("Be sure to enter a month value.");
		select(field);
		return false;
	} else {
		if (!isNumber(input)) {
			alert("Month entries must be numbers only.");
			select(field);
			return false;
		} else {
			if (!inRange(input, 1, 12))
			{
				alert("Enter a month number between 1 (January) and 12 (December).");
				select(field);
				return false;
			}
		}
	}
	return true;
}

function validateDate(field, varMonth, varYear) {
	var input = stripZeros(field.value); //
	var monthField = varMonth;
	var yearField = varYear;
	
	if (isEmpty(input)) {
		alert("Be sure to enter a date value.");
		select(field);
		return false;
	} else {
		if (!isNumber(input)) {
			alert("Date entries must be numbers only.");
			select(field);
			return false;
		} else {
			if (!validateMonth(monthField)) return false;
			var monthVal = parseInt(stripZeros(monthField.value));
			
			tmpYear = new Number(yearField.value); //
			if (LeapYear(tmpYear)) {
				var monthMax = new Array(31,31,29,31,30,31,30,31,31,30,31,30,31);
			} else {
				var monthMax = new Array(31,31,28,31,30,31,30,31,31,30,31,30,31);
			}
			
			var top = monthMax[monthVal];
			if (!inRange(input, 1, top)) {
				alert("Enter a number between 1 and " + top + ".");
				select(field);
				return false;
			}
		}
	}
	
	return true;
}

function validateYear(field) {
	var input = stripZeros(field.value);
	if (isEmpty(input)) {
		alert("Be sure to enter a year value.");
		select(field);
		return false;
	} else {
		if (!isNumber(input)) {
			alert("Entries must be numbers only.");
			select(field);
			return false;
		} else {
			if (!inRange(input, 1900, 2090)) {
				alert("Enter a four digit year.");
				select(field);
				return false;
			}
		}
	}
	
	return true;
}

function select(field) {
	// Note: Cannot be used for selection boxes.
	field.focus();
	field.select();
}

function isWhitespace(s) {
	var i;
	
	// Is s empty?
	if (isEmpty(s)) return true;
	
	// Search through string's characters one by one
	// until we find a non-whitespace character.
	// When we do, return false; if we don't, return true.
	
	for (i = 0; i < s.length; i++) {
		// Check that current character isn't whitespace.
		var c = s.charAt(i);
		
		if (whitespace.indexOf(c) == -1) return false;
	}
	
	// All characters are whitespace.
	return true;
}

function isDigit(c) {
	return ((c >= "0") && (c <= "9"))
}

function isLetter(c) {
	return (((c >= "a") && (c <= "z")) || ((c >= "A") && (c <= "Z")))
}

function isLetterOrDigit(c) {
	return (isLetter(c) || isDigit(c))
}

function isInteger(s) {
	var i;
	
	if (isEmpty(s))
		if (isInteger.arguments.length == 1) return defaultEmptyOK;
		else return (isInteger.arguments[1] == true);
	
	// Search through string's characters one by one
	// until we find a non-numeric character.
	// When we do, return false; if we don't, return true.
	
	for (i = 0; i < s.length; i++) {
		// Check that current character is number.
		var c = s.charAt(i);
		
		if (!isDigit(c)) return false;
	}
	// All characters are numbers.
	return true;
}

function isFloat(s) {
	var i;
	var seenDecimalPoint = false;
	
	if (isEmpty(s))
		if (isFloat.arguments.length == 1) return defaultEmptyOK;
		else return (isFloat.arguments[1] == true);
	
	if (s == decimalPointDelimiter) return false;
	
	// Search through string's characters one by one
	// until we find a non-numeric character.
	// When we do, return false; if we don't, return true.
	
	for (i = 0; i < s.length; i++) {
		// Check that current character is number.
		var c = s.charAt(i);
		
		if ((c == decimalPointDelimiter) && !seenDecimalPoint) seenDecimalPoint = true;
		else if (!isDigit(c)) return false;
	}
	
	// All characters are numbers.
	return true;
}

function isUSPhoneNumber(s) {

	if (isEmpty(s)) 
		return false;
		
	//Assume the format is XXX-XXX-XXXX
	var sspl =  s.split("-");
	var sArea = sspl[0];
	var sExch = sspl[1];
	var sDig  = sspl[2];

	if((sArea.length != 3) || (!isInteger(sArea)))
		return false;
		
	if((sExch.length != 3) || (!isInteger(sExch)))
		return false;
	
	if((sDig.length != 4) || (!isInteger(sDig)))
		return false;
		
	return true;
}

function isInternationalPhoneNumber(s) {
	if (isEmpty(s))
		if (isInternationalPhoneNumber.arguments.length == 1) return defaultEmptyOK;
		else return (isInternationalPhoneNumber.arguments[1] == true);
	return (isPositiveInteger(s))
}

function isSSN(s) {
//&& s.length == digitsInSocialSecurityNumber
	return (isInteger(s))
}

function isZIPCode(s) {
	if (isEmpty(s))
		if (isZIPCode.arguments.length == 1) return defaultEmptyOK;
	else return (isZIPCode.arguments[1] == true);
	return (isInteger(s) && ((s.length == digitsInZIPCode1) || (s.length == digitsInZIPCode2)))
}

function isEmail(s) {
	if (isEmpty(s))
		if (isEmail.arguments.length == 1) return defaultEmptyOK;
		else return (isEmail.arguments[1] == true);
	
	// is s whitespace?
	if (isWhitespace(s)) return false;
	
	// there must be >= 1 character before @, so we
	// start looking at character position 1 
	// (i.e. second character)
	var i = 1;
	var sLength = s.length;
	
	// look for @
	while ((i < sLength) && (s.charAt(i) != "@")) {
		i++;
	}

	if ((i >= sLength) || (s.charAt(i) != "@"))
		return false;
	else 
		i += 2;
	
	// look for.
	while ((i < sLength) && (s.charAt(i) != ".")) {
		i++;
	}
	
	// there must be at least one character after the .
	if ((i >= sLength - 1) || (s.charAt(i) != ".")) 
		return false;
	else
		return true;
}

// Limit the number of characters per textarea
function textCounter(field, friendlyname, maxlimit, showAlert, goodColor, badColor) {
	if (field.value.length > maxlimit) {
		if(showAlert)
			alert("You have reached the max length of this field.\nThe limit for " + friendlyname + " is " + maxlimit + " characters.\nPlease delete " + (field.value.length - maxlimit) + " characters.");
		field.style.background = badColor;
		//field.focus();
		return false;
	} else {
		field.style.background = goodColor;
		return true;
	}
	/* Sample usage:
		<!--- Textarea tag using the textCounter function --->
		<textarea name="short_description" cols="37" rows="7"
		onKeyDown="textCounter(this,'Short Description',255)"
		onKeyUp="textCounter(this,'Short Description',255)"></textarea>
	*/
}

function isCurrency(curr) {
	//remove all occurences of '$' and ',' and check if what's left is a number
	var invalidChars = "$,"
	for(i = 0; i < curr.length; i++)
		if(invalidChars.indexOf(curr.charAt(i)) >= 0)
			curr = curr.substring(0, i) + curr.substring(i+1, curr.length);
	return !(isNaN(curr) || parseInt(curr * 100) <= 0);
}

function isPercent(str) {
	//remove all occurences of '%' and ',' and check if what's left is a number
	var invalidChars = "%,"
	for(i = 0; i < str.length; i++)
		if(invalidChars.indexOf(str.charAt(i)) >= 0)
			str = str.substring(0, i) + str.substring(i + 1, str.length);
	return !isNaN(str);
}

function formatCurrency(strValue) {
	strValue = strValue.toString().replace(/\$|\,/g,'');
	dblValue = parseFloat(strValue);
				
	blnSign = (dblValue == (dblValue = Math.abs(dblValue)));
	dblValue = Math.floor(dblValue * 100 + 0.50000000001);
	intCents = dblValue % 100;
	strCents = intCents.toString();
	dblValue = Math.floor(dblValue / 100).toString();
	if (intCents < 10)
		strCents = "0" + strCents;
	for (var i = 0; i < Math.floor((dblValue.length - (1 + i)) / 3); i++)
		dblValue = dblValue.substring(0, dblValue.length - (4 * i + 3)) + ',' +
			dblValue.substring(dblValue.length - (4 * i + 3));
	return (((blnSign)?'':'-') + '$' + dblValue + '.' + strCents);
}

function stripWhitespace(s) {
	var i;
	var regEx = " \t\n\r";
	var returnString = "";
				
	for (i = 0; i < s.length; i++) {
		// Check that current character isn't whitespace.
		var c = s.charAt(i);
		if (regEx.indexOf(c) == -1) returnString += c;
	}
	return returnString;
}

function isDate(s) {
	var vMonth;
	var vYear;
	var vDay;
	var sspl;
		
	//Assume date is MM/DD/YYYY
	sspl = s.split("/");
	vMonth = sspl[0];
	vDay = sspl[1];
	vYear = sspl[2];

	if((!isInteger(vMonth))||(!isInteger(vDay))||(!isInteger(vYear))){
		return false;
	}

	if ((vMonth < 1) || (vMonth > 12)){
	 return false;
	}
	var monthVal = parseInt(stripZeros(vMonth));

	var tmpYear = new Number(vYear); //

	if (LeapYear(tmpYear)) {
		var monthMax = new Array(31,31,29,31,30,31,30,31,31,30,31,30,31);
	} else {
		var monthMax = new Array(31,31,28,31,30,31,30,31,31,30,31,30,31);
	}

	var top = new Number(monthMax[monthVal]);
	var cDay = new Number(vDay);

	if (cDay < 1 || cDay > top) {
		//alert("Enter a number between 1 and " + top + " for Month.");
		//select(field);
		return false;
	}

	if (vYear.length != 4){

		return false;
	}

	return true;
}
