﻿

	// Create the hints object
	jQuery.Hints = {};
	jQuery.Hints.Display = {
		Always: 0, OnFocus: 1, OnMouseOver: 2, OnFocusOrMouseover: 3, Never: 4
	};
	jQuery.Hints.MessageOptions =
	{
		attribute: '', priority: 0, display: $.Hints.Display.Never, animate: false,
		template: "<span class='Form Message {class}'>{content}<span class='Form {class}Pointer'>&nbsp;</span></span>"
	};
	jQuery.Hints.Types = { 
	Manual: { cssClass: 'ManualMessage', attribute: 'message', priority: -1, display: $.Hints.Display.Never }, 
	Hint: { cssClass: 'Hint', attribute: 'hint', priority: 1, display: $.Hints.Display.OnFocus }, 
	Tip: { cssClass: 'Tip', attribute: 'tip', priority: 0, display: $.Hints.Display.OnMouseOver },
	Error: { cssClass: 'ErrorHint', attribute: 'errorhint', priority: 2, display: $.Hints.Display.OnFocusOrMouseover }
	};

 
// JavaScript Document
(function($){ 
    $.fn.extend({ 
        enableMessages: function(options) {
			
			  // define defaults and override with options, if available
			  // by extending the default settings, we don't modify the argument
			  var settings = jQuery.extend({}, options);
			
			  // Function Wrappers
			  var updateMessages = function() { $(this).updateMessages(); };
			  
			  // Show and Hide Messages on Rollover or Focus
			  this.find("input, select, textarea, *[tip]")
			  .focus(updateMessages).blur(updateMessages)
			  .mouseover(updateMessages).mouseout(updateMessages);
			  
			  // Watermarks
			  this.enableWatermarks();
			  
			  /*
			  // Validate the page on submit, and remove watermarks on focused fields after submit (error field may be auto-focused)
			  // and Hijack submit event, to clear watermarks before form submit
			  $("form").submit(function()
				  { 
				      var valid = true;
				      
				      // Validate
					  if (typeof(Page_ClientValidate) == "function") {
					  	valid = Page_ClientValidate(this._validationGroup);
				  	  }
				  	  
				  	  // Dewatermark if form is to be submitted
				  	  if (valid)
				  	  {
				  	    $("input[watermark], textarea[watermark]").each(function() { $(this).dewatermark(); });
				  	  }
				      
				      return valid;
				  });*/    
			
            return this;
        },
		
		enableWatermarks: function()
		{
			  // Function Wrappers
			  var watermark = function() { $(this).watermark(); };
			  var dewatermark = function() { $(this).dewatermark(); };
			  
			  // Add watermarks to all unfocused form controls
			  this.find("input[watermark]:not(:focus), textarea[watermark]:not(:focus)").each(watermark);
			  
			  // Remove watermarks on focus, and add them back when the control loses focus
			  this.find("input[watermark], textarea[watermark]").focus(dewatermark).blur(watermark);
		},
		
		updateMessages: function(options)
		{
			 return this.each(
					 function() { 	
					 	var currentPriority = -1000; var message = null;
						for (var i in $.Hints.Types)
						{
							if ($(this)._shouldMessageBeActive($.Hints.Types[i]) && $.Hints.Types[i].priority > currentPriority) { 
							message = $.Hints.Types[i]; currentPriority = message.priority; }
						}
						if (message != null)
						{
							$(this).showMessage(message);
						}
						else
						{
							$(this).hideMessage();
						}
					 });
		},
		
		_shouldMessageBeActive: function(options)
		{
			var $element = $(this);
			var settings = jQuery.extend({}, jQuery.Hints.MessageOptions, options);
			if (!$element.attr(settings.attribute)) { return false; }
			switch (settings.display)
			{
				case $.Hints.Display.Always: return true;
				case $.Hints.Display.OnFocus: return $element.is(":focus");
				case $.Hints.Display.OnMouseOver: return $element.is(":hover");
				case $.Hints.Display.OnFocusOrMouseover: return $element.is(":hover") || $element.is(":focus");
				case $.Hints.Display.Never: return false;
				default: return false;
			}
		},
		
		showMessage: function(options)
		{
			return this.each(
					 function() { 
						var $element = $(this);
						var settings = jQuery.extend({}, jQuery.Hints.MessageOptions, options);
						if (!settings.content) { settings.content = $element.attr(settings.attribute); }
					 
						// Create the message HTML, and add it after the element.
						var message = $(settings.template.replace(/{class}/g, settings.cssClass).replace(/{content}/g, settings.content));
						
						// Only animate message if it's not already visible
						settings.animate = settings.animate && !$element.next().is("." + settings.cssClass);

						// Remove any other messages
						$element.hideMessage();
						
						// Add Message
						$element.after(message);
						//message.hide().show('slow');
			
						// Position the message
						if ($element.is("input, select, textarea"))
						{
							// Display it at a set vertical height for input elements
							 var left = $element.offset().left + $element.outerWidth() + 10;
                			 var top = $element.offset().top - $(document).scrollTop();
						}
						else
						{
							// Display it centered verticaly beside the element, for non input elements (e.g. div tags, images, links etc.)
							var top = $element.offset().top - $(document).scrollTop() + $element.outerHeight()/2 - 16;
							var left = $element.offset().left + $element.outerWidth() + 8;
						}
						
						// Display it at a set vertical height for input elements
						if (settings.animate)
						{
							message.css({left: left + 50 + "px", top: top + "px", opacity: 0}).animate({left: left + "px", opacity: 1.0}, 500);
						}
						else
						{
							message.css({left: left + "px", top: top + "px"});
						}
			});
		},
		
		hideMessage: function()
		{
			return this.each(
					 function() { 
						if ($(this).next().is("span.Form.Message"))
						{
							$(this).next("span.Form.Message").remove();
						}
					 });
		},
		
		watermark: function()
		{
			return this.each(
					 function() { 
					 
					    // Remove Watermarks on Submit
					    var $form = $(this.form);
				        if (!$form.data("dataFormSubmit")) {
				        
				            // Keep Copy of Original Function
					        $form.data("dataFormSubmit", this.form.submit);
					        $form.submit(function () { $("input[watermark], textarea[watermark]").each(function() { $(this).dewatermark(); }); });
        					
					        this.form.submit = function () {
						        var nativeSubmit = $form.data("dataFormSubmit");
        						
						        $("input[watermark], textarea[watermark]").each(function() { $(this).dewatermark(); });
        						
						        if (nativeSubmit.apply) {
							        nativeSubmit.apply($form[0], arguments);
						        }
						        else {
							        nativeSubmit();
						        }
					        };
				        }     
					 
						if ($(this).val() == "" && $(this).attr("watermark"))
						{
							$(this).val($(this).attr("watermark"));
							if ($(this).hasClass("UpperCase"))
							{
								this.upperCase = true;
								$(this).removeClass("UpperCase");
							}
							$(this).addClass("Watermark");
						}
			 });
		},
		
		dewatermark: function()
		{
			return this.each(
					 function() { 
						        if ($(this).is(".Watermark"))
								{
								  if (this.upperCase)
								  {
									  $(this).addClass("UpperCase");
								  }
								  $(this).removeClass("Watermark");
								  $(this).val("");
								} else if ($(this).attr("watermark") && $(this).val() == $(this).attr("watermark")) { $(this).val(""); }
			 });
		},
		
		node: function()
		{
			return document.getElementById(this.attr('id'));
		},
		
		addError: function(message)
		{
			return this.each(
					 function() { 
						        // Set the error to be displayed on its target control, and add the error message as an attribute of the control. This will be displayed by the Hints code.
								$(this).addClass("Error");
								$(this).removeClass("Valid");
								$(this).attr("errorhint", message);
								 });
		},
		
		removeError: function()
		{
			return this.each(
					 function() { 
					 	// If the control is indeed valid, then mark it as so, and remove any error messages.
						$(this).removeClass("Error");
						$(this).removeAttr("errorhint");
						$(this).addClass("Valid");	        
			 });
		},
		
		enableHover: function()
		{
			return this.each(function() { this.hover = false; }).mouseover(function() { this.hover = true; }).mouseout(function() { this.hover = false; });
		}
    }); 
})(jQuery);
 

