/* validation */
/* standard regex tests can be given to data-validation without any edits to the logic 
   special cases */
   
var validationCase = new Array();
validationCase["url"] = {rgx:/(http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?/, errorString:"Invalid URL<br />"}
validationCase["phone4"] = {rgx:/((^\d{10}$)?)/, errorString:"Invalid Phone Number<br />"}
validationCase["phone3"] = {rgx:/(^\d{3}?( )?\d{3}( )?\d{4})$/, errorString:"Invalid Phone Number<br />"}
validationCase["phone2"] = {rgx:/^1?-? ?\(?\d{3}\)?-? ?\d{3} ?-?\d{4}$/, errorString:"Invalid Phone Number<br />"}
validationCase["phone"] = {rgx:/^1?-? ?\(?\d{3}\)?-? ?\d{3} ?-?\d{4}$/, errorString:"Invalid Phone Number<br />"}
validationCase["zip"] = {rgx:/(^\d{5}(-\d{4})?$)|(^[ABCEGHJKLMNPRSTVXY]{1}\d{1}[A-Z]{1} *\d{1}[A-Z]{1}\d{1}$)/, errorString:"Invalid Postal Code<br />"}
validationCase["email"] = {rgx: /^(([a-zA-Z0-9_\-\.]+)@([a-zA-Z0-9_\-\.]+)\.([a-zA-Z]{2,5}){1,25})+([;.](([a-zA-Z0-9_\-\.]+)@([a-zA-Z0-9_\-\.]+)\.([a-zA-Z]{2,5}){1,25})+)*$/,errorString:"Invalid Email Address<br />"}
validationCase["email2"] = {rgx: /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+.[a-zA-Z]{2,4}$/, errorString:"Invalid Email Address<br />"}
validationCase["date"] = {rgx:/^\d{1,2}\/\d{1,2}\/\d{4}$/, errorString:"Invalid Date<br />"}
validationCase["ssn"] = {rgx:/^\d{3}-\d{2}-\d{4}$/, errorString:"Invalid Social Security Number<br />"}
validationCase["integer"] = {rgx:/^0*[1-9][0-9]*$/, errorString:"Invalid Number<br />"}
validationCase["decimal"] = {rgx:/^0*[1-9][0-9]*(.\d{2}|\d{1})?$/, errorString:"Invalid Number<br />"}
validationCase["price"] = {rgx:/^\$?\d+(\.(\d{2}))?$/, errorString:"Invalid Price<br />"}
validationCase["year"] = {rgx:/^\d{4}$/, errorString:""}
validationCase["month"] = {rgx:/^(0?[1-9]|1[0-2])$/, errorString:""}
validationCase["alpha"] = {rgx:/^[a-zA-Z .-]*$/, errorString:""}

validationCase["visa"] = {rgx:/^4[0-9]{12}(?:[0-9]{3})?$/, errorString:"Credit card number is invalid<br />"}
validationCase["mastercard"] = {rgx:/^5[1-5][0-9]{14}$/, errorString:"Credit card number is invalid<br />"}
validationCase["amex"] = {rgx:/^3[47][0-9]{13}$/, errorString:"Credit card number is invalid<br />"}
validationCase["dinersclub"] = {rgx:/^3(?:0[0-5]|[68][0-9])[0-9]{11}$/, errorString:"Credit card number is invalid<br />"}
validationCase["discover"] = {rgx:/^6(?:011|5[0-9]{2})[0-9]{12}$/, errorString:"Credit card number is invalid<br />"}
validationCase["jcb"] = {rgx:/^(?:2131|1800|35\d{3})\d{11}$/, errorString:"Credit card number is invalid<br />"}

/* data-placeholder */
/* set up handlers */
$(function() {
	$("'[data-placeholder]'").focus(function() {
	  var input = $(this);
	  if (input.val() == input.attr("data-placeholder")) {
		clearError(input.attr('id'));
		input.val("");
		input.removeClass("'data-placeholder'");
	  }
	}).blur(function() {
	  var input = $(this);
	  if (input.val() == "" || input.val() == input.attr("data-placeholder")) {
		input.addClass("'data-placeholder'");
		input.val(input.attr("data-placeholder"));
	  }
	}).blur();
	
	$("'[data-placeholder]'").parents("form").submit(function() {
	  $(this).find("[data-placeholder]").each(function() {
		var input = $(this);
		if (input.val() == input.attr("data-placeholder")) {
		  input.val("");
		}
	  })
	});
});

/* clear and fill pre- and post- submit (on failure) */
function clearPlaceholders(el) {
	$(":input","#"+el).each(function() {
		if($(this).val() == $(this).attr("data-placeholder"))
		{
			$(this).val("");
		}
	});
}

function clearPlaceholder(el) {
	if($("#"+el).val() == $("#"+el).attr("data-placeholder"))
	{
		//$("#"+el).val("");
	}
}

function fillPlaceholder(el) {
	if($("#"+el).val() == "")
	{
		$("#"+el).val($("#"+el).attr("data-placeholder"));
	}
}

function fillPlaceholders(el) {
	$(":input","#"+el).each(function() {
		if($(this).val() == "")
		{
			$(this).val($(this).attr("data-placeholder"));
		}
	});
}

function setErrorState(el) {
	//console.log("Setting error state " + el);
	$("#"+el).addClass("error");
	if(!$("#"+el).attr("validating"))
	{
		if($("#"+el).attr("type") == "text")
		{
			$("#"+el).attr("validating","true");
			$("#"+el).bind("keyup.live_validation",function() {
				clearPlaceholder(el);
//				validateField(el);
	//			filldata-placeholder(el);
			})
		}
	}
	if($("#"+el).attr("data-errorOutput")) {
		$("#"+$("#"+el).attr("data-errorOutput")).html($("#"+el).attr("data-error"));
		if(!$("#"+el).attr("data-errorPopup"))
		{
			$("#"+$("#"+el).attr("data-errorOutput")).css("display","block");
		}
		else {
			var ip = $("#"+el);
			ip.bind('focus.popup',function() {
				$("#"+$("#"+el).attr("data-errorOutput")).css("display","block");
			});
			
			ip.bind('blur.popup',function() {
				$("#"+$("#"+el).attr("data-errorOutput")).css("display","none");
			});
		}
	}
	
	if($("#"+el).attr("data-errorTarget")) {
		var errorList = $("#"+el).attr("data-errorTarget").split("|");
/*		$(errorList).each(function() {
			$("#"+errorList[i]).addClass("error");
		});*/
		for(var i = 0;i < errorList.length;i++)
		{
			$("#"+errorList[i]).addClass("error");
		}
	}
	else $("#"+el).addClass("error");
}

function setFormController(el,submitbtn) {
	$("#"+submitbtn).click(function() {
		clearPlaceholders(el);
		if(validateForm(el)) {
			$("#"+el).submit();	
		}
	});
	
	$(":input",$("#"+el)).each(function() {
		if($(this).attr("data-errorOutput"))
		{
			$("#"+$(this).attr("data-errorOutput")).css("display","none");
		}
	});
	
	/*$("#"+el).submit(function() {
		cleardata-placeholders(el);
		if(validateForm(el))
			document.getElementById(el).submit();
			
	});*/
}



function validCreditCard(val,type) {
	if(type)
	{
		if(regex(val,validationCase[type].rgx))
			return true;
		else return false;
	}
	else {
		if(regex(val,validationCase["amex"].rgx) || regex(val,validationCase["mastercard"].rgx) || regex(val,validationCase["visa"].rgx ) || regex(val,validationCase["dinersclub"].rgx) || regex(val,validationCase["jcb"].rgx) || regex(val,validationCase["discover"].rgx))
			return true;
		else return false;
	}
}

function regex(val,pattern) {
	return pattern.test(val);	
}

function validFutureDate(val,offset) {
	if(offset)
		return((Date.parse(val)-parseInt(offset)*86400 * 1000) > new Date().getTime());
	else return((Date.parse(val) > new Date().getTime()));
}

function validPastDate(val,offset) {
	return((Date.parse(val)+parseInt(offset)*86400 * 1000) < new Date().getTime())
}

function addError(valItem,el) {
	if($("#"+el).attr("data-error")) {
		return $("#"+el).attr("data-error")+"<br />";
	} else return valItem.errorString;
}

function addErrorByString(err,el) {
	if($("#"+el).attr("data-error")) {
		return $("#"+el).attr("data-error")+"<br />";
	} else return err;
}

function validateCheckbox(el) {

	var name = $("#"+el).attr("name");

	if($("input[name='"+name+"']:checked", '#'+formToValidate).val())
	{
		return true;
	}
	
	return false;
}

function validateRadio(el) {

	var name = $("#"+el).attr("name");

	if($("input[name='"+name+"']:checked", '#'+formToValidate).val())
	{
		return true;
	}
	
	return false;
}

function validateField(el) 
{
	if(document.getElementById(el))
	{
		clearError(el);
		$("#"+el).each(function() {

			if($(this).attr("data-validate"))
			{
				if($(this).attr("type") == "radio" && $(this).attr("data-validate") == "required")
				{
					if(!validateRadio(el))
					{
						errorStr += $(this).attr("name") + " is required.";
						setErrorState($(this).attr("id"));
					}
				} else if($(this).attr("type") == "checkbox" && $(this).attr("data-validate") == "required") {
					if(!validateCheckbox(el))
					{
						errorStr += $(this).attr("name") + " is required.";
						setErrorState($(this).attr("id"));
					}
				}
			
				// get validation types from data-validate
				var validateList = $(this).attr("data-validate").split("|");
				
				for(var i = 0;i < validateList.length;i++) {
					var validateItem = validateList[i];
			
					/* parse arguments (arg1,arg2) */
					var args = new Array();
					// get arguments for this validation item
					var argsArr = validateItem.split("(");
					
					if(argsArr.length > 1)
					{
						validateItem = validateItem.split("(")[0];
						var argArr3 = argsArr[1].split(")");
						var argStr = argArr3[0];
						
						if(argStr.length > 0)
						{
							
							var argsArr2 = argStr.split(",");
							for (var curArg in argsArr2)
							for(var q = 0;q < argsArr2.length;q++)
							{
								args.push(argsArr2[q]);
							}
						}
					}
					
					/* validate */
				
					switch(validateItem) {
						case "required" :
							if($(this).val().length < 1) {
								errorStr += addErrorByString($(this).attr("data-placeholder") + " is required.<br />",
											$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							break;
							
						case "minlength" :
							if(args.length < 1)
								args.push(1);
								
							if($(this).val().length < parseInt(args[0]))
							{
								setErrorState($(this).attr("id"));
								errorStr += addErrorByString($(this).attr("data-placeholder") + " must be at least " + args[0] + " character"+((args[0] == 1) ? "" :"s")+".<br />",
											$(this).attr("id"));
							}
							break;
							
						case "maxlength" :
							if(args.length < 1)
								args.push(10);
								
							if($(this).val().length > parseInt(args[0]))
							{
								setErrorState($(this).attr("id"));
								errorStr += addErrorByString($(this).attr("data-placeholder") + " cannot be longer than " + args[0] + " characters.<br />",
											$(this).attr("id"));
							}
							break;
							
						case "match" :
							if($(this).val() != $("#"+args[0]).val())
							{
								setErrorState($(this).attr("id"));
								errorStr += addErrorByString($(this).attr("data-placeholder") + " must match " + $("#"+args[0]).attr("data-placeholder")+".<br />",
											$(this).attr("id"));
							}
							break;
							
						case "future_month" :
							var year = $("#"+args[0]).val();
							var today = new Date();
							if(year == today.getFullYear()) {
								if(parseInt($(this).val()) < today.getMonth()+1)	 {
									errorStr += addError(validationCase["date"],$(this).attr("id"));
									setErrorState($(this).attr("id"));
									setErrorState(args[0]);
								}
							}
						
							break;
							
						case "future_date" :
							if(!regex($(this).val(),validationCase["date"].rgx))
							{
								errorStr += addError(validationCase["date"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							else if(!validFutureDate($(this).val(),args[0]))
							{
								errorStr += addError(validationCase["date"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							break;
							
						case "past_date" :
							if(!regex($(this).val(),validationCase["date"].rgx))
							{
								errorStr += addError(validationCase["date"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							else if(!validPastDate($(this).val(),args[0]))
							{
								errorStr += addError(validationCase["date"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							break;
							
						case "creditcard" :
							if(!validCreditCard($(this).val(),$('#'+args[0]).val()))
							{
								errorStr += addError(validationCase["visa"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}
							
							/*
							if(!validCreditCard($(this).val(),$('input:radio[name='+args[0]+']:checked').val()))
							{
								errorStr += addError(validationCase["visa"],$(this).attr("id"));
								setErrorState($(this).attr("id"));
							}*/
							break;
							
						default:
							if(validationCase[validateItem])							
								if(!regex($(this).val(),validationCase[validateItem].rgx))
								{
									errorStr += addError(validationCase[validateItem],$(this).attr("id"));
									setErrorState($(this).attr("id"));
								}
								
							break;
					}
				}
			}
		});
	}
}
var errorStr = "";
var errorCount = 0;
var formToValidate = "";

function validateForm(el) {
	errorStr = "";
	errorCount = 0;
	formToValidate = el;
	clearAllErrors(el);
	
	$(":input","#"+el).each(function() {
		//console.log("Validating " + $(this).attr("id"));
		validateField($(this).attr("id"));
	});
	
	if(errorStr.length > 0)
	{
		if($("#"+el).attr("data-errorBlock"))
			$("#"+$("#"+el).attr("data-errorBlock")).html(errorStr);
		fillPlaceholders(el);
		
		return false;
	}
	
	if($("#"+el).attr("data-errorBlock"))
		$("#"+$("#"+el).attr("data-errorBlock")).html("");
	return true;
}

function validateFieldSet(el,fs) {
	errorStr = "";
	errorCount = 0;
	formToValidate = el;
	clearAllErrors(el);
	
	$(":input","#"+fs).each(function() {
		validateField($(this).attr("id"));
	});
		$("select","#"+fs).each(function() {
	});
	
	if(errorStr.length > 0)
	{
		if($("#"+el).attr("data-errorBlock"))
			$("#"+$("#"+el).attr("data-errorBlock")).html(errorStr);
		fillPlaceholders(el);
		return false;
	}
	if($("#"+el).attr("data-errorBlock"))
		$("#"+$("#"+el).attr("data-errorBlock")).html("");
	return true;
}

function clearError(el) {
	$("#"+el).removeClass("error");
	
	if($("#"+el).attr("data-errorOutput"))
	{
		$("#"+$("#"+el).attr("data-errorOutput")).css("display","none");
		var ip = $("#"+el).unbind('focus.popup').unbind('blur.popup');
	}
}

function clearAllErrors(el) {
	if(document.getElementById(el))
	{
		$(":input","#"+el).each(function() {
			if($(this).attr("id"))
				clearError($(this).attr("id"));
		});
		
	}
}
