// Declaring required variables
var digits = "0123456789";
// non-digit characters which are allowed in phone numbers
var phoneNumberDelimiters = "()- .";
// characters which are allowed in international phone numbers
// (a leading + is OK)
var validWorldPhoneChars = phoneNumberDelimiters + "+";
// Minimum no of digits in an international phone no.
var minDigitsInIPhoneNumber = 10;

function isInteger(s)
{   var i;
    for (i = 0; i < s.length; i++)
    {   
        // Check that current character is number.
        var c = s.charAt(i);
        if (((c < "0") || (c > "9"))) return false;
    }
    // All characters are numbers.
    return true;
}

function stripCharsInBag(s, bag)
{   var i;
    var returnString = "";
    // Search through string's characters one by one.
    // If character is not in bag, append to returnString.
    for (i = 0; i < s.length; i++)
    {   
        // Check that current character isn't whitespace.
        var c = s.charAt(i);
        if (bag.indexOf(c) == -1) returnString += c;
    }
    return returnString;
}

function validPhone(element){
	var value = element.value;
	if(value == null){
		return true;
	}
	s = stripCharsInBag(value,validWorldPhoneChars);
	if(isInteger(s) && s.length >= minDigitsInIPhoneNumber){
		return false;
	}
	return true;
}

function isEmpty(element){
	var value = element.value;
	return ((value == null) || (value.length == 0));
}

function exists(element){
	if($(element.name)){
		return false;
	}
	return true;
}

function validEmail(element){
	var value = element.value;
	var pattern = /^[^@]+@([a-zA-Z\-]+\.)+[a-zA-Z]{2,}$/;
	if(pattern.test(value)){
		return false;
	}
	return true;
}

function validChecked(element){
	if(element.getProperty('checked')){
		return false;
	}
	return true;
}

var ValidatedForm = new Class({
	
	Implements:[Options, Events],
	
	options:{
		fieldSelectors:'input[required], select[required], textarea[required]',
		useVisualizations: true,
		useSubmitValidation: false
	},
	
	initialize: function(form, options){
		this.setOptions(options);
		this.form = $(form);
		this.elements = this.form.getElements(this.options.fieldSelectors);
		this.ajaxElements = new Array();
		this.submitChecks = new Array();
		if(this.options.useVisualizations){
			this.visualizations();
		}
		if(this.options.useSubmitValidation){
			this.form.addEvent('submit', this.onSubmit.bind(this));
		}
	},
	
	visualizations: function(){
		var obj = this;
		var elements = this.elements;
		for(i=0; i < elements.length; i++){
			if(elements[i].getProperty('type') != 'hidden'){
				var element = elements[i];
				var span = new Element('p', {'id':element.id+'Status', 'class':'required'});
				span.injectBefore(element);
				element.addEvent('keypress', function(){
						$(this.id + 'Status').removeProperty('class');
						$(this.id + 'Status').addClass('editing');
					});
				if(element.getProperty('type') == 'checkbox'){
					element.addEvent('change', function(){
						var elementStatus = $(this.id + 'Status');
						elementStatus.removeProperty('class');
						var validator = this.getProperty('required');
				 		var error = obj.validate(this, validator);
						if(error){
							elementStatus.addClass('invalid');
						} else {
							elementStatus.addClass('valid');
						}
					});
				} else {
					element.addEvent('blur', function(){
						var elementStatus = $(this.id + 'Status');
						elementStatus.removeProperty('class');
						var validator = this.getProperty('required');
				 		var error = obj.validate(this, validator);
						if(error){
							elementStatus.addClass('invalid');
						} else {
							elementStatus.addClass('valid');
						}
					});
				}
				
				
			}
		}
	},
	
	addCheck: function(obj){
		this.submitChecks.push(obj);
	},
	
	onSubmit: function(event){
		var errorMsg = '';
		var elements = this.elements;
	 	for(i=0; i < this.elements.length; i++){
			var element = this.elements[i];
	 		var validator = element.getProperty('required');
	 		var error = this.validate(element, validator);
	 		if(error){
	 			errorMsg += (element.getProperty('message'))? element.getProperty('message')  + '\n' : '';
	 		}
		}
		for(i=0; i < this.ajaxElements.length; i++){
			var element = this.ajaxElements[i];
			var validator = element.required;
	 		var error = this.validate(element, validator);
	 		if(error){
	 			errorMsg += element.message + '\n';
	 		}
		}
		for(i=0; i < this.submitChecks.length; i++){
			var check = this.submitChecks[i];
			if(!check.test()){
				errorMsg += check.message + '\n';
			}
		}
		
		
		
		if(errorMsg != ''){
	 		new Event(event).stop();
	 		alert(errorMsg);
	 	}
	},
	
	validate: function(element, validator){
		switch (validator){
			case 'EMPTY':
			 	error = isEmpty(element);
			 	break;
			 case 'EMAIL':
			 	error = validEmail(element);
			 	break;
			 case 'PHONE':
			 	error = validPhone(element);
			 	break;
			 case 'CHECKED':
			 	error = validChecked(element);
			 	break;
			 case 'EXISTS':
			 	error = exists(element);
			 	break;
	 	}
		
		return error;
	},
	
	addAjaxElement: function(element, validator, message){
		var obj = {};
		obj.name = element;
		obj.required = validator;
		obj.message = message;
		this.ajaxElements.push(obj);
	}
	
	
});
var Validator = new Class({
	foo: function(){
		alert('ooga booga');
	}
});
//Validator['foo']();