/**
 * jQuery Sabramedia Plugin Library - Function for Sabramedia Virtual Office System
 * Copyright (C) 2008 - 2009 Sabramedia, LLC
 * http://www.sabramedia.com
 *
 * @author Nick Johnson {@link http://nickjohnson.com}
 */

/* Global Variables */
var sabramediaSpinnerSmall = '<span class="pending-spinner"><img src=\'/admin/theme/default/img/spinner-small.gif\' /></span>';

/* jQuery Begins */
(function ($)
{

/**
 *	@name listCollapser
 *	@desc Simple function that makes a list collapsible. 
 *	 
 *	Note: jQuery UI Accordion widget should be used instead of this in most cases.
 *	
 *	@example <ul id="collapse"><li><h2>Click to Expand</h2><ul><li>Content</li></ul><li><ul>
 *	@example $('#collapse').listCollapser();
 *	@desc
 */	
	$.fn.listCollapser = function()
	{
		$('li:has(ul)',this).children('ul').hide().end()
		.find(':first').click(function(event){
			if(event.target){
				if($(this).parent().children('ul').is(':hidden')){
					$(this)
						.parent().children('ul').slideToggle('normal');
				}else{
					$(this)
						.parent().children('ul').slideToggle('normal');
				}
			}
			return false;
		});
	};
/**
 *  @name paginatedSearch
 *  @desc Paginated Search Function
*/

	$.paginatedSearch = function(searchObject){
	window.paginatedSearch = {};
	searchObject.backButton.attr("disabled",true);
	searchObject.nextButton.attr("disabled",true);
	(searchObject.pageLimit) ? window.paginatedSearch.pageLimit = searchObject.pageLimit : window.paginatedSearch.pageLimit = 20 ;
	var search = function(search,page){
	if (window.paginatedSearch.searchRequest != undefined){
		window.paginatedSearch.searchRequest.abort();
		$('.pending-spinner').remove();
	}
	window.paginatedSearch.entryCount = 1;
	window.paginatedSearch.lastSearch = '';
	window.paginatedSearch.currentPage = page;
	var searchLength = window.paginatedSearch.lastSearch.length;
	var cutString = search.substring(0,searchLength);
	if ( ( window.paginatedSearch.entryCount != 0 ) || ( window.paginatedSearch.currentPage != 0 ) || ( cutString.toLowerCase() != window.paginatedSearch.lastSearch.toLowerCase() ) )
	{
		$('#search-field').after(sabramediaSpinnerSmall);
		window.paginatedSearch.lastSearch = search;
		window.paginatedSearch.searchRequest = $.ajax({
				type:"POST",
				url:searchObject.url,
				dataType:"json",
				data:{search:search,limit:window.paginatedSearch.pageLimit,page:page},
				success:function(data){
					$('#transaction-list').empty();
					$('#transaction-table .inserted').remove();
					$('.pending-spinner').remove();
					window.paginatedSearch.entryCount = 0;
					$.each(data,function(key,value){
						window.paginatedSearch.entryCount += 1;
					})
					if (window.paginatedSearch.entryCount < window.paginatedSearch.pageLimit){
						$('#forward-page').attr("disabled",true);
					} else {
						$('#forward-page').attr("disabled",false);
					};
					if (page > 0){
						$('#back-page').attr("disabled",false);
					} else {
						$('#back-page').attr("disabled",true);
					}
					searchObject.callback(data);
					
				}
		});
	}};
	searchObject.backButton.click(function(){
			searchObject.backButton.attr("disabled",true);
			if (searchObject.searchField){
				var searchkey = searchObject.searchField.val();
			} else {var searchkey = ''}
			window.paginatedSearch.currentPage -= 1;
			search(searchkey,window.paginatedSearch.currentPage);
	});
	searchObject.nextButton.click(function(){
		searchObject.nextButton.attr("disabled",true);
		if (searchObject.searchField){
			var searchkey = searchObject.searchField.val();
		} else {var searchkey = ''}
		window.paginatedSearch.currentPage += 1;
		search(searchkey,window.paginatedSearch.currentPage)
	});
	
	if (searchObject.searchField){
		window.paginatedSearch.search_timeout = undefined;
		searchObject.searchField.keyup(function(){
			if (window.paginatedSearch.search_timeout != undefined) {
				clearTimeout(window.paginatedSearch.search_timeout);
			}
			window.paginatedSearch.search_timeout = setTimeout(function(){
				window.paginatedSearch.search_timeout = undefined;
				var searchkey = searchObject.searchField.val();
				search(searchkey,0);
			},750);
			
		});
	};
	search('',0);
	
	};


	
/**
 *	@name navigationMenu
 *	@desc Makes <ul> tags with infinite ul children into hover on/off navigation (requires css styling) 
*/
	$.fn.navigationMenu = function( callerSettings )
	{
		var settings = $.extend({
			eventType : 'hover',
			menuWrap: 'ul',
			timeout: 300
		}, callerSettings || {});
		
		var navigation = $(this);

		$('li:has('+settings.menuWrap+')',this).children(settings.menuWrap).hide().end()
			.each(function(i){
				var menu = $(this).children(settings.menuWrap);
				$(this).addClass('ui-has-child');
				$(this).mouseover(function(event){
					//console.log($(this));
					$(this).addClass('ui-on-child');
					if(event.target){
						if($(menu).is(':hidden')){					
							$(menu).slideDown(100);
							menuHandler(menu);
						}
					}
				});
			});
				
		function menuHandler(menu)
		{
			var timerID = 0;
			
			switch(settings.eventType){
				case 'hover':
					$(menu).parent().hover(function(event){
						if(timerID){ clearTimeout(timerID); };
						timerID  = 0;
						$(this).siblings().children(settings.menuWrap).slideUp(100);
						$(menu).parent('li').removeClass('ui-on-child');
					},
					function(){
						timerID = setTimeout(function(){ 
							$(menu).slideUp(100);
							$(menu).parent('li').removeClass('ui-on-child');
						},settings.timeout);
					});
				break;
				
				case 'toggle':
					// We can do this later
				break;
			
			}
		};
	};

	
/* Ajax Handling Functions */

	// Ajax event handler for submiting input fields with in a set of <li> or <tr> tags 
	$.fn.setListFieldEvents = function(callerSettings)
	{
		var settings = $.extend({
			actionDeletePath: false,
			actionSavePath: false,
			rowEvents: false, // For passing custom row-level events to the added row
			showAddButton:false,
			placeAddButton:false,
			removeObject:false,
			index:false
		}, callerSettings || {});
		
		// Hide all parent format containers
		$('.sibling-format').hide();
		var parentContainer = $(this).parent();
		
		if(settings.actionSavePath && settings.index == 0){
			$('.template-add', parentContainer).hide();
			
			if(settings.showAddButton){
				var addButton = $('<input type=\"button\" value=\"Add\" class=\"button-add\" />').click(function(){
					$('.template-add',parentContainer).toggle();
				});
				
				if(settings.placeAddButton){
					settings.placeAddButton( addButton );
				}else{
					$(addButton).insertBefore(parentContainer);
				}
			}
			
			$('.key-enter-add', parentContainer).ajaxEventHandler({
				dataContainer:'.template-add',
				dataObject:{'vo-action':'insert'},
				eventType:'keyup',
				keyCode:13,
				actionController: settings.actionSavePath,
				success:[successAdd]
			});
		}
			$.fn.rowEvents = function()
			{
				var obj = $(this);
				
				if(settings.actionSavePath){
					$('.key-enter-update',this).ajaxEventHandler({
						dataContainer:obj,
						dataObject:{'vo-action':'update'},
						eventType:'keyup',
						keyCode:13,
						actionController: settings.actionSavePath
					});
						
					$('.keyup-update',this).ajaxEventHandler({
						dataContainer:obj,
						dataObject:{'vo-action':'update'},
						eventType:'keyup',
						actionController: settings.actionSavePath
					});
					
					$('.click-update',this).ajaxEventHandler({
						dataContainer:obj,
						dataObject:{'vo-action':'update'},
						eventType:'click',
						actionController: settings.actionSavePath
					});
				}
				
				if(settings.actionDeletePath){
					$('.click-delete',this).ajaxEventHandler({
						dataContainer:obj,
						dataObject:{'vo-action':'delete'},
						eventType:'click',
						actionController: settings.actionDeletePath,
						verifyAction: 'Are you sure you want to delete this?',
						success:[function(data, status){
								// Change class name so that the .click-delete class does not get re-enabled.
								$('.click-delete',obj).attr('class','click-delete-remove');
								var removeObject = obj;
								if(settings.removeObject){
									removeObject = settings.removeObject;
								}
								$(removeObject).fadeOut('normal',function(){
									$(removeObject).remove();
								});
							}]
					}).hover(function(){
						$(this).addClass('ui-state-hover');
					},
					function(){
						$(this).removeClass('ui-state-hover');
					});
				}
			};
		
		$(this).rowEvents();
		
		var rowTemplate = $('.template', parentContainer).hide().clone();
		// Custom success function for adding
		function successAdd( data, status, ajaxOptions )
		{
			var newRow = $(rowTemplate).show().clone();
			
			$.each(data.newRow, function( key, val ){
				if($('.'+key,newRow).is('input')){
					$('.'+key,newRow).val(val);
				}else{
					$('.'+key,newRow).text(val);
				}
			});
			
			$('.template-add', parentContainer).hide(function(){
				$('input',this).val('');
				$(newRow)
					.removeClass('template-add')
					.attr('data-json','{id:' + data.newId + '}')
					.insertAfter('.template-add')
					.rowEvents();
			});
			
			if(settings.rowEvents){
				settings.rowEvents( newRow, data );
			}
		};
		
		function checkULContent(parentContainer)
		{
			if($(parentContainer).children().length == 0){
				$(parentContainer).append('<li>No data here.</li>').hide().slideDown('normal');
			}
		};
	};
	/**
		Default: Assume that the event handler is a parent tag with children input tags.<b>
		If dataObject is set from outside, then only send that and don't run data row functions 
	*/
	
/**
 *	@name ajaxEventHandler
 *	@desc Standard method for connecting dom elements with events that send data to php action controllers.
 *	@dependency livejquery
 * 	@param Object of options
 *	
*/
	$.fn.ajaxEventHandler = function( callerSettings )
	{
		var settings = $.extend({
			eventType: '',
			keyCode: null,
			dataContainer: null, // Container where data-json attributes holds data and any children inputs represent data
			dataObject: null, // Raw JSON data object that can be sent by itself or appended to the dataContainer
			actionController: '/action/public/404-json.php',
			verifyAction: false,
			beforeSend: null,
			waiting: null,
			success: null,
			complete: null,
			spinner: true
		}, callerSettings || {});
		
	// If dataObject is passed, send as Ajax data
		var thisUpdateField = $(this);
		
		
	// Set event here
		$(this).bind(settings.eventType,function(event){
			var verify = true;
			if(settings.verifyAction){
				verify = confirm(settings.verifyAction);
			}
			
			if(verify){
				// If a keyCode is set, then we want to check which one before executing the ajaxCall()
				if(settings.keyCode){
					// On keyup from the 'enter' key code which is 13
					if(event.keyCode == settings.keyCode){
						$.voAjax( settings, thisUpdateField );
						
					}
				}else{
					$.voAjax( settings, thisUpdateField );
				}
			}
			return false;
		});	
		
		return this;
	};
	
	$.voAjax = function( settings , thisUpdateField )
	{
		
	// Data Preparation
	
		// if tinyMCE variable set then we need to trigger the new values.
		if(typeof(tinyMCE) != 'undefined'){
			//tinyMCE.triggerSave();
		}
		
		// This doesn't work... I know how to get it to work now, think iframe.
		if(typeof(editAreaLoader) != 'undefined'){
			$('textarea#content-js').append(editAreaLoader.getValue('content-js'));
		}
		
	// Methods
		function getSerializedData()
		{
			var serializedData = '';
			// Set data here. Important to set after this just in case we need to do an preparation.
			if(settings.dataContainer){
				serializedData += $(settings.dataContainer).serializeRowData();
			}
			
			if(settings.dataObject){
				if(settings.dataContainer){ serializedData += '&'; } // Appending character if both are set
				serializedData += serializeJSON(settings.dataObject);
			}
			
			
			return serializedData;
		};
		
		function beforeSend(xhr)
		{
			if(settings.spinner){
				$(thisUpdateField).after(sabramediaSpinnerSmall);
			}
			
			// Disable all sibling fields only dataObject is not passed and rowData is used
			$('button').attr('disabled','disabled');
	
			// Iterate through custom fields
			if(settings.beforeSend){
				
				$.each(settings.beforeSend,function(i,customFunction){
					// Pass field object of event handler
					customFunction(xhr,thisUpdateField);
				});
			}
		};
		
		function success( data, status )
		{
			$('.pending-spinner').remove();
			if(settings.success){
				$.each(settings.success,function(i,customFunction){
					// Pass field object of event handler
					if($.isFunction( customFunction )){
						customFunction( data, status, thisUpdateField );
					}
				});
			}else{
//				$(thisUpdateField)
//					.focus()
//					.siblings('.temp-message').remove().end()
//					.parent('li').removeAttr('style').end();
			}
			
			if(data.warning){
				$.voMessage.alert( data.warning );
			}
			if(data.message){
				$.voMessage.dock( data.message );
			}
		};
		
		function complete( xhr, status)
		{
			// Re-enable disabled fields upon success
			$('button').removeAttr('disabled');
			if(settings.complete){
				$.each(settings.complete,function(i,customFunction){
					// Pass field object of event handler
					if($.isFunction( customFunction )){
						customFunction( xhr, status );
					}
				});
			}
		};

	// Ajax intializes here
		
		return $.ajax({
			type:'POST',
			url:settings.actionController,
			dataType:'json',
			data:getSerializedData(),
			beforeSend:beforeSend,
			success:success,
			complete:complete
		});
	};
	
	/**
	* serializeJSON()
	* Turns JSON object into a serialized string in the form of: key=val&key2=val2 
	*
	* @param object literal object
	* @return string serialized for Ajax
	*/
	function serializeJSON(dataObject)
	{
		var dataArray = [];
		var retval;
		
		$.each(dataObject,function(key,data){
			dataArray.push(key + '=' + escape(data));
		});
		
		retval = dataArray.join('&');
		return retval;
	};
	
	function simplifyInputData(dataObject)
	{
		var object = [];
		var retval;
		
		$.each(dataObject,function(key,data){
			
			object[data.name] = data.value;
		});
		
		retval = object;
		return retval;
	};
	
	/** 
	* serializeRowData()
	* Accesses this elements parent element data-json attribute and all sibling element form-type
	* fields, then serializes data for sending via Ajax XHR.<b>
	*
	* @return string serialized data to send via Ajax
	* @dependency metadata
	*/
	$.fn.serializeRowData = function()
	{
		// Gets all json data contained in the parent tag's data-json wrapper 
		var metaData='';
		if($.metadata){
			$.metadata.setType('attr','data-json');
			jsonObject = $('[data-json]',this).andSelf().metadata();
			metaData += serializeJSON(jsonObject)+'&';
		}
		if($(this).data('postdata')){
			metaData += serializeJSON($(this).data('postdata'))+'&';
		}
		// Gets all form type fields based on the current field's containing parent,
		// Then it serializes the data for passing to the ajax controller.
		var inputData = $(this).find(':input');
		
		// Concatentate the jsonData and the inputData
		var serialData = metaData+inputData.serialize();
		//return jsonData;
		// Optional dual-type data object
		
		return serialData;
	};
		
	// Takes JSON returned data and places data in fields or tags with data.key == '.class'
	$.fn.setDataDisplay = function( data )
	{
		if(data){
			object = $(this);
			$.each(data, function( key, val ){
				if(typeof(val) != 'object'){
					var input_type = $('.'+key, object).attr('type');
					
					if($('.'+key, object).is('select')){
						input_type = 'select';
					}
					
					switch (input_type) {
						case 'text':
							$('.'+key, object).val(val);
						break;
						case 'textarea':
							$('.'+key, object).val(val);
						break;
						case 'radio':
							if(val == true){ val=1; }
							if(val == false){ val=0; }
							$('.'+ key +'[value='+ val +']', object).attr('checked','checked');
						break;
						case 'checkbox':
							if(val == true){ val=1; }
							if(val == false){ val=0; }
							$('.'+ key +'[value='+ val +']', object).attr('checked','checked');
						break;
						case 'select':
							$('.'+key+' option[value='+val+']', object).attr('selected','selected');
						break;
						default:
							$('.'+key, object).text(val);
						break;
					}
					//$('.'+key, object).text(val);
				}
			});
			return this;
		}
	};
		
	$.extend({
	
	/**
	* @name jqPhp
	* @desc Purpose is for php variables to be passed into object to be globally accessed.
	*/
		jqPHP : {
		
			phpUrl : {}, // Url object
			phpVar : {}, // Url object

			// Set the urls from php so custom plugins can access the unique urls created by Sabramedia Virtual Office.
			setUrl : function( name, url )
			{
				this.phpUrl[name] = url;
			},
			// Get the urls in the plugin by name
			getUrl : function( name )
			{
				return this.phpUrl[name];
			},
			
			setVar : function( name, variable )
			{
				this.phpVar[name] = variable;
			},

			getVar : function( name )
			{
				return this.phpVar[name];
			}
		},
	/**
	* @name voMessage
	* @desc Standard method for bringing basic messages to system users.
	*/
		voMessage : {
			// Replaces standard alert with a nicer popup
			alert : function( message )
			{
				var randomId = Math.floor(Math.random()*11);
				var $dialog = $('<div id="vo-dialog'+randomId+'" />');
				$dialog.append('<span class="ui-icon ui-icon-alert" style="float:left; margin:2px 7px 20px 0;"></span>' + message);
				$dialog.appendTo('body'); 
				
				$dialog.dialog({
					title: 'Virtual Office Alert',
					bgiframe: true,
					resizable: false,
					height:200,
					width:300,
					modal: true,
					overlay: {
						backgroundColor: '#000',
						opacity: 0.5
					},
					buttons: {
						'Ok': function() {
							$(this).dialog('close');
							$(this).dialog('destroy');
							$('"#vo-dialog'+randomId).remove();
						}
					}
				});
				
			},
			
			// Footer alert
			dock : function( message )
			{
				$("#dock-container").hide();
				$("#dock-container #ajax-message").empty().append( message );
				$("#dock-container").fadeIn('normal');
				setTimeout("$('#dock-container').fadeOut('slow')",4000);
			},
			
			// Safer way to post to Firebug console
			debug : function( message )
			{
				if(window.console){
					console.log(message);
				}else{
					if(typeof message != 'string'){
						message = 'Your browser doesn\'t support advanced debugging. Try Firefox and Firebug!';
					}
					alert(message);
				}
			}
		}
	});
		
/* Not Standardized */

	$.fn.addInput = function(name,value,type)
	{
		type = type ? type : 'hidden';
		$('input[type='+type+'][name='+name+']',this).remove();
		$(this).prepend($('<input>').attr({'type':type,'name':name,'value':value}));
	};
	
// Start form setup and validation
	$.fn.checkWarnings = function( buttonValue )
	{
		buttonValue = buttonValue ? buttonValue : 'Next Step >';
		
		var numWarnings = $('.warning').length;
		if(numWarnings > 0){
			$('.submit',this).attr('disabled','disabled').val('Fill in required fields');
		}else{
			$('.submit',this).removeAttr('disabled').val(buttonValue);
		}
	};

	$.fn.setFormValidation = function( buttonValue )
	{
		var requiredFlag = '<span class="required-flag">*</span>';
		$('.required-flag',this).remove();
	
		$(':input',this).filter('.required')
		.prev('label').addClass('required')
		.append(requiredFlag)
		.parents('li').addClass('warning');
		
		$(this).checkWarnings(buttonValue);
	
		$(':input:visible',this).each(setRequired).bind('keyup change',setRequired);
		
		function setRequired()
		{
			if($(this).is('.required')){
				if($(this).val()){
					$(this).parents('li:first').removeClass('warning');
				}else{
					$(this).parents('li:first').addClass('warning');
				}
				$(this).parents('form').checkWarnings(buttonValue);
			}
		};
	};

	/*	Blog Entry:
		jQuery Comments() Plug-in To Access HTML Comments For DOM Templating
		
		Author:
		Ben Nadel / Kinky Solutions
		
		Link:
		http://www.bennadel.com/index.cfm?dax=blog:1563.view
		
	*/
	
	$.fn.comments = function( blnDeep ){
		var blnDeep = (blnDeep || false);
		var jComments = $( [] );
	 
		// Loop over each node to search its children for
		// comment nodes and element nodes (if deep search).
		this.each(
			function( intI, objNode ){
				var objChildNode = objNode.firstChild;
				var strParentID = $( this ).attr( "id" );
				// Keep looping over the top-level children
				// while we have a node to examine.
				while (objChildNode){
					// Check to see if this node is a comment.
					if (objChildNode.nodeType === 8){
						// We found a comment node. Add it to
						// the nodes collection wrapped in a
						// DIV (as we may have HTML).
						/*jComments = jComments.add(
							"<div rel='" + strParentID + "'>" +
							objChildNode.nodeValue +
							"</div>"
							);*/
						
						jComments = jComments.add(objChildNode.nodeValue); // Nick modifed this
					} else if (
						blnDeep &&
						(objChildNode.nodeType === 1)
						) {
	 
						// Traverse this node deeply.
						jComments = jComments.add(
							$( objChildNode ).comments( true )
							);
					}
					// Move to the next sibling.
					objChildNode = objChildNode.nextSibling;
				}
			}
			);
		// Return the jQuery comments collection.
		return( jComments );
	};
	
	
	/*
	 * The backbone for click and discover interaction
	 */
	
	$.voCnd = {
			'settings':
				{
					'controller':null,
					'panel':'#cnd-navigation',
					'pagination':'.cnd-pagination',
					'contentDom': '',
					'contentDomRow': '',
					'filterPanel' : 0,
					'initContent' : 1
				},
			'hierarchyArray' : {}, // Cached arrays for mult-dimensional catgories
			'filterArray' : {}, // sent via ajax to controller
			'data':{}, // Set externally to be sent via ajax to controller
			'panelGroups' : {},
			'customContentFunction':{},
			'ajaxCompleteFunction': function( data, status ){},
			'resultTotal' : '', // resultTotal set in setInterface() and filterResults()
			'_currentXhr' : null,
			
			
			'init' :
				function()
				{
					$.voAjax({
						'actionController': $.voCnd.settings.controller,
						'dataObject':$.extend($.voCnd.data,{'vo-action':'init','filter_conditions':$.toJSON($.voCnd.filterArray)}),
						'success':[$.voCnd.setInterface],
						'complete':[$.voCnd.ajaxCompleteFunction]
					});
				},
				
			'setPaginationMessage' :
				function()
				{
					if($.voCnd.resultTotal){
						$('span.results .current-page',$.voCnd.settings.pagination).text(($.voCnd.filterArray['page'] + 1));
						$('span.results .total-page',$.voCnd.settings.pagination).text( Math.ceil( ($.voCnd.resultTotal / $.voCnd.filterArray['limit'])) );
						$('span.results .total-item',$.voCnd.settings.pagination).text($.voCnd.resultTotal);
					}
				},
				
			'setPagination' :
				function()
				{
					if(!$.voCnd.filterArray['page']){ $.voCnd.filterArray['page'] = 0; }

					$.voCnd.setPaginationMessage();
					$('button',$.voCnd.settings.pagination).unbind('click').click(function(e){
						var resultTotal = $.voCnd.resultTotal ? $.voCnd.resultTotal : $($.voCnd.settings.pagination+':first .total-item').text();
						if($(e.target).is('.previous')){
							var previousPage = $.voCnd.filterArray['page'] - 1;
							if( previousPage + 1 > 0 ){
								$.voCnd.filterArray['page'] = previousPage;
							}else{
								$.voCnd.filterArray['page'] = Math.floor( resultTotal / $.voCnd.filterArray['limit'] ); // go to last page
							}
							$.voCnd.getResults();
						}else{
							// page * limit < results
							var nextPage = $.voCnd.filterArray['page'] + 1;
							
							if( nextPage * $.voCnd.filterArray['limit'] < resultTotal ){
								
								$.voCnd.filterArray['page'] = nextPage;
							}else{
								$.voCnd.filterArray['page'] = 0;
							}
							$.voCnd.getResults();
						}
						
						$.voCnd.setPaginationMessage();
					});
				},
				
			'setFilterPanel' : 
				function( boolean )
				{
					$.voCnd.settings.filterPanel = boolean;
				},
				
			'setLimit' : 
				function( limit )
				{
					$.voCnd.filterArray.limit = limit;
				},
				
			'getResults' :
				function()
				{
					// **Key efficiency logic - abort other ajax requests in favor of current
					// speeds up response
					if($.voCnd._currentXhr){ $.voCnd._currentXhr.abort(); }
					$.voCnd._currentXhr = $.voAjax({
						'actionController': $.voCnd.settings.controller,
						'dataObject':$.extend($.voCnd.data,{'vo-action':null,'filter_conditions':$.toJSON($.voCnd.filterArray)}),
						'beforeSend':[$.voCnd.waitingForResults],
						'success':[$.voCnd.ajaxSuccessFunction,$.voCnd.filterResults],
						'complete':[$.voCnd.ajaxCompleteFunction]
					});
				},
				
			'setController' :
				function( location )
				{
					$.voCnd.settings.controller = location;
				},
			
			'setContentDom' :
				function( contentDom, contentDomRow )
				{
					$.voCnd.settings.contentDom = contentDom;
					$.voCnd.settings.contentDomRow = contentDomRow;
				},
				
			'preload' :
				function()
				{
					
				},
				
			'setPanelGroup' :
				function( callerSettings )
				{
					// groupName, groupDisplayName , multiDimension, defaultValue
					// Build the group object, but don't overwrite it proecedurally.
					// The interface conrtoller gets precedence over the Ajax data settings for group.
					$.voCnd.panelGroups[callerSettings.group] = $.extend({
						'displayName' : (callerSettings.displayName ? callerSettings.displayName : callerSettings.group ),
						'multiDimension' : (callerSettings.multiDimension ? 1 : 0), // if true then treat the group like a categoric hierarchy
						'dataFormatSingle' : callerSettings.dataFormatSingle,
						'filter' : callerSettings.filter,
						'filterEffect' : callerSettings.filterEffect
					},$.voCnd.panelGroups[callerSettings.group] || {});
				},
			'setGroupDefault' :
				function( groupName, id )
				{
					if(typeof($.voCnd.filterArray[groupName]) != 'object'){
						$.voCnd.filterArray[groupName] = [];
					}
					$.voCnd.filterArray[groupName].push(id);
					$.voCnd.panelGroups[groupName] = $.extend({'defaultValue':id},$.voCnd.panelGroups[groupName] || {});
				},
				
			// Group class
			'group' : 
				function( domObject, groupName, groupSettings )
				{
					var thisGroup= this;
					
					this.menuClose =
						function( e )
						{
							$('h3 span',domObject).removeClass('ui-icon-triangle-1-s');
							$('h3 span',domObject).addClass('ui-icon-triangle-1-e');
							$('.cnd-list',domObject).slideUp('fast');
						};
						
					this.menuOpen = 
						function( e )
						{
							$('h3 span',domObject).removeClass('ui-icon-triangle-1-e');
							$('h3 span',domObject).addClass('ui-icon-triangle-1-s');
							$('.cnd-list',domObject).slideDown('fast');
						};
						
					this.itemClick =
						function( e )
						{
						if($(this).is('.ui-state-disabled')){
							e.stopPropagation();
						}else{
							// Click on
							if(!$(this).is('.ui-state-active')){
								// Format interface so group data is sent as a single string
								if(groupSettings.dataFormatSingle){
									$.voCnd.filterArray[groupName] = $(this).attr('rel');
								}else{
								// Format interface so group data is sent as an array
									if((clearItemId =$.inArray($('.crumb-current',domObject).attr('rel'), $.voCnd.filterArray[groupName])) != -1){
										$.voCnd.filterArray[groupName].splice(clearItemId,1);
									}
									$.voCnd.filterArray[groupName].push($(this).attr('rel'));
									
									// Show filter-cancel button							
									if($.voCnd.filterArray[groupName].length  > 0){
										$(domObject).find('.cnd-button.cancel').show();
									}
								}
								$.voCnd.filterArray['page'] = 0;
								
								// Simulate toggle unbind current event and bind another
								/*$(this)
									.unbind('click')
									.bind('click',thisGroup.itemClickOff);*/
								if(groupSettings.dataFormatSingle){
									$(this).siblings().removeClass('ui-state-active');
								}
								$(this).addClass('ui-state-active');
								
								$.voCnd.getResults(); // Remember with new parameters we need to set page to 0
							}else{
							// Click off
								$(domObject).find('.cnd-button.cancel').show();
								
								// Remove the clicked item id
								var clickedItem = $(this).attr('rel');
								
								if(groupSettings.dataFormatSingle){
									$.voCnd.filterArray[groupName] = 0;
								}else{
									if((clearCategoryId = $.inArray(clickedItem,$.voCnd.filterArray[groupName])) != -1){
										$.voCnd.filterArray[groupName].splice(clearCategoryId,1);
									}
								}
								$.voCnd.filterArray['page'] = 0;
								
								// Remove filter-cancel button
								if(groupSettings.dataFormatSingle || $.voCnd.filterArray[groupName].length  < 1){
									if($('.crumb-current',domObject).attr('rel')){
										if(groupSettings.dataFormatSingle){
											$.voCnd.filterArray[groupName] = $('.crumb-current',domObject).attr('rel');
										}else{
											$.voCnd.filterArray[groupName] = [$('.crumb-current',domObject).attr('rel')];
										}
									}
									$(domObject).find('.cnd-button.cancel').hide();
								}
								
								// Set class to off
								$(this).removeClass('ui-state-active');
								$.voCnd.getResults(); // Remember with new parameters we need to set page to 0
							}
						}
					};
						
					this.reset =
						function( e )
						{
							$(this).hide();
							$('li.ui-state-active', domObject)
								.removeClass('ui-state-active');
							
							if($('.crumb-current',domObject).attr('rel')){
								if(groupSettings.dataFormatSingle){
									$.voCnd.filterArray[groupName] = $('.crumb-current',domObject).attr('rel');
								}else{
									$.voCnd.filterArray[groupName] = [$('.crumb-current',domObject).attr('rel')];
								}
							}else{
								$.voCnd.filterArray[groupName] = [];
							}
							$.voCnd.getResults();
						};
					/**
					 * filterResults turns group items on or off based on returned panelFilter data.
					 */
					this.filterResults =
						function( groupFilter )
						{
							//$.voMessage.debug(groupFilter);
							
/**/						// Hack: If results are filtered out, e.g. brand, then we need to remove them from query
							// and go get results again. This should be done on php side eventually
							var rerunResults = false;
							$('ul.cnd-list li', domObject).each(function(i, item){
								if($.inArray(parseInt($(item).attr('rel')), groupFilter) != -1){
									if(groupSettings.filterEffect == 'hide'){
										$(item).show();
									}else{
										$(item).removeClass('ui-state-disabled');
									}
								}else{
									if(groupSettings.filterEffect == 'hide'){
										$(item).hide();
									}else{
										$(item).addClass('ui-state-disabled');
									}
									
								// Remove filter ids
									if(groupSettings.dataFormatSingle){
										$.voCnd.filterArray[groupName] = 0;
									}else{
										if((clearCategoryId = $.inArray($(item).attr('rel'),$.voCnd.filterArray[groupName])) != -1){
											$.voCnd.filterArray[groupName].splice(clearCategoryId,1);
											rerunResults = true;
										}
									}
										
								}
							});
							if(rerunResults){ $.voCnd.getResults(); }
						};
					
					this.formatMultiDimension =
						function( cid, data )
						{
							// Initialize cache and breadcrumb dom here
							if(typeof($.voCnd.hierarchyArray[groupName]) != 'object'){
								
								$.voCnd.hierarchyArray[groupName] = (data.panel[groupName]['array'] ? data.panel[groupName]['array'] : data.panel[groupName] ); // cache the hierarchy
								
								$('h3',domObject).append('<span class="crumb-parent" />');
								$('h3',domObject).append('<span class="crumb-current" />');
								
								// Events		
								
								// Current Category and Parent
								$('h3 span.crumb-parent',domObject).unbind('click').click(function(){
									if(groupSettings.dataFormatSingle){
										if($(this).attr('rel') > 0){
											$.voCnd.filterArray[groupName] = $(this).attr('rel');
										}else{
											$.voCnd.filterArray[groupName] = '';
										}
									}else{
										$.voCnd.filterArray[groupName] = [];
										if($(this).attr('rel') > 0){
											$.voCnd.filterArray[groupName].push($(this).attr('rel'));
										}
									}
									
									$.voCnd.filterArray['page'] = 0;
									$(domObject).find('.cnd-button.cancel').hide();
									$.voCnd.getResults();
									thisGroup.formatMultiDimension( $(this).attr('rel') );
									return false;
								});
							}
							
							function getCategoryStructure(categoryArray, cid, parentObject)
							{
							// first level if there will be no parent object, the return category array
								
								if(typeof(cid) == 'undefined' || cid == 0 ){
									return {'parent':null,'categoryArray':{'children':categoryArray}};
								}else{
								// If cid is set then start looking for the id
									if(typeof(retVal) != 'object'){ var retVal = {}; };
									$.each(categoryArray, function(key, category){
										if( category.id == cid ){										
											parentObject = typeof(parentObject) == 'object' ? parentObject : null;
											
											// If this category has no children, then step back up the branch
											if($(category.children).length > 0){
												retVal = {'parent':parentObject,'categoryArray':category};
											}else{
												if(parentObject != null){
													retVal = {'parent':parentObject.parentObject,'categoryArray':parentObject};
												}else{
													retVal = {'parent':null,'categoryArray':{'children':categoryArray}};
												}
											}
											
											return false;
										}else{
											
											if( $(category.children).length > 0 && typeof(retVal.categoryArray) != 'object' ){
												var parent = category;
												parent.id = category.id;
												parent.parentObject = parentObject; // (parent's parent) allows for stepping back up the branch
												retVal = getCategoryStructure(category.children, cid, parent);
											}
										}
									});
									
									return retVal;
								}
							};
							
							var categoryStructure = getCategoryStructure($.voCnd.hierarchyArray[groupName],cid);
							
							var category = categoryStructure.categoryArray;
							var parent = categoryStructure.parent ? categoryStructure.parent : null;
							
								if(cid > 0){
									// $.voMessage.debug(category.name);
									if(category.name){
										$('h3 span.crumb-current',domObject).html('&gt; '+category.name).attr('rel',category.id).css('display','block');
									}
								}else{
									$('h3 span.crumb-current',domObject).empty().removeAttr('rel');
								}
								
								if(parent){
									$('h3 span.crumb-parent',domObject).text(parent.name).attr('rel',parent.id);
								}else{
									
									$('h3 span.crumb-parent',domObject).text(groupSettings.displayName).attr('rel',0);
								}
								
								$('li',domObject).remove();
								if( category.children ){
									$.each(category.children, function(i,child){
						
										var newList = $('<li rel=\"'+child.id+'\" class="'+groupName+' ui-state-default">'+child.name+'</li>');
										
										if(!groupSettings.dataFormatSingle){
											if($.inArray(child.id,$.voCnd.filterArray[groupName]) != -1){
												newList.addClass('ui-state-active');
												$(domObject).find('.cnd-button.cancel').show();
											}
										}else{
											if(child.id == $.voCnd.filterArray[groupName]){
												newList.addClass('ui-state-active');
												$(domObject).find('.cnd-button.cancel').show();
											}
										}
										
										if($(child.children).length > 0 ){
											newList.click(function(){
											// If the single data format is set, then set the ajax data as a string rather than an array
												if(groupSettings.dataFormatSingle){
													$.voCnd.filterArray[groupName] = $(this).attr('rel');
												}else{
													$.voCnd.filterArray[groupName] = [];
													$.voCnd.filterArray[groupName].push($(this).attr('rel'));
												}
												$.voCnd.filterArray['page'] = 0;
												//$.voMessage.debug($.voCnd.filterArray[groupName]);
												$.voCnd.getResults();
												thisGroup.formatMultiDimension($(this).attr('rel'));
												//
												$('.cnd-list li.ui-state-active',domObject).removeClass('ui-state-active');
												$('.cnd-list li[rel='+$(this).attr('rel')+']',domObject).unbind('hover').removeClass('ui-state-hover').addClass('ui-state-active');
												return false;
											});
										}else{
											// Removing the parent only matters on array formatted ajax data
											if(!groupSettings.dataFormatSingle){
												// !! Important, remove the parent id from the array.
												if((clearParent = $.inArray(category.id,$.voCnd.filterArray[groupName])) != -1){
													$.voCnd.filterArray[groupName].splice(clearParent,1);
												}
											}
											newList.click(thisGroup.itemClick);
										}
										$('.cnd-list', domObject).append(newList);
									});
								}
						};
						
					this.formatSingleDimension =
						function( data )
						{
							$('h3',domObject).prepend($('<span>'+groupSettings.displayName+'</span>'));
							
							var panelArray = (data.panel[groupName]['array'] ? data.panel[groupName]['array'] : data.panel[groupName] ); // Backward compat
							
							$.each(panelArray, function( liKey, liData ){
								var newList = $('<li rel=\"'+liKey+'\" class="'+groupName+' ui-state-default">'+liData.name+'</li>');
								$(newList).attr('rel',liKey);
								
								if(!groupSettings.dataFormatSingle){
									if($.inArray(liKey,$.voCnd.filterArray[groupName]) != -1){
										newList.addClass('ui-state-active');
										$(domObject).find('.cnd-button.cancel').show();
									}
								}
								$(newList).click( thisGroup.itemClick );
								$('.cnd-list',domObject).append(newList);
							});
						};
						
					return this;
				},
				
			'setInterface' :
				function(data, status)
				{
					$.voCnd.resultTotal = data.resultTotal;
					$.voCnd.setPagination();
					
				// Set panel dynamically from ajax feed
					$.each(data.panel, function(groupName, groupSettings){
						$.voCnd.setPanelGroup({
							'group':groupName,
							'displayName':groupSettings.display_name,
							'multiDimension':(groupSettings.multi_dimension ? groupSettings.multi_dimension : 0),
							'dataFormatSingle':(groupSettings.data_format_single ? 1 : 0),
							'filter':(groupSettings.filter_panel ? 1 : 0),
							'filterEffect':(groupSettings.filter_effect ? groupSettings.filter_effect : 'disable')
						});
					});
					
					// Set Each Panel Group
					$.each(data.panel, function(groupName){
						var groupSettings = $.voCnd.panelGroups[groupName];
					
						if( !groupSettings.dataFormatSingle && typeof($.voCnd.filterArray[groupName]) != 'object'){ 
							groupSettings.defaultValue = $.voCnd.filterArray[groupName] ? $.voCnd.filterArray[groupName] : [];
							$.voCnd.filterArray[groupName] = $.voCnd.filterArray[groupName] ? $.voCnd.filterArray[groupName] : []; 
						}else{
							groupSettings.defaultValue = $.voCnd.filterArray[groupName] ? $.voCnd.filterArray[groupName] : "";
							$.voCnd.filterArray[groupName] = $.voCnd.filterArray[groupName] ? $.voCnd.filterArray[groupName] : "";
						}
	
						object = $('<div id="cnd-'+ groupName +'" class="cnd-header" />');
						groupObject = new $.voCnd.group( object, groupName, groupSettings );

						$('li',object).remove();
						var collapseButton = $('<div class="ui-state-default ui-corner-all cnd-button collapse"><span class="ui-icon ui-icon-triangle-1-s" /></div>')
												.toggle(groupObject.menuClose, groupObject.menuOpen );
						var cancelButton = $('<div class="ui-state-default ui-corner-all cnd-button cancel"><span class="ui-icon ui-icon-cancel" /></div>')
												.hide()
												.bind('click',groupObject.reset);

						$('<h3 />')
							.addClass('ui-corner-all')
							//.text( groupSettings.displayName ) for now I am doing this in the singleDim and multiDim functions
							.appendTo(object)
							.append(cancelButton)
							.append(collapseButton);
						
						$('<ul class="cnd-list"></ul>').appendTo(object);
						
						// Load group's item list
						
						// Multi Dimensional
						if( groupSettings.multiDimension ){
							groupObject.formatMultiDimension((groupSettings.defaultValue ? groupSettings.defaultValue : 0), data);
							
						// Single Dimension
						}else{
							groupObject.formatSingleDimension( data );
						}
						
						if(typeof(data.panelFilter[groupName]) == 'object'){
							object.show();
							if(groupSettings.filter){
								groupObject.filterResults( data.panelFilter[groupName] );
							}
						}else{
							object.hide();
						}
						
						$($.voCnd.settings.panel).append(object);
					});
					
					// Set Content
					if( $.voCnd.settings.initContent ){
						$.voCnd.setContent(data.content);
					}
				},
			'waitingForResults' :
				function()
				{
					$($.voCnd.settings.contentDom).hide();
					$('.no-results').hide();
					$('.waiting-for-results').show();
				},
				
			'filterResults' :
				function( data )
				{
					$.voCnd.resultTotal = data.resultTotal;
					$.voCnd.setPaginationMessage();
					// Set Each Panel Group
					$.each($.voCnd.panelGroups, function(groupName, groupSettings){
						var groupObject = new $.voCnd.group( $('#cnd-'+ groupName), groupName, groupSettings );
						if(typeof(data.panelFilter[groupName]) == 'object'){
							$('#cnd-'+ groupName).show();
							if(groupSettings.filter){
								groupObject.filterResults( data.panelFilter[groupName] );
							}
						}else{
							$('#cnd-'+ groupName).hide();
						}
					});
					
					// Set Content
					$('.waiting-for-results').hide();
					// Slower but more flexible for interface developers
					if(data.content_html){
						$($.voCnd.settings.contentDom).replaceWith($(data.content_html).filter('ul'));
					}else{
					// Faster because unformatted Json data is sent and is formatted by javascript.
						$.voCnd.setContent(data.content);
					}
					$($.voCnd.settings.contentDom).fadeIn('fast');
				},
				
			'setContent':
				function( content )
				{
				var thisObject = this;
					var $rowTemplate = $(thisObject.settings.contentDom).comments();
					$(thisObject.settings.contentDomRow,thisObject.settings.contentDom).remove();
					
					if($(content).length > 0 ){
						$('.no-results').hide();
						$.each(content, function(key, contentItem){
							// Set list display
							
								var $newRow = $rowTemplate.clone();
								$newRow.setDataDisplay( contentItem );
								$.voCnd.customContentFunction( key, contentItem, $newRow );
								$(thisObject.settings.contentDom).append( $newRow );
						});
					}else{
						$('.no-results').show();
					}
				}
	};
	
	$.voSlugFormat = function( slug )
	{
		var newSlug = slug.replace(/[^a-zA-Z0-9\s\-]/g,'');
		newSlug = newSlug.replace(/\s+/g,'-');
		return newSlug.toLowerCase();
	};
	
/* Non-Standard */
	$.fn.setRSSItemDisplay = function(jsonObject)
	{
		$('.title',this).text(jsonObject.title[0].Text);
		$('.link',this).attr('href',jsonObject.link[0].Text);
		$('.description',this).html(jsonObject.description[0].Text);
		
		//$(this).show();
		return this;
	};
	
	$.fn.setRSSChannelDisplay = function(jsonObject)
	{
		$('.title',this).text(jsonObject.title[0].Text);
		$('.link',this).attr('href',jsonObject.link[0].Text);
		$('.description',this).text(jsonObject.description[0].Text);
		//$('.image',this).attr('src',jsonObject.image[0].url[0].Text);
		
		//$(this).show();
		return this;
	};
	
	// Depends on jquery.XMLUtils.pack.js
	$.fn.XMLReader = function(callerSettings)
	{
		var settings = $.extend({
			feed: false,
			sortName: 'title',
			sortOrder: 'ASC',
			limit: false
		}, callerSettings || {});
		
		var object = this;
		var feed = settings.feed ? settings.feed : $(this).attr('data-feed');
		
		$.ajax({
			type: 'POST',
			url: 'xml',
			data:{feed:feed},
			dataType: 'xml', //Make sure that you specify the type of file you expecting (XML)
			complete: function(data) {
				// Grab the display template
				var feedChannelTemplate = $('.rss-channel',object).remove();
				var feedItemTemplate = $('.rss-items .template',object).remove();
				var json = $.xmlToJSON(data.responseXML); //Please notice that we use responseXML here which is DOMDocument object
				
				$(object).prepend($(feedChannelTemplate).setRSSChannelDisplay(json.channel[0]));
				
				// Now I want to sort all item nodes by their value
				json.channel[0].item.SortByNode(settings.sortName,settings.sortOrder); //Default order is ASC
				for(var i = 0; i < json.channel[0].item.length; i++) {
					var newList = $(feedItemTemplate).clone();
					$('.rss-items', object).append($(newList).setRSSItemDisplay(json.channel[0].item[i]));
				}
				
				if( settings.limit > 0 ){
					$('.rss-items li:gt('+ (settings.limit - 1) +')', object).hide();
				}
			}
		});
	};
	
/* Deprecated */
	
	// Deprecated because setDataDisplay    
	$.fn.setAddressForm = function(addressObject)
	{
		$(this).attr('data-json','{id:' + addressObject.id + '}');
		$('input[name=full_name]',this).val(addressObject.full_name);
		$('input[name=address1]',this).val(addressObject.address1);
		$('input[name=address2]',this).val(addressObject.address2);
		$('input[name=city]',this).val(addressObject.city);
		$('input[name=state]',this).val(addressObject.state);
		$('input[name=zip]',this).val(addressObject.zip);
		$('input[name=phone]',this).val(addressObject.phone);
		
		addressObject.default_billing ? $('input[name=type_billing]').attr('checked','checked') : $('input[name=type_billing]').attr('checked','');
		addressObject.default_shipping ? $('input[name=type_shipping]').attr('checked','checked') : $('input[name=type_shipping]').attr('checked','');
		
		//addressObject.default_billing ? $('input[name=phone]',this)
		
		return this;
	};
	
})(jQuery);
	
