(function($){
	$.fn.kwicks = function(options) {
		var defaults = {
			isVertical: false,
			sticky: false,
			defaultKwick: 0,
			event: 'mouseover',
			spacing: 0,
			duration: 500
		};
		var o = $.extend(defaults, options);
		var WoH = (o.isVertical ? 'height' : 'width'); // WoH = Width or Height
		var LoT = (o.isVertical ? 'top' : 'left'); // LoT = Left or Top

		return this.each(function() {
			var container = $(this);
			var kwicks = container.children('li');
			var normWoH = kwicks.eq(0).css(WoH).replace(/px/,''); // normWoH = Normal Width or Height
			if(!o.max) {
				o.max = (normWoH * kwicks.size()) - (o.min * (kwicks.size() - 1));
			} else {
				o.min = ((normWoH * kwicks.size()) - o.max) / (kwicks.size() - 1);
			}
			// set width of container ul
			if(o.isVertical) {
				container.css({
					width : kwicks.eq(0).css('width'),
					height : (normWoH * kwicks.size()) + (o.spacing * (kwicks.size() - 1)) + 'px'
				});
			} else {
				container.css({
					width : (normWoH * kwicks.size()) + (o.spacing * (kwicks.size() - 1)) + 'px',
					height : kwicks.eq(0).css('height')
				});
			}

			// pre calculate left or top values for all kwicks but the first and last
			// i = index of currently hovered kwick, j = index of kwick we're calculating
			var preCalcLoTs = []; // preCalcLoTs = pre-calculated Left or Top's
			for(i = 0; i < kwicks.size(); i++) {
				preCalcLoTs[i] = [];
				// don't need to calculate values for first or last kwick
				for(j = 0; j < kwicks.size(); j++) {
					if(i == j) {
						preCalcLoTs[i][j] = j * o.min + (j * o.spacing);
					} else {
						preCalcLoTs[i][j] = (j <= i ? (j * o.min) : (j-1) * o.min + o.max) + (j * o.spacing);
					}
				}
			}

			// loop through all kwick elements
			kwicks.each(function(i) {
				var kwick = $(this);
				// set initial width or height and left or top values
				// set first kwick
				if(i === 0) {
					kwick.css(LoT, '0px');
				}
				// set last kwick
/*				else if(i == kwicks.size() - 1) {
					kwick.css(o.isVertical ? 'bottom' : 'right', '0px');
				} */
				// set all other kwicks
				else {
					if(o.sticky) {
						kwick.css(LoT, preCalcLoTs[o.defaultKwick][i] + 9);
					} else {
						kwick.css(LoT, (i * normWoH) + (i * o.spacing));
					}
				}
				// correct size in sticky mode
				if(o.sticky) {
					if(o.defaultKwick == i) {
						kwick.css(WoH, o.max + 'px');
						kwick.addClass('active');

						$('.kwicks li.active h6').hide();
						$('.kwicks li.active').prepend($('li.active h6').
								removeClass('none').removeClass('head').clone().addClass('header').show());
						Cufon.replace('li.active h6.header');
					} else {
						kwick.css(WoH, o.min + 'px');
					}
				}
				kwick.css({
					margin: 0,
					position: 'absolute'
				});

				kwick.bind(o.event, function() {
					if ($(this).hasClass('active'))
						return false;


					var l = $('.kwicks li.active');

					// calculate previous width or heights and left or top values
					var prevWoHs = []; // prevWoHs = previous Widths or Heights
					var prevLoTs = []; // prevLoTs = previous Left or Tops
					kwicks.stop().removeClass('active');
					for(j = 0; j < kwicks.size(); j++) {
						prevWoHs[j] = kwicks.eq(j).css(WoH).replace(/px/, '') + 9;
						prevLoTs[j] = kwicks.eq(j).css(LoT).replace(/px/, '');
					}
					var aniObj = {};
					aniObj[WoH] = o.max;
					var maxDif = o.max - prevWoHs[i];
					var prevWoHsMaxDifRatio = prevWoHs[i]/maxDif;
					$('.kwicks').css('z-index', '0');
					$('#slide').css('z-index', '10001');
					$('h6.header', l).remove();
					$('p', l).hide();
					kwick.addClass('active').animate(aniObj, {
						step: function(now) {
							$('.kwicks li.active h6').hide();
							// calculate animation completeness as percentage
							var percentage = maxDif != 0 ? now/maxDif - prevWoHsMaxDifRatio : 1;
							// adjsut other elements based on percentage
							kwicks.each(function(j) {
								if(j != i) {
									kwicks.eq(j).css(WoH, prevWoHs[j] - ((prevWoHs[j] - o.min) * percentage) + 'px');
								}
								if(j > -1 && j < kwicks.size()) { // if not the first or last kwick
									var ss = parseInt(prevLoTs[j]) - 8 ;
									kwicks.eq(j).css(LoT, prevLoTs[j] - ((ss - preCalcLoTs[i][j]) * percentage) + 'px');
								}
							});



						},
						complete: function() {
							var t = $('.kwicks li.active').css('top').replace(/px/,'');
							var tt = parseInt(t) + 8;
							if ($('.kwicks li.active').hasClass('first'))
								tt = 0;
							$('#slide').animate(
								{ top: tt + 'px' },
								{
									duration: 100,
									complete: function()
									{
										$('#slide').css('z-index', '0');
									}
								}
							);
							$('.kwicks').css('z-index', '10001');

							$('.kwicks li.active').prepend($('li.active h6').clone().
									removeClass('none').removeClass('head').addClass('header').show());
							$('.kwicks li.active h6.head').addClass('none');
							$('.kwicks li.active p').fadeIn("fast");
							$('li[class != \'active\'] h6').removeClass('none').fadeIn("fast");
							Cufon.replace('li.active h6.header', { color: 'white' });

							$('.kwicks li').css('background', 'transparent');
							if (!$('.kwicks li.active').hasClass('first'))
							{
								$('h6.header').css('top', '30px');
							}
							else
							{
								$('h6.header').css('top', '16px');
								$('.kwicks li.active p').css('bottom', '60px');
							}

							if ($('.kwicks li.active').hasClass('last'))
							{
								$('.kwicks li.active').css('background', 'url(images/orange-bg.jpg) repeat-x bottom');
								$('.kwicks li.active').height($('.kwicks li.active').height() - 11);
								$('.kwicks li.active h6.head').hide();
							}

							if ($('.kwicks li.active').hasClass('first'))
							{
								$('.kwicks li.active h6').hide();
								$('.kwicks li.active h6.header').show();
							}


							$('.above-active').removeClass('above-active');
							$('.kwicks li.active').prev('li').addClass('above-active');

						},
						duration: o.duration,
						easing: o.easing
					});

				});
			});
		});
	};
})(jQuery);
