(function($)
{
	var imgCache = [];
	
	/* 
	 * Usage:
	 * 
	 * $('#search').defaultText('Search the site');
	 * $('.required').defaultText('Required');
	 * $('#myfield').defaultText('Don\'t replace this text', false);
	 */
	$.fn.defaultText = function(text, replace)
	{
		if (typeof replace == 'undefined')
		{
			replace = true;
		}
		
		var $fo = $(this).parents('form');
		
		$(this).each(function()
		{
			var $fi = $(this);
			
			// Set the default text if not already
			if ($.trim($fi.val()) == '')
			{
				$fi.val(text);
			}
			
			if (replace)
			{
				// React depending on presence of default text
				$fi.focus(function()
				{
					if ($.trim($fi.val()) == text)
					{
						$fi.val('');
					}
				}).blur(function()
				{
					if ($.trim($fi.val()) == text)
					{
						$fi.val(text);
					}
					else if ($.trim($fi.val()) == '')
					{
						$fi.val(text);
					}
				});
			}
			
			// Make sure default text gets sent as nothing instead
			$fo.each(function()
			{
				$(this).submit(function()
				{
					if ($.trim($fi.val()) == text)
					{
						$fi.val('');
					}
				});
			});
		});
		
		return this;
	};
	
	/* 
	 * Usage:
	 * 
	 * $('#mylink').hoverFade({
	 *     opcIn: opacityOnMouseOver, 
	 *     opcOut: opacityOnMouseOut, 
	 *     speed: fadeSpeed
	 * });
	 */
	$.fn.hoverFade = function(options)
	{
		var defaults = {
			opcIn: 1.0, 
			opcOut: 0.5, 
			speed: 100
		}, 
			settings = $.extend(defaults, options);
		
		this.each(function()
		{
			var $t = $(this);
			
			$t.css('opacity', settings.opcOut).hover(function()
			{
				// Mouse over, fade in to this opacity
				$t.animate({ opacity: settings.opcIn }, settings.speed);
			}, function()
			{
				// Mouse over, fade out to that opacity
				$t.animate({ opacity: settings.opcOut }, settings.speed);
			});
		});
		
		return this;
	};
	
	/* 
	 * Usage:
	 * 
	 * $('#myelm')
	 *     .animate(fancyAnimationObject)
	 *     .idle(timeMilliseconds)
	 *     .animate(anotherFancyAnimationObject);
	 */
	$.fn.idle = function(time)
	{ 
		var $t = $(this);
		
		$t.queue(function()
		{
			setTimeout(function()
			{
				$t.dequeue();
			}, time);
		});
		
		return this;
	};
	
	/* 
	 * Usage:
	 * 
	 * $.preloadImages('path/to/image.png', 'path/to/another-image.gif');
	 */
	$.preloadImages = function()
	{
		for (var i = arguments.length; i--;)
		{
			var img = document.createElement('img');
			img.src = arguments[i];
			imgCache.push(img);
		}
	};
// I think self-invoking closures are cute
})(jQuery);