// This assists file uploads. We can clean this up later
	var newStageImageTemplate; // For adding dom outside of ready function
	var voFile = {
		'settings':
			{
				'ulDom':''
			}
		,
		'addFileToDom':
			function( id, fileName )
			{
				var $newRow = typeof(newStageImageTemplate) == 'object' ? newStageImageTemplate.clone() : $(voFile.settings.ulDom).comments();
				$newRow.attr('id','loading'+id);
				$newRow.attr('class','loading');
				var $progressBar = $('<div class="progress-bar" />').progressbar({value:0});
				$newRow.append('<div class="loading-title">Loading '+ fileName +'</div>');
				$newRow.append($progressBar);
				$('img', $newRow).hide();
				
				$newRow.appendTo(voFile.settings.ulDom);
				needToSave = 1;
			}
		,
		'setProgressBar':
			function setProgressBar( id, percent )
			{
				$('#loading'+id+' .progress-bar').progressbar('option', 'value', percent);
			}
		,
		'loadThumbnail':
			function loadThumbnail( id, flashEvent )
			{
				$('#loading'+id+' .progress-bar').progressbar('destroy');
				$('.progress-bar, .loading-title',$('#loading'+id)).remove();
				// Load image here
				var data = $.evalJSON(flashEvent.data);
				voFile.setInterface( '#loading'+id, data );
				$('#loading'+id).attr('id','').removeClass('loading');
			}
		,
		'setInterface':
			function( loadingObject, data )
			{
				// Set externally 
			}		
	};

