
rf = new rf();




// Form Class
function Rf_form (f_id) {
	
    this.id = f_id;
    this.fields = new Array(); // list of field objects
    this.error_output;
	
    this.invalid_fields; // list of field names
    this.empty_required_fields; // list of field names
	this.captcha = 0;
	this.require_captcha = 0;
	  
	
	/********************
	*
	*  Method
	*
	*/	
    this.addField = function (field_obj) {
        this.fields.push(field_obj);
    };
	  
	
	/********************
	*
	*  Method
	*
	*/	
    this.init = function () {
		
        // attach hint listeners to fields
        for (var i = 0; i < this.fields.length ; i++) {
			this.fields[i].init();
		}
		
		// find the captcha if there is one
		this.findCaptcha();
		
		  
    };
	
	/********************
	*
	*  Method
	*  return the html element for this form
	*/	
    this.el = function () {
		return document.getElementById(this.id);
    };
	
	
	/********************
	*
	*  Method
	*
	*/	
	this.validate = function () {
		
		
        this.invalid_fields = new Array(); // list of field names
        this.empty_required_fields = new Array(); // list of field names
        for (var i = 0; i < this.fields.length ; i++) {
			this.fields[i].validate(); // this function will add the fields name to either one of the 2 above arrays if something is wrong
        }
		
		
		
		// check if there were any errors in either of the 2 lists
		// if there were any errors in either of the 2 lists, then construct an error message based on those lists' contents
		if(this.empty_required_fields.length > 0 || this.invalid_fields.length > 0){
		
            var error_output = this.create_error_message ();
		
            if (this.error_replaces_intro) {
                document.getElementById('intro_msg_'+this.form_id).style.display = 'none';
            }
		
            // show the error
            var js_form_error = document.getElementById('js_form_error_'+this.id);
            if (js_form_error == null) {
                js_form_error = document.createElement('div');
                js_form_error.setAttribute('id', 'js_form_error_'+this.id);
                var submit_btn = document.getElementById("submit_"+this.id);
                submit_btn.parentNode.insertBefore(js_form_error, submit_btn);
            }
            js_form_error.innerHTML = error_output;
		
            return false;

        } else {
		
            // will submit the form
			
			// remove error message
            var js_form_error = document.getElementById('js_form_error_'+this.id);
            if (js_form_error != null) {
                js_form_error.parentNode.removeChild(js_form_error);
            }
			
			// hide submit button
			this.hide_submit();

            return true;
		
        } // end if empty_req_fields.length > 0 || invalid_fields.length > 0
		
		
		
	}
	
	/*
	*
	*  METHOD: create_error_message : creates an error message to output to the screen based on the arrays of empty required fields and fields that faced their validations
	*  PARAM: empty_req_fields : 
	*  PARAM: invalid_fields : 
	*
	*/
	this.create_error_message = function () {
		
		var empty_req_fields = this.empty_required_fields;
		var invalid_fields =  this.invalid_fields;
	  
		var  error_output = '<p class="error">';
		
		// if a customer error message has been set
		if (this.custom_error) {
			error_output = this.custom_error;
		} else {
			
			
	
		 
			if (empty_req_fields.length > 0) {
		
				error_output += 'You forgot to enter ';
		
				for (i = 0 ; i < empty_req_fields.length ; i++) {
		  
					error_output += '<strong>'+empty_req_fields[i]+'</strong>';
		  
					if (i < empty_req_fields.length - 2) {
						error_output += ", ";
					} else if (i < empty_req_fields.length - 1) {
						error_output += " and ";
					}
				}
		 
			} // required
		 
		 
			if (invalid_fields.length > 0) {
		 
		 
				if (empty_req_fields.length > 0) {
					error_output += ", and ";
				}
		   
		   
				for (i = 0 ; i < invalid_fields.length ; i++) {
		  
					error_output += invalid_fields[i];
		
					if (i < invalid_fields.length - 2) {
						error_output += ", ";
					} else if (i < invalid_fields.length - 1) {
						error_output += " and ";
					}
				}
		  
				if (invalid_fields.length > 1) {
					error_output += " are invalid";
				} else if (invalid_fields.length == 1) {
					error_output += " is invalid";
				}
			}
		 
			error_output += ". Message not sent.";
		
		} // end if custom error
		
		error_output += "</p>";
		 
		return error_output;

	  
	} // end create error message
  
	
	  

	
	/********************
	*
	*  Method
	*
	*/	
    this.show_captcha = function () {
		
		if (!this.captcha) {
		
            // create the captcha
            this.captcha = document.createElement("div");
            this.captcha.setAttribute("id", 'captchawrapper_'+this.id);
            var c_img = document.createElement("img");
            c_img.setAttribute("id", 'captcha_'+this.id);
            c_img.setAttribute("src", 'contact/files/captcha/securimage_show.php');
            c_img.setAttribute("alt", 'CAPTCHA Image');
            var c_input = document.createElement("input");
            c_input.setAttribute("type", 'text');
            c_input.setAttribute("name", 'captcha_code_'+this.id);
		
            // insert the captcha before the submit button
            var sub_btn = document.getElementById("submit_"+this.id);
            sub_btn.parentNode.appendChild(this.captcha);
            this.captcha.appendChild(c_img);
            this.captcha.appendChild(c_input);
		
		}
		
	}
	
	
	/********************
	*
	*  Method
	*
	*/	
    this.hide_captcha = function () { 
		
		if (this.captcha && !this.require_captcha) {
		  this.captcha.parentNode.removeChild(this.captcha);
		  this.captcha = 0;
		}
		
	}
	
	/********************
	*
	*  Method: checks the page to see if this form has a captcha div, and if so sets the captcha memeber to the dom element
	*
	*/	
	this.findCaptcha = function () {
		
	   this.captcha = document.getElementById('captchawrapper_'+this.id);
	   if (!this.captcha) {
		   this.captcha = 0;
	   }
		
		
	}
	
	/********************
	*
	*  Method: checks all the fields to see whether any of them are asking for the captcha to be displayed, and if so, display it
	*
	*/	
	this.updateShowCaptcha = function () {
		
		var show_cap = false;
        for (var i = 0; i < this.fields.length ; i++) {
			if (this.fields[i].showCaptcha) {
			    show_cap = true;	
			}
        }
		
		if (show_cap) {
			this.show_captcha();
		} else {
			this.hide_captcha();
		}
		
	}
	  
	
	
	
	////////////////////////////////
	//  function: Replaces the submit button with a message to give feedback that the form is submitting
	///////////////////////////////
    this.hide_submit = function () {
		
		var sub_btn = document.getElementById("submit_"+this.id);
		sub_btn.style.display = "none";
		
		var form_el = document.getElementById(this.id);
		
		var feeback_el = document.createElement('p');
		var feedback_txt = document.createTextNode('Sending Message . . .');
		feeback_el.appendChild(feedback_txt);
		form_el.appendChild(feeback_el);
		
	}
	
	  
	  
}


