/**
 * jQuery custom selectboxes
 * 
 * Copyright (c) 2008 Krzysztof Suszyński (suszynski.org)
 * Licensed under the MIT License:
 * http://www.opensource.org/licenses/mit-license.php
 *
 * @version 0.6.1
 * @category visual
 * @package jquery
 * @subpakage ui.selectbox
 * @author Krzysztof Suszyński <k.suszynski@wit.edu.pl>
**/
(function($) {
	$.fn.selectbox = function(options){
		/* Default settings */
		var settings = {
			className: 'jquery-selectbox',
			animationSpeed: "normal",
			listboxMaxSize: 20,
			replaceInvisible: false
		};
		
		settings.selectorByClassName = '.' + settings.className.split(' ').join('.');
		
		var commonClass = 'jquery-custom-selectboxes-replaced';
		var listOpen = false;
		var showList = function(listObj) {
			var selectbox = listObj.parents(settings.selectorByClassName);
			listObj.slideDown(settings.animationSpeed, function(){
				listOpen = true;
			});
			selectbox.addClass('selecthover');
			jQuery(document).bind('click', onBlurList);
			return listObj;
		}
		var hideList = function(listObj) {
			var selectbox = listObj.parents(settings.selectorByClassName);
			listObj.slideUp(settings.animationSpeed, function(){
				listOpen = false;
				jQuery(this).parents(settings.selectorByClassName).removeClass('selecthover');
			});
			jQuery(document).unbind('click', onBlurList);
			return listObj;
		}
		var onBlurList = function(e) {
			var trgt = e.target;
			var currentListElements = jQuery(settings.selectorByClassName + '-list:visible').parent().find('*').andSelf();
			//settings.selectorByClassName
			if(jQuery.inArray(trgt, currentListElements)<0 && listOpen) {
				hideList( jQuery('.' + commonClass + '-list') );
			}
			return false;
		}
		
		/* Processing settings */
		settings = jQuery.extend(settings, options || {});
		/* Wrapping all passed elements */
		return this.each(function() {
			var _this = jQuery(this);
			if(_this.filter(':visible').length == 0 && !settings.replaceInvisible)
				return;
			var replacement = jQuery(
				'<div class="' + settings.className + ' ' + commonClass + '">' +
					'<div class="' + settings.className + '-moreButton" />' +
					'<div class="' + settings.className + '-list ' + commonClass + '-list" />' +
					'<span class="' + settings.className + '-currentItem" />' +
				'</div>'
			);
			jQuery('option', _this).each(function(k,v){
				var v = jQuery(v);
				var listElement =  jQuery('<span class="' + settings.className + '-item value-'+v.val()+' item-'+k+'">' + v.text() + '</span>');	
				listElement.click(function(){
					var thisListElement = jQuery(this);
					var thisReplacment = thisListElement.parents(settings.selectorByClassName);
					var thisIndex = thisListElement[0].className.split(' ');
					for( k1 in thisIndex ) {
						if(/^item-[0-9]+$/.test(thisIndex[k1])) {
							thisIndex = parseInt(thisIndex[k1].replace('item-',''), 10);
							break;
						}
					};
					var thisValue = thisListElement[0].className.split(' ');
					for( k1 in thisValue ) {
						if(/^value-.+$/.test(thisValue[k1])) {
							thisValue = thisValue[k1].replace('value-','');
							break;
						}
					};
					thisReplacment
						.find(settings.selectorByClassName + '-currentItem')
						.text(thisListElement.text());
					thisReplacment
						.find('select')
						.val(thisValue)
						.triggerHandler('change');
					var thisSublist = thisReplacment.find(settings.selectorByClassName + '-list');
					if(thisSublist.filter(":visible").length > 0) {
						hideList( thisSublist );
					}else{
						showList( thisSublist );
					}
				}).bind('mouseenter',function(){
					jQuery(this).addClass('listelementhover');
				}).bind('mouseleave',function(){
					jQuery(this).removeClass('listelementhover');
				});
				jQuery(settings.selectorByClassName + '-list', replacement).append(listElement);
				if(v.filter(':selected').length > 0) {
					jQuery(settings.selectorByClassName + '-currentItem', replacement).text(v.text());
				}
			});
			replacement.find(settings.selectorByClassName + '-moreButton').click(function(){
				var thisMoreButton = jQuery(this);
				var otherLists = jQuery(settings.selectorByClassName + '-list')
					.not(thisMoreButton.siblings(settings.selectorByClassName + '-list'));
				hideList( otherLists );
				var thisList = thisMoreButton.siblings(settings.selectorByClassName + '-list');
				if(thisList.filter(":visible").length > 0) {
					hideList( thisList );
				}else{
					showList( thisList );
				}
			}).bind('mouseenter',function(){
				jQuery(this).addClass('morebuttonhover');
			}).bind('mouseleave',function(){
				jQuery(this).removeClass('morebuttonhover');
			});
			_this.hide().replaceWith(replacement).appendTo(replacement);
			var thisListBox = replacement.find(settings.selectorByClassName + '-list');
			var thisListBoxSize = thisListBox.find(settings.selectorByClassName + '-item').length;
			if(thisListBoxSize > settings.listboxMaxSize)
				thisListBoxSize = settings.listboxMaxSize;
			if(thisListBoxSize == 0)
				thisListBoxSize = 1;
			var thisListBoxWidth = Math.round(_this.width() + 60);
			replacement.css('width', thisListBoxWidth + 'px');
			thisListBox.css({
				width: Math.round(thisListBoxWidth-5) + 'px'
			});
		});
	}
	$.fn.unselectbox = function(){
		var commonClass = 'jquery-custom-selectboxes-replaced';
		return this.each(function() {
			var selectToRemove = jQuery(this).filter('.' + commonClass);
			selectToRemove.replaceWith(selectToRemove.find('select').show());
		});
	}
})(jQuery);