(function($) {
	
	$.fn.extend({
		iScrollHorizontal: function(options) {
			var defaults = {
				children: "div",
				childWidth: null,
				onStart: null,
				onEnd: null,
				snapDuration: 400,
				allowMouse: false
			};
			
			var options = $.extend(defaults, options);
			
			var childWidth = options.childWidth;
			var childCount = 0;
			
			var context = $(this);
			
			context[0].ontouchstart = function(e) {
				if (e.touches.length != 1) { return; }
				var startOffset = getOffset(context);
				var startTouch = e.touches[0].pageX;
				
				var left = startOffset;
				context.stop().css("left", 0).css("-webkit-transform", "translateX(" + left + "px)");
				
				//Deferred loading
				if (childCount == 0) {
					
					childCount = $(this).children(options.children).length;
					//If there's still no children, just cancel the event
					if (childCount == 0) {
						return;
					}
					
					if (childWidth == null) {
						childWidth = $(this).children(options.children).first().width();
					}
				}
			
				
				if (typeof options.onStart == "function") {
					options.onStart();
				}
				
				
				context[0].ontouchmove = function(e) {
					if (e.touches.length != 1) {
						return;
					}
					left = startOffset + (e.touches[0].pageX - startTouch);
					context[0].style["-webkit-transform"] = "translateX(" + left + "px)";
					
					return false;
				};
				
				
				context[0].ontouchend = function(e) {
					
					var startIndex = Math.round(-startOffset / childWidth);
					var index = startIndex;
					if (Math.abs(startOffset - left) > (childWidth / 4)) {
						if (startOffset > left) {
							index += 1;
						} else if (startOffset < left) {
							index -= 1;
						}
					}
					
					if (index < 0) {
						index = 0;
					}
					
					if (index > childCount - 1) {
						index = childCount - 1;
					}
					
					target = -index * childWidth;
					
					context.css("-webkit-transform", "none").css("left", left)
						.animate({left: target}, options.snapDuration, function() {
							if (typeof options.onEnd == "function") {
								options.onEnd(index);
							}
						});
					
					
					context[0].ontouchmove = null;
					context[0].ontouchend = null;
					context[0].ontouchcancel = null;
					
					return false;
				};
				
				context[0].ontouchcancel = function(e) {
					context.stop().css("left", startOffset)
						.css("-webkit-transform", "none");
					
					context[0].ontouchmove = null;
					context[0].ontouchend = null;
					context[0].ontouchcancel = null;
				};
				
				return false;
			};	
			
			if (options.allowMouse) {
					context[0].onmousedown = function(e) {
					e.touches = [{pageX: e.pageX, pageY: e.pageY}];
					context[0].ontouchstart(e);
					
					context[0].onmousemove = function(e) {
						e.touches = [{pageX: e.pageX, pageY: e.pageY}];
						context[0].ontouchmove(e);
					};
					context[0].onmouseup = function(e) {
						e.touches = [{pageX: e.pageX, pageY: e.pageY}];
						context[0].ontouchend(e);
						context[0].onmousemove = null;
						context[0].onmouseup = null;
					};
				};
				
			}
		}
	});
	
	function getOffset(context) {
		var left = context.css("left").replace("px", "");
		if (left == "auto") {
			left = 0;
		}
		return parseInt(left);
	}
})(jQuery);

