(function($){
	$(function(){
		var 
			drpdwn_height	= 26,
			search_func = function( search_string , value )
				{
					var
						regex = new RegExp( escape( value ) , "i" );
													
					$( search_string )
						.each(
							function()
								{									
									if( !regex.test( $( this ).text() ) )
										$( this )
											.removeClass( 'show' );
								}
							);
				},
			escape = function( str )
				{
					return str.replace(new RegExp("[.*+?|()\\[\\]{}\\\\]", "g"), "\\$&");
				};
	
		$('.dropdown_container')
			//Het laten zien van de lijst
			.live( 'show_list' , function()
				{
					var $container 	= $( '.dropdown_box_container' , $( this ) ),
						$list		= $( 'div.dropdown_box_list' , $container.parent() );

					$container.trigger( 'pos_list' );

					$list.show();
				}
			)
			//Het verstoppen van de lijst
			.live( 'hide_list' , function()
				{
					var $container 	= $( '.dropdown_box_container' , $( this ) ),
						$list		= $( 'div.dropdown_box_list' , $container.parent() );

					$list.hide();
				}
			)
			//Het positioneren van de lijst
			.live( 'pos_list' , function()
				{
					var $container	= $( '.dropdown_box_container' , $( this ) ),
						pos			= $container.position(),
						$list		= $( 'div.dropdown_box_list' , $container.parent() ),
						margin		=  parseInt( $container.css("margin-left").replace( "px" , "" ) , 10 );

					$list
						.css(
							{
								//Als positioneren bugged, ik heb hier eval weggesloopt
								top		: ( pos.top + drpdwn_height ) + "px",
								left	: ( pos.left + margin + 5) + "px"
							}
						);
				}
			)
			//De click op een item handlen
			.live( 'handle_click' , function( e , sel_id )
				{
					var
						$container	= $( this ),
						$sel_li		= $( 'ul li#' + sel_id , $container ),
						cont_data	= $container
										.data( "dropdown" ),
						sel_aantal	= $( 'li.choice' , $container ).length;
						
					if( !$sel_li.hasClass( 'optgroup' ) )
					{
						if( sel_aantal === cont_data.max_select_items && cont_data.max_select_items > 1 )
						{
							if( $sel_li.is( '.choice' ) )
							{
								$sel_li
									.removeClass( 'choice' )
									.children( ':checkbox' )
									.removeAttr( 'checked' );
							}
							else
								$container.trigger( 'max_select_reached' );
						}
						else if( cont_data.max_select_items === 1 )
						{
							var 
								$val_field = $( 'input[type=hidden]' , $container );
							
							//Keuze class verwijderen bij de anderen, omdat er maar 1 geselecteerd kan worden
							$( 'li.choice' , $container )
								.removeClass( 'choice' );
							
							//Keuze class toevoegen
							$sel_li
								.addClass( 'choice' );
							
							//Wijziging doorvoeren in het hidden field
							$val_field
								.val( sel_id.replace( "val_" , "" ) );
							
							//List hiden
							$( this ).trigger( 'hide_list' );
						}
						else
						{							
							if( $sel_li.is( '.choice' ) )
							{
								$sel_li
									.removeClass( 'choice' );
							
								//De checkbox checken
								if( $( ':checkbox' , $sel_li ).length > 0 )
									$( ':checkbox' , $sel_li ).removeAttr( 'checked' );
							}
							else
							{
								//De keuze doorvoeren
								$sel_li
									.addClass( 'choice' );

								//De checkbox checken
								if( $( ':checkbox' , $sel_li ).length > 0 )
								{									
									$( ':checkbox' , $sel_li ).attr( 'checked' , true );
								}
							}
						}
						$( this )
							.trigger( 'change_value' );
					}
					else
					{
						$container.trigger( 'cant_select_optgroup' );
					}
					$container
						.trigger("dropdown_callback", [sel_id.replace("val_","")]);
				}
			)
			//Value wijzigen
			.live( 'change_value' , function()
				{
					var 
						$container	= $( this ),
						$var_field	= $container
										.children( '.dropdown_box_container' )
										.children( '.dropdown_box_value' ),
						$list		= $container
										.children( 'div.dropdown_box_list' )
										.children( 'ul' ),
						selected	= $( '.choice' , $list )
										.length,
						destValue	= "",
						$contData	= $container.data("dropdown"),
						change		= true;
						
					if( $( 'input' , $var_field ).length > 0 && !$( 'input' , $var_field ).is( '.no_search') )
						change = false;
					
					if( change )
					{
						if( selected === 1 )
							//Als er 1 geselecteerd is: value = value van die li
							destValue = $.trim( $( 'li.choice span' , $list ).html() );
						else if( selected > 1 )
							//Als er meer geselecteerd zijn: 10 items geselecteerd
							destValue = selected + " items geselecteerd";
						else if( $( 'li.optgroup span' , $list  ).length > 0 )
							//Bij 0 geselecteerde items: eerste optgroup value
							destValue = $.trim( $( 'li.optgroup:first span' , $list ).html() );
						else
							//Geen optgroup: gewoon eerste value
							destValue = $.trim( $( 'li:first span' , $list ).html() );

						/**
						 * Toevoeging: maximale aantal selecties aan het einde
						 */
						if( $contData.max_select_items > 1 )
							destValue += " (max. " + $contData.max_select_items + ")";

						//Hier krijgt het field ook echt zn value
						if( $( 'input' , $var_field ).length >= 1 )
						{
							if( $( 'input' , $var_field ).is( '.no_search' ) )
							{
								//Wanneer er een textfield aanwezig is: value daarvan wijzigen
								$var_field
									.children( 'input' )
									.val( destValue );
							}						
						}
						else
							//Anders gewoon de html van de div wijzigen
							$var_field
								.html( destValue );
					}
				}
			);

		//Click op de button
		$( 'div.dropdown_box_button, div.dropdown_box_value' )
		//$( 'div.dropdown_box_container' )
			.live( 'click' , function( e )
				{
					var $container 	= $( this )
										.parent()
										.parent(),
						$list		= $( 'div.dropdown_box_list' , $container );

					$( '.dropdown_container' )
						.not( $container )
						.trigger( 'hide_list' );

					if( $list.is( ':hidden' ) )
						$container
							.trigger( 'show_list' );
					else if( !$( e.target ).is( 'input' ) )
						$container
							.trigger( 'hide_list' );
					
					//Zorgen dat het event niet naar het document bubbled
					e.stopImmediatePropagation();
					return false;
				}
		);
		
		//De zoek variabele waar de timeout in staat
		var zoeken;
		
		//De keyup event, hier wordt dus gezocht!:D
		$( 'div.dropdown_box_value input' )
			.live( 'keyup' , function( e )
				{
					window
						.clearTimeout( zoeken );
					
					var	
						search		= $( this )
										.val(),
						$container	= $( this )
										.closest( '.dropdown_container' ),
						prev_search	= $container
										.data( "dropdown" )
										.last_search
									||
									  search,
						jQuery_src	= "div.dropdown_box_list ul li.show";
					
					if( search.substr( 0 , prev_search.length ) !== prev_search )
						$( 'div.dropdown_box_list ul li' )
							.addClass( 'show' );
					
					zoeken = setTimeout( 
								function()
									{
										search_func( jQuery_src , search );
									} 
								, 200 );
					
					$container
						.data( "dropdown" )
						.last_search = search;
				}
			);

		$( '.dropdown_container div.dropdown_box_list ul li.show' )
			.live( 'click' , function( e )
			 	{
					var
						$container 	= $( this )
										.closest( '.dropdown_container' ),
						$target		= $( e.target ),
						li_id		= $( this )
										.attr('id');
						
					$( this ).trigger( 'handle_click' , [ li_id ] );

					e.stopImmediatePropagation();

					return false;
				}
			);
		
		//Hover, omdat internet explorer pauper is
		$( 'div.dropdown_box_list ul li' )
			.live( 'mouseover' ,
				function()
					{
						$( 'div.dropdown_box_list ul li.selected' )
							.removeClass( 'selected' );
						
						$( this ).addClass( 'selected' );
					} )
			.live( 'mouseout' , 
				function()
					{
						$( 'div.dropdown_box_list ul li.selected' )
							.removeClass( 'selected' );
					}
				);


		$( document )
			.bind( 'click' , function( e )
				{
					if( !$( e.target ).is( 'div.dropdown_box_list :checkbox' ) )
						$( '.dropdown_container' ).trigger( 'hide_list' );
				}
			);
	});
	
	$.fn.dropdown = function(options2) {
		var defaults = 
			{
				"select_list"				: true,
				"filter_items"				: false,
				"max_select_items"			: 1,
	 			"button_background"			: '/media/gasdokter/images/dropdown_right.png',
	 			"button_background_click"	: '/media/gasdokter/images/dropdown_right.png',
	 			"button_background_hover"	: '/media/gasdokter/images/dropdown_right.png',
				"text_value"				: 'items geselecteerd',
				"total_width"				: 290,
				"callback"					: function( val ){ },
				"verplicht"					: false,
				"marginLeft"				: 0
			},
			options = $.extend(defaults, options2),
			trim 	= function(value) 
				{
		  			value = value.replace(/^\s+/,'');
					value = value.replace(/\s+$/,'');
					return value;
				},
			format_li = function( type , $option , name )
				{
					var val		= $option.val() || "",
						text	= $option.attr('label') || $option.html() || "";
			
					if( $option.is( 'optgroup' ) )
					{
						return "<li class=\"optgroup show\"><span>" + text + "</span></li>";
					}
					else if( $option.is( 'option' ) )
					{
						var multiple = false,
							selected = $option.is( ':selected' );
						
						if( $option.val() !== "" )
						{
							if( type === "multiple" )
							{
								if( selected )
									return "<li class=\"choice show\" id=\"val_" + val + "\"><input type=\"checkbox\" name=\"" + name + "\" selected=\"selected\" value=\"" + val + "\" /><span>" + text + "</span></li>";
								else
									return "<li class=\"show\" id=\"val_" + val + "\"><input type=\"checkbox\" name=\"" + name + "\" value=\"" + val + "\" /><span>" + text + "</span></li>";
							}
							else
							{
								if( selected )
									return "<li class=\"choice show\" id=\"val_" + val + "\"><span>" + text + "</span></li>";
								else
									return "<li class=\"show\" id=\"val_" + val + "\"><span>" + text + "</span></li>";
							}
						}
						else
						{
							return "<li class=\"optgroup show\"><span>" + text + "</span></li>";
						}
					}
				},
			styles = {
				dropdown_box_container : 'width:' + options.total_width + 'px; margin-left:' + parseInt( options.marginLeft , 10 ) + 'px;',
				dropdown_box_list : 'min-width:' + (options.total_width - 10) + 'px; overflow-y: auto;',
				dropdown_box_value : 'width:' + ( options.total_width - 35 ) + 'px;',
				dropdown_box_button : 'background:url(\'' + options.button_background_hover + '\') center center no-repeat'
			};
		
		return this.each(function(){
			var search_value 	= '',
				id 				= Math.floor(Math.random() * 999999),
				$container		= $( '<span />' )
									.addClass( "dropdown_container"	)
									.insertAfter( $( this ) );
				//$label			= $( 'label[for=]' );
			
			if( options.select_list !== true )
				if( $( this ).is( 'select' ) )
					options.select_list = true;
			
			if($(this).is('.obl'))
				options.verplicht = true;
			
			if( options.select_list )
			{
				
				var $select 	= $( this ),
					sel_name	= $select.attr( 'name' ),
					sel_id		= $select.attr( 'id' ) || false;
				
				// Max select items instellen op het juiste aantal
				if( $select.attr('multiple') !== undefined && $select.attr('multiple') !== false )
				{
					if( options.max_select_items === 1 )
						options.max_select_items = 0;
				}
				else
					options.max_select_items = 1;
				
				$container
					.prepend('<div class="dropdown_box_container" style="' + styles.dropdown_box_container + '"><div class="dropdown_box_value" style="' + styles.dropdown_box_value + '"></div><div class="dropdown_box_button" style="' + styles.dropdown_box_button + '"></div></div><div class="dropdown_box_list" style="' + styles.dropdown_box_list + '"><ul></ul></div>');	
			
				if( options.max_select_items === 1 )
					$container
						.append( '<input type="hidden" ' + ( options.verplicht ? 'class="obl"' : '' ) + ' name="' + sel_name + '" value="" />' );
				else
					$( '.dropdown_box_list ul' , $container )
						.addClass( 'multiple' );
				
				if( options.filter_items )
					$( '.dropdown_box_value' ,  $container )
						.append( '<input type=\"text\" class=\"no_search\" style=\"width: ' + ( options.total_width - 35 ) + 'px;\" />' );
								
				var $ul = $( 'ul' , $container );
				
				if( sel_id !== false )
					$ul.attr( 'id' , sel_id );
				
				$select
					.children( 'option, optgroup' )
					.each(function()
						{
							if( $( this ).is( 'option' ) )
								$ul.append( 
									format_li( ( options.max_select_items !== 1 ? "multiple" : "single" ) , $( this ) , sel_name ) 
								);
							else
							{
								$ul.append( 
									format_li( ( options.max_select_items !== 1 ? "multiple" : "single" ) , $( this ) , sel_name ) 
								);
																
								$( this )
									.children( )
									.each(function()
										{
											$ul.append(
												format_li( ( options.max_select_items !== 1 ? "multiple" : "single" ) , $( this ) , sel_name )
											);
										}
									);
							}
						}
					);
			}
			
			if( options.max_select_items === 1 )
				$( 'input:hidden' , $container )
					.val( $( '.choice' , $ul ).attr('id').replace("val_","") );
			
			//Dit moet hier binnen de each omdat jquery nog geen focus ondersteund in live events
			if( options.filter_items )
				$( 'input' , $container )
					.bind( 'focus' , function()
						{
							if( $( this ).is( '.no_search' ) )
								$( this )
									.removeClass( 'no_search' )
									.val( '' );
							
							$( this )
								.trigger( 'click' );
						}
					)
					.bind( 'blur' , function()
						{
							if( $.trim( $( this ).val() ) === "" )
							{
								$( this )
									.addClass( 'no_search' );
								
								$container
									.trigger( 'change_value' );
							}
						}
					);
			
			//$container.trigger('dropdown.pos_list');
			
			$select.remove();
			
			$container
				.data( "dropdown" , options )
				.bind("dropdown_callback", function(e, val) { options.callback(val); })
				.trigger( 'change_value' );
			
			return this;
		});
	};
})(jQuery);