// END OF PLUGINS

// Body stuff

/*
Example DOM:
<ul id="n1">
	<li>Level 1
		<ul>
			<li>Level 2</li>
			<li>Level 2</li>
		</ul>
	</li>
	<li>Level 1</li>
</ul>

*/

$(document).ready(function(){
		
$("#main-navigation").navigationMenu();
	var nav1 = $('.dropdowns');
	var nav2 = $('li ul',nav1);

	function nav(level)
	{
		var nextLevel = $('li ul',level);
		$(nextLevel).hide()
			.siblings('a').addClass('button').removeAttr('href')
			.mouseover(function(){
				//$(nextLevel).not(':hidden').hide('slow');

				if($(this).siblings('ul').is(':hidden')){
					$(nextLevel).siblings('a').removeClass('buttonOver');
					$(this).addClass('buttonOver');

					$(nextLevel).slideUp('slow');
					$(this).siblings('ul').slideDown('slow');
				}else{
					$(nextLevel).siblings('a').removeClass('buttonOver');
					$(this).siblings('ul').slideUp('slow');
				}
			});
	}
	
	// Click Image Button
	$('#dialog-media-manager').dialog({
		'autoOpen':false,
		'bgiframe':true,
		'height':450,
		'width':960,
		'modal':true,
		'position':'top',
		'title':'Media Manager'
	});
	
// Forms
	$('label.hint').each(function(){
		var labelText	= $(this).remove().text();
		var forField	= $(this).attr("for");
		var input		= $("input[name='"+forField+"']");
		if(!input.val()){
			$(input).addClass('placeholder').val(labelText).focus(function(){
				if(this.value == labelText){
					$(this).removeClass('placeholder').val('');
				};
			}).blur(function(){
				if(this.value == ''){
					$(this).addClass('placeholder').val(labelText);
				};
			});
		}
	});
	
	 
	
//	$('.ui-state-default').livequery(function(){
//		$(this).hover(function(){
//			$(this).addClass('ui-state-hover');
//		},
//		function(){
//			$(this).removeClass('ui-state-hover');
//		});
//	}, function() { 
//		// unbind the mouseover and mouseout events 
//		$(this) 
//			.unbind('mouseover') 
//			.unbind('mouseout'); 
//	});

});
//Handle money formatting
function isThousands( position )
{
	if (Math.floor(position/3)*3==position) return true;
	return false;
};

function formatMoney (theNumber,theCurrency,theThousands,theDecimal)
{
	var theDecimalDigits = Math.round((theNumber*100)-(Math.floor(theNumber)*100));
	theDecimalDigits= ""+ (theDecimalDigits + "0").substring(0,2);
	theNumber = ""+Math.floor(theNumber);
	var theOutput = theCurrency;
	for (x=0; x<theNumber.length; x++) {
		theOutput += theNumber.substring(x,x+1);
		if (isThousands(theNumber.length-x-1) && (theNumber.length-x-1!=0)) {
			theOutput += theThousands;
		};
	};
	
	theOutput += theDecimal + theDecimalDigits;
	return theOutput;
};
