function validateEmail(email) 
{ 
  var re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/ 
  return email.match(re);
}

function validateNotEmpty(str) {
  return str.length > 0;
}

var fullName = /^ *\w[A-Za-z.'-]*\w +\w[A-Za-z.'-]*\w( \w[A-Za-z.'-]*\w[.]*)? *$/;

function validate(validator, str) {
  if (validator instanceof RegExp) {
    return validator.test(str);
  } else if (typeof validator == 'function') {
    return validator(str);
  }
  throw "validator needs to be a function or regex."
  return false;
}

var addField = function(field, validator) {
  var defaultText = field.attr('value');
  var focus = function(e) {
    field.focus();
    field.addClass("selected-field");
    if (defaultText && field.attr('value') == defaultText)
      field.attr('value', "");
  }
  field.focusin(function(e) {focus()});
  
  field.focusout(function(e) {
    field.removeClass("selected-field");
    field.removeClass("bad-field");
    if(validate(validator, field.attr('value'))) {
      field.addClass("good-field");
    } else {
      field.removeClass("good-field");
      if(field.attr('value') == '') {
        field.attr('value', defaultText);
      } else {
        field.addClass("bad-field");
      }
    }
  });
}

function Validator(field, validator) {
  this.field = field;
  this.id = field.attr('id');
  this.defaultText = field.attr('value');
  //this.type = field.nodeName.toLowerCase();
  this.validator = validator;
  this.validated = null;
};
Validator.prototype.addField = function() {
  var _parent = this;
  this.field.focusin(function(e) {
//    alert(this.id);
//    alert(_parent.field.attr('value'));
//    alert(this.id);
//    alert(this.field2);
    _parent.focus();
  });
  
  this.field.focusout(function(e) {
    var field = _parent.field;
    field.nextAll().remove();
    if(validate(_parent.validator, _parent.getVal())) {
      field.after("<img class='yes-status' src='images/yes.png'>");
      field.next('.yes-status').fadeIn(200);
      field.next('.no-status').fadeOut(200);
      _parent.validated = true;
    } else {
      if(_parent.getVal() == '') {
        _parent.setVal(_parent.defaultText);
        _parent.validated = null;
      } else {
        field.after("<img class='no-status' src='images/no.png'>");
        field.next('.no-status').fadeIn(200);
        field.next('.yes-status').fadeOut(200);
        _parent.validated = false;
      }
    }
  });
  return this;
};
//sets the value of a form input
Validator.prototype.setVal = function(value) {
//  this.field.attr('value', value);
  this.field.val(value);
};
//gets the value of a form input
Validator.prototype.getVal = function() {
  return this.field.val();
//  return this.field.attr('value');
};
Validator.prototype.focus = function(e) {
  //alert(this);
  this.field.focus();
  //this.field.addClass("selected-field");
  if (this.defaultText && this.field.attr('value') == this.defaultText)
    this.field.attr('value', "");
};
Validator.fromID = function(str, validator) {
  return new Validator($('#'+str), validator).addField();
};
Validator.prototype.restore = function(e) {
  this.setVal("");
  this.field.trigger('focusout');
}



function Validators(arr) {
  this.list = [];
};
/*
 * Expected format for arr param:
 * [
 *   {id: "email-field", validator: validateEmail},
*    {tag: "selector", validator: validateSelectorGeneric}
 * ]
 */
Validators.create = function(arr) {
  var validators = new Validators();
  for (var i = 0; i < arr.length; i ++) {
    var item = arr[i];
    if (item.validator == null) {
      item.validator = validateNotEmpty;
    }
    if (item.id != null)
      validators.list.push(Validator.fromID(item.id, item.validator));
    else if(item.jquery != null)
      validators.list.push(new Validator($(item.jquery), item.validator).addField());
  }
  return validators;
};
Validators.prototype.restore = function() {
//  alert(this.list.length);
  var i = 0;
  for (i = 0; i < this.list.length; i++) {
//    alert(this.list[i].id);
    this.list[i].restore();
  }
};
Validators.prototype.anyEmpty = function() {
  var someEmpty = false;
  for (i = 0; i < this.list.length; i++) {
    var field = this.list[i];
    if (field.getVal() == field.defaultText)
      someEmpty = true;
  }
  return someEmpty;
}