// Selectors
jQuery.extend(jQuery.expr[':'], {
	focus	: "a==document.activeElement",
	blur		: "a==document.lastActiveElement",
	hover		: "a.hover"
});



// Active Selecotrs
$(document).ready(function() {
						   $("*").enableHover();
						   });
 
 // When page loads, run this code:
 $(document).ready(function() { $(document).enableMessages(); });

    
    // Run this code on Page Load
    window.onload = function() {
        // Return if no asp.net validation on page
        if (typeof(Page_Validators) == "undefined") { return; }
		
        // Cycle through all the ASP.net validators on the page
        for (var i in Page_Validators)
        {
            // Hide it, to supress the ugly asp.net validation message
            Page_Validators[i].style.display = 'none';
            
            // Keep a copy of the original validation function, store it in ‘originalfunction’
            Page_Validators[i].originalfunction = Function.createDelegate(Page_Validators[i], Page_Validators[i].evaluationfunction);
            
            // Override the new evaluation function to call Validate (see below)
            Page_Validators[i].evaluationfunction = Function.createDelegate(Page_Validators[i], Validate);
        }
    }
    
    // Check whether a control is indeed valid (control may have multiple validators)   
    function isValid(control)
    {
        var valid = true;
        // Cycle through all the ASP.net validators on the page
        for (var i = 0; i < Page_Validators.length; i++)
        {
            // If the validator validates this control, and it validates it as invalid, then the control is invalid.
            if (Page_Validators[i].controltovalidate == control && !Page_Validators[i].originalfunction(Page_Validators[i])) { 
                valid = false;
            }
        }
        return valid;
    }
    
    // This code overrides the default validation function for a validator, to be run on validation.
    function Validate(val) {
    
        // Remove the watermark text, before validation, to avoid confusing the validation function
        $("#" + val.controltovalidate).each(function() { $(this).dewatermark(); });
        
        // Call the original validation function, to check if its valid
        val.isvalid = val.originalfunction(val);
        
        // Add the watermark back in (if it was removed)
        $("#" + val.controltovalidate + ":not(:focus)").each(function() { $(this).watermark(); });
        
        // Hide it, to supress the ugly asp.net validation message
        val.style.display = 'none';
        
        // Is it invalid?
        if (!val.isvalid)
        {
            $("#" + val.controltovalidate).addError(val.errormessage);
        }
        // Check first whether the control to validate is indeed valid, by calling isValid(...), before marking it as so (control may have multiple validators)
        else if (isValid(val.controltovalidate))
        {
            $("#" + val.controltovalidate).removeError();
        }
        
        // Return whether this validator is valid
        return val.isvalid;
    }
