var F_TEXTONLY = 0;
var F_EMAIL = 1;
var F_CARDNUMBER = 2;
var F_NUMBER = 3;
var F_ALPHA_NUMERIC = 4;
var F_PHONE = 5;

var FIELD_IMAGE_VALID = "/images/form-approved.png";
var FIELD_IMAGE_INVALID = "/images/form-error.png";

var NAVIGATOR_IS_IE6 = (navigator.userAgent.indexOf("MSIE 6") != -1);

var AJAXValidator = function(objOptions){
	this.Formats=new Array();
	this.Formats[F_TEXTONLY] = [this.checkTextOnly, "must be made of only text, no numbers or special characters"];
	this.Formats[F_EMAIL] = [this.checkEmail, "must be a properly formatted email address"];
	this.Formats[F_CARDNUMBER] = [this.checkCardNumber, "must be a valid credit/debit card number"];
	this.Formats[F_NUMBER] = [this.checkNumber, "must be a numerical value"];
	this.Formats[F_ALPHA_NUMERIC] = [this.checkAlphaNum, "must contain only letters and numbers"];
	this.Formats[F_PHONE]=new Array(this.checkPhone, "must be a phone/fax number");
	
	this.Fields = [];
	this.Form = objOptions.Form;
	this.Valid = false;
}

AJAXValidator.prototype.AddField = function(objOptions){
	this.Fields[objOptions.ID] = {
		ID : objOptions.ID,
		Name : objOptions.Name,
		Format : objOptions.Format,
		Required : objOptions.Required,
		Ignore : false,
		Valid : true,
		Error : ""
	};
	if(NAVIGATOR_IS_IE6) return;
	var objField = $(objOptions.ID);
	if(objField){
		var sFieldType = objField.tagName.toLowerCase();
		var sFieldEvent;
		switch(sFieldType){
			case "input":
				sFieldEvent = "blur";
				break;
			case "select":
				sFieldEvent = "change";
				break;
			default:
				sFieldEvent = "blur";
		}
		Event.observe(objField, sFieldEvent, this.Run.bindAsEventListener(this));
		if(!$("AV_" + objOptions.ID + "_Result")){
			var sHTML = "<div id=\"AV_" + objOptions.ID + "_Result\" style=\"display: inline; margin: 0px 5px 0px 5px;\"></div>";
			Element.insert($(objOptions.ID), {after : sHTML});
		}
	}
}

AJAXValidator.prototype.AddFormat = function(objOptions){
	var iFormatID = this.Formats.length;
	this.Formats[iFormatID] = [objOptions.Validator, objOptions.ErrorMessage];
	return iFormatID;
}

AJAXValidator.prototype.Run = function(objEvent){
	var objElement = objEvent ? Event.element(objEvent) : this.Form.elements[this.Form.elements.length - 1];
	var bShowValidation = true;
	this.Valid = true;
	for(var i=0; i<this.Form.elements.length; i++){
		var sElementTag = this.Form.elements[i].tagName.toLowerCase();
		if(sElementTag == "input" || sElementTag == "textarea" || sElementTag == "select"){
			var objField = this.Fields[this.Form.elements[i].name];
			if(objField){
				if(!objField.Ignore){
					var sValue = this.Form.elements[i].value;
					if(objField.Required){
						if(sValue.blank()){
							objField.Valid = false;
							objField.Error = "The field '" + objField.Name + "' must be filled.";
						}
						else{
							objField.Valid = true;
							objField.Error = "";
						}
					}
					else{
						objField.Valid = true;
						objField.Error = "";
					}
					if(objField.Format != null && !sValue.empty()){
						var aFormat = this.Formats[objField.Format];
						var objFunction = aFormat[0];
						var bResult = objFunction(sValue);
						if(bResult){
							objField.Valid = true;
							objField.Error = "";
						}
						else{
							objField.Valid = false;
							objField.Error = "The field '" + objField.Name + "' " + aFormat[1] + ".";
						}
					}
					var sHTML = "";
					if(objField.Valid){
						sHTML = "<img src=\"" + FIELD_IMAGE_VALID + "\" />";
					}
					else{
						this.Valid = false;
						sHTML = "<a class=\"av_tooltip_wrapper\"><img src=\"" + FIELD_IMAGE_INVALID + "\" /><span class=\"av_tooltip_box\">" + objField.Error + "</span></a>";
					}
					if(bShowValidation && !document.all){
						$("AV_" + objField.ID + "_Result").update(sHTML);
					}
				}
			}
			if(this.Form.elements[i].name == objElement.name) bShowValidation = false;
		}
	}
}

AJAXValidator.prototype.checkTextOnly = function(txt){
	var exp=new RegExp("^[a-z. ]{0,}$", "i");
	return exp.test(txt);
}

AJAXValidator.prototype.checkEmail = function(email){
	if(email=="") return true;
	var exp=new RegExp("^[a-z0-9_.\-]{3,}@[a-z0-9.\-]{3,}\.[a-z]{2,3}$", "i");
	return exp.test(email);
}

AJAXValidator.prototype.checkPassword = function(txt){
	var exp=new RegExp("^[A-Za-z0-9]{5,15}$");
	return exp.test(txt);
}

AJAXValidator.prototype.checkPhone = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[0-9( )+,.\-]{5,}$");
	return exp.test(txt);
}

AJAXValidator.prototype.checkZipCode = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[0-9]{5}$", "i");
	return exp.test(txt);
}

AJAXValidator.prototype.checkCAZipCode = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[a-z0-9]{3} ?[a-z0-9]{3}$", "i");
	return exp.test(txt);
}

AJAXValidator.prototype.checkUSA_CA_ZipCode = function(txt){
	if(txt=="") return true;
	return (checkZipCode(txt) || checkCAZipCode(txt));
}

AJAXValidator.prototype.checkCardNumber = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[0-9 .\-]{15,16}$");
	return exp.test(txt);
}

AJAXValidator.prototype.checkNumber = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[0-9.]{1,}$");
	return exp.test(txt);
}

AJAXValidator.prototype.checkAlphaNum = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[a-z0-9]{1,}$", "i");
	return exp.test(txt);
}

AJAXValidator.prototype.checkPhone = function(txt){
	if(txt=="") return true;
	var exp=new RegExp("^[0-9( )+,.\-]{5,}$");
	return exp.test(txt);
}
