﻿(function($) {
	$.fn.listnav = function(options) {
		var opts = $.extend({}, $.fn.listnav.defaults, options);
		var letters = ['A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'];
		return this.each(function(){
			var $wrapper, list, $list, $letters, $letterCount, id;
			id = this.id;
			$wrapper = $('#' + id + '-nav');
			$list = $(this);
			var counts, allCount, isAll, prevLetter;
			counts = [];
			allCount = 0;
			isAll = true;
			prevLetter = '';
			function init(){
				$wrapper.append( createLettersHtml() );
				$letters = $('.ln-letters', $wrapper).slice(0,1); // will always be a single item
				if (opts.showCounts) $letterCount = $('.ln-letterCount', $wrapper).slice(0,1);
				$('.z', $letters).addClass(opts.lastClass);
				addLIClasses();
				addNoMatchLI();
				storeLetterCounts();
				bindHandlers();
				if (! opts.includeAll) $list.show();
				if (! opts.includeAll) $('.all', $letters).hide();
				if (opts.initLetter != '') $('.' + opts.initLetter, $letters).slice(0,1).click();
				else {
					if (opts.includeAll) $('.all', $letters).addClass(opts.selectedClass);
					else { 
						for(var i=0;i<counts.length;i++){
							if (counts[i] > 0){
								$('.' + letters[i].toLowerCase(), $letters).slice(0,1).click();
								break;
							}
						}
					}
				}
			}
			function setLetterCountTop(){
				$letterCount.css({top: $('.a', $letters).slice(0,1).offset({margin:false, border:true}).top - $letterCount.outerHeight({margin:true})}); 
			}
			function addLIClasses(){
				var str;
				$('>li', $list).each(function(){
					str = $(this).text().replace(/\s+/g,'').toLowerCase();
					if (str != '') $(this).addClass( str.slice(0,1) ); 
				});
			}
			function storeLetterCounts(){
				var count = 0; var letter;
				for(var i=0;i<letters.length;i++){
					letter = letters[i].toLowerCase();
					count = $('>li.' + letter, $list).length;
					counts.push(count);
					allCount += count;
					if (opts.flagDisabled && (count == 0)) $('.' + letter, $letters).addClass(opts.disabledClass);
				}
			}
			function addNoMatchLI(){
				$list.append('<li class="noMatch" style="display:none">' + opts.noMatchText + '</li>');
			}
			function getLetterCount(el){
				return ( $(el).hasClass('all') ) ? allCount : counts[ $.inArray( $(el).attr('class').split(' ')[0].toUpperCase(), letters ) ]; 
			}
			function bindHandlers(){
				if (opts.showCounts){
					$wrapper.mouseover(function(){
						setLetterCountTop();
					});
				}
				if (opts.showCounts){
					$('a', $letters).mouseover(function(){
						var left = $(this).position().left;
						var width = ($(this).outerWidth({margin:true})-1) + 'px';
						var count = getLetterCount(this);
						$letterCount.css({left:left, width:width}).text( count ).show() ;
					});
					$('a', $letters).mouseout(function(){
						$letterCount.hide();
					});
				}
				$('a', $letters).click(function(){
					$('a.' + opts.selectedClass, $letters).removeClass(opts.selectedClass);

					var letter = $(this).attr('class').split(' ')[0];
					
					if(letter == 'all'){
						$('>li', $list).show();
						$('>li.noMatch', $list).hide();
						isAll = true;
					} else {
						if(isAll){
							$('>li', $list).hide();
							isAll = false;
						} else if (prevLetter != '') $('>li.' + prevLetter, $list).hide();
						
						var count = getLetterCount(this);
						if (count > 0) {
							$('>li.noMatch', $list).hide();
							$('>li.' + letter, $list).show();
						}
						else $('>li.noMatch', $list).show();
						
						prevLetter = letter;
					}
					
					$(this).addClass(opts.selectedClass);
					$(this).blur();
					return false;
				});
			}
			function createLettersHtml(){
				var html = [];
				for(var i=0;i<letters.length;i++){
					if (html.length == 0) html.push('<a class="all" href="#">ALL</a>');
					html.push('<a class="' + letters[i].toLowerCase() + '" href="#">' + letters[i] + '</a>');
				}
				return '<div class="ln-letters">' + html.join('') + '</div><div style="clear:both"></div>' + ((opts.showCounts) ? '<div class="ln-letterCount" style="display:none; position:absolute; top:0; left:0; width:20px;">0</div>' : '');
			}

			init();
		});
	};
	$.fn.listnav.defaults = {
		initLetter: '',
		includeAll: true,
		flagDisabled: true,
		noMatchText: 'No matching entries',
		lastClass: 'ln-last',
		selectedClass: 'ln-selected',
		disabledClass: 'ln-disabled',
		showCounts: true
	};
})(jQuery);