/***********************************************************************************/
/***********************************************************************************/

// Field Class
function Rf_field () {
	
      this.form; // the form object to which this field belongs
      this.name; // the name of the field - string
      this.display_name; // the name of the field to display in any error message
      this.type; // the type of this field
      this.required = false; // boolean - if this is a required field
      this.hint = ''; // the hint to display in this field. 
      this.validation = 0; // the type of validation eg, phone, email, no_url, captcha_url
      this.my_error = 0; // any validation error associated with this field
	  this.wrapper_el; // the wrapper that goes around a form part
	  this.error_el; // the wrapper that goes around a form part
	  this.formpart_name; // 
	  this.show_captcha = 0; // whether the contents of this field should cause the captcha to be shown
	  
    /*******************
    *
    *  METHOD: 
    *
    */
	this.init = function () {
		
		// apply hint if necessary
		if (this.hint != '') {
			this.attachHint();
		}
	  
        // check if the validation is 'captcha_url'
        if (this.validation == 'captcha_url') {
			this.addUrlListener();
		}
		
		if (this.formpart_name) {
		  this.wrapper_el = document.getElementById('formpart_'+this.formpart_name+'_'+this.form.id);
		  this.error_el = document.getElementById('error_'+this.formpart_name+'_'+this.form.id);
		} else {
		  this.wrapper_el = document.getElementById('formpart_'+this.name+'_'+this.form.id);
		  this.error_el = document.getElementById('error_'+this.name+'_'+this.form.id);
		}
		
	}
	
    /*******************
    *
    *  METHOD: 
    *
    */
	this.belongsTo = function (formpart) {
		this.formpart_name = formpart;
	}
	  
	  
    /*******************
    *
    *  METHOD: 
    *
    */
    this.attachHint = function () {
		
        var elem_id = this.name+'_'+this.form.id;
		
		// add the hint style to this field if the hint is displayed
		var form_el = document.getElementById(this.form.id);  //!! get the dom element of the form
		var value = form_el[this.name].value;
		if (value == this.hint) {
          rf.jscss('add',document.getElementById(elem_id),'hint'); 
		}

        document.getElementById(elem_id).onfocus = function(elem_id, hintstring) {
			
			return function() {

                var form_element = document.getElementById(elem_id);
                var val = form_element.value;
			
                if (val == hintstring) {
                    if (rf.jscss('check',form_element,'hint')) {
                        rf.jscss('remove',form_element,'hint');
                    } 
                    form_element.value = '';
                }
			
            }
		 
		 
        }(elem_id, this.hint); // end on focus function
	  
        document.getElementById(elem_id).onblur = function(elem_id, hintstring) {
			
			return function() {
			
                var form_element = document.getElementById(elem_id);
                var val = form_element.value;
		  
		  
                if (rf.trim(val) == '') {
                    form_element.value = hintstring;
                    if (!rf.jscss('check',form_element,'hint')) {
                        rf.jscss('add',form_element,'hint');
                    } 
                }// if blur and empty
		  	
			}

			
        }(elem_id, this.hint); // end onblur function
	  
	  
    }  // END ATTACH HINT
	
	
    /*******************
    *
    *
    *
    *  METHOD: add_url_listener : adds a keypress listener to the field which checks for a url on each keystroke
    *                              the keypress listener calls the function to show or hide the captcha for this field's form
	*                              if a url is present
    *
    */
    this.addUrlListener = function () {
	
			
	
                // get the field id (the field name plus underscore plus the form id
                var field_id = (this.name+'_'+this.form.id);
		
		
                // add keypress event handler for the field
                document.getElementById(field_id).onkeypress=function (thisfield) {
					
					return function () {
						
			
                        // check if the value of the field contains a url
                        // if it contains a url then show the captcha, otherwise hide the captcha
                        var el_id = field_id;
                        if (rf.contains_url(document.getElementById(el_id).value)) {
                            thisfield.form.updateCaptcha();  // !!
                        } else {
							thisfield.setShowCaptcha(0);
                        }
					};
		  
                }(this); // end onkeypress function
	
	  
	
    } // END ADD URL LISTENERS FUNCTION
	
	
	
    /*******************
    *
    *  METHOD: sets this field's showcaptcha property. If the value of it changes, call the update captcha on the form
	*
	*/
	this.setShowCaptcha = function (show) {
		
		var oldval = this.show_captcha;
		this.show_captcha = show;
		
		if (oldval != this.show_captcha) {
			this.form.updateShowCaptcha();
		}
		
	}
	
	
    /*******************
    *
    *  METHOD: 
    *
    */
	this.validate = function () {
		
		// first check if required an missing
		if (this.required == 1) {
			
			if (this.isEmpty()) {
				this.form.empty_required_fields.push(this.display_name);
				this.showFieldError(this.display_name+ ' is mandatory');
				
				return;
			}
			
		} 
		
		if (this.validation != 0) {
			
			
		    var form = document.getElementById(this.form.id);  //!! get the dom element of the form
			var value = form[this.name].value;
			
			
			switch (this.validation){
			    case 'email':
			        if (!rf.isValidEmail(value, false)) {
					    this.form.invalid_fields.push(this.display_name);
				        this.showFieldError('Please enter a valid email');
			            return;
					}
			    case 'phone':
			        if (!rf.isValidPhone(value, false)) {
					    this.form.invalid_fields.push(this.display_name);
				        this.showFieldError('Please enter a valid phone number');
			            return;
					}
			} // end switch
		} // end validation
		
		// default no error
		this.hideFieldError();
		
	}
	
	
	this.showFieldError = function (msg) {
		
		this.my_error = msg;
		if (!this.error_el) {
			this.error_el = document.createElement('span');
			this.error_el.className = 'field_error';
			this.wrapper_el.insertBefore(this.error_el, this.wrapper_el.childNodes[0]);
		}
			
		this.error_el.innerHTML = this.my_error;
		
		rf.jscss('add',this.wrapper_el,'field_error_border'); // add the hint style to this field
		
	}
	
	this.hideFieldError = function  () {
		if (this.error_el) {
			this.wrapper_el.removeChild(this.error_el);
			this.error_el = false;
		    rf.jscss('remove',this.wrapper_el,'field_error_border'); // add the hint style to this field
		}
	}


	/*
	*
	*  FUNCTION: isEmpty : checks if a given field in a given form has been filled out
	*  PARAM: strfieldname : the name of the field
	*  PARAM: form : the form element
	*  PARAM: hint : the hint that is displayed in this field
	*
	*/
	this.isEmpty = function () {
		
		
		var strfieldname = this.name;  //!! name or id?
		var form = document.getElementById(this.form.id);  //!! get the dom element of the form
	
	
		if (typeof(form[strfieldname].selectedIndex) != "undefined") {
		// for select element (dropdown list)
		
			if (form[strfieldname].selectedIndex > 0) {
				return false;
			} else {
				return true;
			}
		
		
		}	
	
		if (typeof(form[strfieldname].length) != "undefined")  {
		// for radio buttons
		
			var myOption = -1;
			for (i=form[strfieldname].length-1; i > -1; i--) {
				if (form[strfieldname][i].checked) {
					myOption = i;
					i = -1;
				}
			}
			if (myOption == -1) {
				return true;
			} else {
				return false;
			}
		
		}
	
	
	
		if (typeof form[strfieldname].value != "undefined")  {
		// if not a set eg radio buttons
	
			strfield = form[strfieldname].value ;
	
			if (strfield == "" || strfield == null || strfield == this.hint) {
				return true;
			} else {
				return false;
			}
	  
		}  
	
		return false;
		
	} // end is_empty()

	  
	  
}







