Pen Settings

HTML

CSS

CSS Base

Vendor Prefixing

Add External Stylesheets/Pens

Any URL's added here will be added as <link>s in order, and before the CSS in the editor. If you link to another Pen, it will include the CSS from that Pen. If the preprocessor matches, it will attempt to combine them before processing.

+ add another resource

JavaScript

Babel includes JSX processing.

Add External Scripts/Pens

Any URL's added here will be added as <script>s in order, and run before the JavaScript in the editor. You can use the URL of any other Pen and it will include the JavaScript from that Pen.

+ add another resource

Packages

Add Packages

Search for and use JavaScript packages from npm here. By selecting a package, an import statement will be added to the top of the JavaScript editor for this package.

Behavior

Save Automatically?

If active, Pens will autosave every 30 seconds after being saved once.

Auto-Updating Preview

If enabled, the preview panel updates automatically as you code. If disabled, use the "Run" button to update.

Format on Save

If enabled, your code will be formatted when you actively save your Pen. Note: your code becomes un-folded during formatting.

Editor Settings

Code Indentation

Want to change your Syntax Highlighting theme, Fonts and more?

Visit your global Editor Settings.

HTML

              
                <div id="carousel">
	<ul>
		<li class="menu">
			<nav>
				<a href="">Created</a>
				<a href="">Using</a>
				<a href="">The</a>
				<a href="">Amazing</a>
				<a href="https://hammerjs.github.io/" target="_blank">Hammer.js</a>
			</nav>
		</li>
		<li class="page">
			<a href="#" class="menu-icon"><span></span></a>
			<div class="flex">
				<div class="middle"><h1>Swipe to open menu :)</h1></div>
			</div>
			<a href="https://codepen.io/adam2326/full/QwQmEX/" target="_blank" class="another">Another hammer.js experiment.</a>
		</li>
	</ul>
</div>
              
            
!

CSS

              
                *{ margin: 0; padding: 0; box-sizing: border-box; }
@import url(https://fonts.googleapis.com/css?family=Roboto:400,100,100italic,300,300italic,400italic,500,500italic,700,700italic,900,900italic);

body{
	height: 100vh;
	font-family: 'Roboto', sans-serif;
	font-weight: 300;
}

.flex{ display: flex; width: 100%; }

.middle{ margin: auto; }

h1{
	padding: 0 10px;
	color: #fff;
	font-size: 42px;
	font-weight: 100;
	text-align: center;
}

#carousel {
  background: silver;
  overflow: hidden;
  width: 100%;
  -webkit-backface-visibility: hidden;
  -webkit-transform: translate3d(0,0,0) scale3d(1,1,1);
  -webkit-transform-style: preserve-3d;
}

#carousel ul.animate {
  transition: all .3s;
}

#carousel ul {
  -webkit-transform: translate3d(0%,0,0) scale3d(1,1,1);
  -moz-transform: translate3d(0%,0,0) scale3d(1,1,1);
  -ms-transform: translate3d(0%,0,0) scale3d(1,1,1);
  -o-transform: translate3d(0%,0,0) scale3d(1,1,1);
  transform: translate3d(0%,0,0) scale3d(1,1,1);
  overflow: hidden;
  -webkit-backface-visibility: hidden;
  -webkit-transform-style: preserve-3d;
}

#carousel ul {
	height: 100vh;
  -webkit-box-shadow: 0 0 20px rgba(0,0,0,.2);
  box-shadow: 0 0 20px rgba(0,0,0,.2);
  position: relative;
}

#carousel li {
	display: flex;
  float: left;
	width: 100%;
	height: 100vh;
  overflow: hidden;
  -webkit-transform-style: preserve-3d;
  -webkit-transform: translate3d(0,0,0);
}

#carousel li.menu{
	max-width: 15%;
	background-color: #2C3E50;
	nav{
		float: left;
		width: 100%;
		padding: 0 15px;
		a{
			float: left;
			width: 100%;
			padding: 10px 20px;
			border-bottom: 1px dotted #fff;
			color: #fff;
			text-decoration: none;
			position: relative;
			&:before{
				content: '';
				width: 6px;
				height: 6px;
				border: 1px solid #fff;
				border-radius: 100%;
				position: absolute;
				top: 16px; left: 8px;
			}
		}
	}
}

#carousel li.page{
	width: 100%;
	background-color: #34495E;
	position: relative;
	box-shadow: 5px 0px 36px 7px rgba(0,0,0,0.20);
}

a.menu-icon{
	width: 34px;
	height: 28px;
	position: absolute;
	top: 20px; left: 20px;
	span{
		width: 100%;
		height: 4px;
		margin: -2px 0 0 0;
		background-color: #fff;
		position: absolute;
		top: 50%; left: 0;
		&:before, &:after{
			content: '';
			width: 100%;
			height: 4px;
			background-color: #fff;
			position: absolute;
			left: 0;
		}
		&:before{
			top: -12px;
		}
		&:after{
			bottom: -12px;
		}
	}
}

a.another{
	padding: 3px 6px;
	background-color: #2C3E50;
	color: #fff;
	text-decoration: none;
	position: absolute;
	bottom: 5px; right: 5px;
}
              
            
!

JS

              
                /*! Hammer.JS - v1.0.10 - 2014-03-28
* https://eightmedia.github.io/hammer.js
*
* Copyright (c) 2014 Jorik Tangelder <j.tangelder@gmail.com>;
* Licensed under the MIT license */

(function(window, undefined) {
'use strict';

/**
* Hammer
* use this to create instances
* @param   {HTMLElement}   element
* @param   {Object}        options
* @returns {Hammer.Instance}
* @constructor
*/
var Hammer = function(element, options) {
return new Hammer.Instance(element, options || {});
};

Hammer.VERSION = '1.0.10';

// default settings
Hammer.defaults = {
// add styles and attributes to the element to prevent the browser from doing
// its native behavior. this doesnt prevent the scrolling, but cancels
// the contextmenu, tap highlighting etc
// set to false to disable this
stop_browser_behavior: {
	// this also triggers onselectstart=false for IE
	userSelect       : 'none',
	// this makes the element blocking in IE10>, you could experiment with the value
	// see for more options this issue; https://github.com/EightMedia/hammer.js/issues/241
	touchAction      : 'none',
	touchCallout     : 'none',
	contentZooming   : 'none',
	userDrag         : 'none',
	tapHighlightColor: 'rgba(0,0,0,0)'
}

//
// more settings are defined per gesture at /gestures
//
};


// detect touchevents
Hammer.HAS_POINTEREVENTS = window.navigator.pointerEnabled || window.navigator.msPointerEnabled;
Hammer.HAS_TOUCHEVENTS = ('ontouchstart' in window);

// dont use mouseevents on mobile devices
Hammer.MOBILE_REGEX = /mobile|tablet|ip(ad|hone|od)|android|silk/i;
Hammer.NO_MOUSEEVENTS = Hammer.HAS_TOUCHEVENTS && window.navigator.userAgent.match(Hammer.MOBILE_REGEX);

// eventtypes per touchevent (start, move, end)
// are filled by Event.determineEventTypes on setup
Hammer.EVENT_TYPES = {};

// interval in which Hammer recalculates current velocity in ms
Hammer.UPDATE_VELOCITY_INTERVAL = 16;

// hammer document where the base events are added at
Hammer.DOCUMENT = window.document;

// define these also as vars, for better minification
// direction defines
var DIRECTION_DOWN = Hammer.DIRECTION_DOWN = 'down';
var DIRECTION_LEFT = Hammer.DIRECTION_LEFT = 'left';
var DIRECTION_UP = Hammer.DIRECTION_UP = 'up';
var DIRECTION_RIGHT = Hammer.DIRECTION_RIGHT = 'right';

// pointer type
var POINTER_MOUSE = Hammer.POINTER_MOUSE = 'mouse';
var POINTER_TOUCH = Hammer.POINTER_TOUCH = 'touch';
var POINTER_PEN = Hammer.POINTER_PEN = 'pen';

// touch event defines
var EVENT_START = Hammer.EVENT_START = 'start';
var EVENT_MOVE = Hammer.EVENT_MOVE = 'move';
var EVENT_END = Hammer.EVENT_END = 'end';


// plugins and gestures namespaces
Hammer.plugins = Hammer.plugins || {};
Hammer.gestures = Hammer.gestures || {};


// if the window events are set...
Hammer.READY = false;


/**
* setup events to detect gestures on the document
*/
function setup() {
if(Hammer.READY) {
	return;
}

// find what eventtypes we add listeners to
Event.determineEventTypes();

// Register all gestures inside Hammer.gestures
Utils.each(Hammer.gestures, function(gesture){
	Detection.register(gesture);
});

// Add touch events on the document
Event.onTouch(Hammer.DOCUMENT, EVENT_MOVE, Detection.detect);
Event.onTouch(Hammer.DOCUMENT, EVENT_END, Detection.detect);

// Hammer is ready...!
Hammer.READY = true;
}

var Utils = Hammer.utils = {
/**
 * extend method,
 * also used for cloning when dest is an empty object
 * @param   {Object}    dest
 * @param   {Object}    src
 * @parm  {Boolean}  merge    do a merge
 * @returns {Object}    dest
 */
extend: function extend(dest, src, merge) {
	for(var key in src) {
		if(dest[key] !== undefined && merge) {
			continue;
		}
		dest[key] = src[key];
	}
	return dest;
},


/**
 * for each
 * @param obj
 * @param iterator
 */
each: function each(obj, iterator, context) {
	var i, o;
	// native forEach on arrays
	if ('forEach' in obj) {
		obj.forEach(iterator, context);
	}
	// arrays
	else if(obj.length !== undefined) {
		for(i=-1; (o=obj[++i]);) {
			if (iterator.call(context, o, i, obj) === false) {
				return;
			}
		}
	}
	// objects
	else {
		for(i in obj) {
			if(obj.hasOwnProperty(i) &&
					iterator.call(context, obj[i], i, obj) === false) {
				return;
			}
		}
	}
},


/**
 * find if a string contains the needle
 * @param   {String}  src
 * @param   {String}  needle
 * @returns {Boolean} found
 */
inStr: function inStr(src, needle) {
	return src.indexOf(needle) > -1;
},


/**
 * find if a node is in the given parent
 * used for event delegation tricks
 * @param   {HTMLElement}   node
 * @param   {HTMLElement}   parent
 * @returns {boolean}       has_parent
 */
hasParent: function hasParent(node, parent) {
	while(node) {
		if(node == parent) {
			return true;
		}
		node = node.parentNode;
	}
	return false;
},


/**
 * get the center of all the touches
 * @param   {Array}     touches
 * @returns {Object}    center pageXY clientXY
 */
getCenter: function getCenter(touches) {
	var pageX = []
		, pageY = []
		, clientX = []
		, clientY = []
		, min = Math.min
		, max = Math.max;

	// no need to loop when only one touch
	if(touches.length === 1) {
		return {
			pageX: touches[0].pageX,
			pageY: touches[0].pageY,
			clientX: touches[0].clientX,
			clientY: touches[0].clientY
		};
	}

	Utils.each(touches, function(touch) {
		pageX.push(touch.pageX);
		pageY.push(touch.pageY);
		clientX.push(touch.clientX);
		clientY.push(touch.clientY);
	});

	return {
		pageX: (min.apply(Math, pageX) + max.apply(Math, pageX)) / 2,
		pageY: (min.apply(Math, pageY) + max.apply(Math, pageY)) / 2,
		clientX: (min.apply(Math, clientX) + max.apply(Math, clientX)) / 2,
		clientY: (min.apply(Math, clientY) + max.apply(Math, clientY)) / 2
	};
},


/**
 * calculate the velocity between two points
 * @param   {Number}    delta_time
 * @param   {Number}    delta_x
 * @param   {Number}    delta_y
 * @returns {Object}    velocity
 */
getVelocity: function getVelocity(delta_time, delta_x, delta_y) {
	return {
		x: Math.abs(delta_x / delta_time) || 0,
		y: Math.abs(delta_y / delta_time) || 0
	};
},


/**
 * calculate the angle between two coordinates
 * @param   {Touch}     touch1
 * @param   {Touch}     touch2
 * @returns {Number}    angle
 */
getAngle: function getAngle(touch1, touch2) {
	var x = touch2.clientX - touch1.clientX
		, y = touch2.clientY - touch1.clientY;
	return Math.atan2(y, x) * 180 / Math.PI;
},


/**
 * angle to direction define
 * @param   {Touch}     touch1
 * @param   {Touch}     touch2
 * @returns {String}    direction constant, like DIRECTION_LEFT
 */
getDirection: function getDirection(touch1, touch2) {
	var x = Math.abs(touch1.clientX - touch2.clientX)
		, y = Math.abs(touch1.clientY - touch2.clientY);
	if(x >= y) {
		return touch1.clientX - touch2.clientX > 0 ? DIRECTION_LEFT : DIRECTION_RIGHT;
	}
	return touch1.clientY - touch2.clientY > 0 ? DIRECTION_UP : DIRECTION_DOWN;
},


/**
 * calculate the distance between two touches
 * @param   {Touch}     touch1
 * @param   {Touch}     touch2
 * @returns {Number}    distance
 */
getDistance: function getDistance(touch1, touch2) {
	var x = touch2.clientX - touch1.clientX
		, y = touch2.clientY - touch1.clientY;
	return Math.sqrt((x * x) + (y * y));
},


/**
 * calculate the scale factor between two touchLists (fingers)
 * no scale is 1, and goes down to 0 when pinched together, and bigger when pinched out
 * @param   {Array}     start
 * @param   {Array}     end
 * @returns {Number}    scale
 */
getScale: function getScale(start, end) {
	// need two fingers...
	if(start.length >= 2 && end.length >= 2) {
		return this.getDistance(end[0], end[1]) / this.getDistance(start[0], start[1]);
	}
	return 1;
},


/**
 * calculate the rotation degrees between two touchLists (fingers)
 * @param   {Array}     start
 * @param   {Array}     end
 * @returns {Number}    rotation
 */
getRotation: function getRotation(start, end) {
	// need two fingers
	if(start.length >= 2 && end.length >= 2) {
		return this.getAngle(end[1], end[0]) - this.getAngle(start[1], start[0]);
	}
	return 0;
},


/**
 * boolean if the direction is vertical
 * @param    {String}    direction
 * @returns  {Boolean}   is_vertical
 */
isVertical: function isVertical(direction) {
	return direction == DIRECTION_UP || direction == DIRECTION_DOWN;
},


/**
 * toggle browser default behavior with css props
 * @param   {HtmlElement}   element
 * @param   {Object}        css_props
 * @param   {Boolean}       toggle
 */
toggleDefaultBehavior: function toggleDefaultBehavior(element, css_props, toggle) {
	if(!css_props || !element || !element.style) {
		return;
	}

	// with css properties for modern browsers
	Utils.each(['webkit', 'moz', 'Moz', 'ms', 'o', ''], function setStyle(vendor) {
		Utils.each(css_props, function(value, prop) {
				// vender prefix at the property
				if(vendor) {
					prop = vendor + prop.substring(0, 1).toUpperCase() + prop.substring(1);
				}
				// set the style
				if(prop in element.style) {
					element.style[prop] = !toggle && value;
				}
		});
	});

	var false_fn = function(){ return false; };

	// also the disable onselectstart
	if(css_props.userSelect == 'none') {
		element.onselectstart = !toggle && false_fn;
	}
	// and disable ondragstart
	if(css_props.userDrag == 'none') {
		element.ondragstart = !toggle && false_fn;
	}
}
};


/**
* create new hammer instance
* all methods should return the instance itself, so it is chainable.
* @param   {HTMLElement}       element
* @param   {Object}            [options={}]
* @returns {Hammer.Instance}
* @constructor
*/
Hammer.Instance = function(element, options) {
var self = this;

// setup HammerJS window events and register all gestures
// this also sets up the default options
setup();

this.element = element;

// start/stop detection option
this.enabled = true;

// merge options
this.options = Utils.extend(
	Utils.extend({}, Hammer.defaults),
	options || {});

// add some css to the element to prevent the browser from doing its native behavoir
if(this.options.stop_browser_behavior) {
	Utils.toggleDefaultBehavior(this.element, this.options.stop_browser_behavior, false);
}

// start detection on touchstart
this.eventStartHandler = Event.onTouch(element, EVENT_START, function(ev) {
	if(self.enabled) {
		Detection.startDetect(self, ev);
	}
});

// keep a list of user event handlers which needs to be removed when calling 'dispose'
this.eventHandlers = [];

// return instance
return this;
};


Hammer.Instance.prototype = {
/**
 * bind events to the instance
 * @param   {String}      gesture
 * @param   {Function}    handler
 * @returns {Hammer.Instance}
 */
on: function onEvent(gesture, handler) {
	var gestures = gesture.split(' ');
	Utils.each(gestures, function(gesture) {
		this.element.addEventListener(gesture, handler, false);
		this.eventHandlers.push({ gesture: gesture, handler: handler });
	}, this);
	return this;
},


/**
 * unbind events to the instance
 * @param   {String}      gesture
 * @param   {Function}    handler
 * @returns {Hammer.Instance}
 */
off: function offEvent(gesture, handler) {
	var gestures = gesture.split(' ')
		, i, eh;
	Utils.each(gestures, function(gesture) {
		this.element.removeEventListener(gesture, handler, false);

		// remove the event handler from the internal list
		for(i=-1; (eh=this.eventHandlers[++i]);) {
			if(eh.gesture === gesture && eh.handler === handler) {
				this.eventHandlers.splice(i, 1);
			}
		}
	}, this);
	return this;
},


/**
 * trigger gesture event
 * @param   {String}      gesture
 * @param   {Object}      [eventData]
 * @returns {Hammer.Instance}
 */
trigger: function triggerEvent(gesture, eventData) {
	// optional
	if(!eventData) {
		eventData = {};
	}

	// create DOM event
	var event = Hammer.DOCUMENT.createEvent('Event');
	event.initEvent(gesture, true, true);
	event.gesture = eventData;

	// trigger on the target if it is in the instance element,
	// this is for event delegation tricks
	var element = this.element;
	if(Utils.hasParent(eventData.target, element)) {
		element = eventData.target;
	}

	element.dispatchEvent(event);
	return this;
},


/**
 * enable of disable hammer.js detection
 * @param   {Boolean}   state
 * @returns {Hammer.Instance}
 */
enable: function enable(state) {
	this.enabled = state;
	return this;
},


/**
 * dispose this hammer instance
 * @returns {Hammer.Instance}
 */
dispose: function dispose() {
	var i, eh;

	// undo all changes made by stop_browser_behavior
	if(this.options.stop_browser_behavior) {
		Utils.toggleDefaultBehavior(this.element, this.options.stop_browser_behavior, true);
	}

	// unbind all custom event handlers
	for(i=-1; (eh=this.eventHandlers[++i]);) {
		this.element.removeEventListener(eh.gesture, eh.handler, false);
	}
	this.eventHandlers = [];

	// unbind the start event listener
	Event.unbindDom(this.element, Hammer.EVENT_TYPES[EVENT_START], this.eventStartHandler);

	return null;
}
};


/**
* this holds the last move event,
* used to fix empty touchend issue
* see the onTouch event for an explanation
* @type {Object}
*/
var last_move_event = null;

/**
* when the mouse is hold down, this is true
* @type {Boolean}
*/
var should_detect = false;

/**
* when touch events have been fired, this is true
* @type {Boolean}
*/
var touch_triggered = false;


var Event = Hammer.event = {
/**
 * simple addEventListener
 * @param   {HTMLElement}   element
 * @param   {String}        type
 * @param   {Function}      handler
 */
bindDom: function(element, type, handler) {
	var types = type.split(' ');
	Utils.each(types, function(type){
		element.addEventListener(type, handler, false);
	});
},


/**
 * simple removeEventListener
 * @param   {HTMLElement}   element
 * @param   {String}        type
 * @param   {Function}      handler
 */
unbindDom: function(element, type, handler) {
	var types = type.split(' ');
	Utils.each(types, function(type){
		element.removeEventListener(type, handler, false);
	});
},


/**
 * touch events with mouse fallback
 * @param   {HTMLElement}   element
 * @param   {String}        eventType        like EVENT_MOVE
 * @param   {Function}      handler
 */
onTouch: function onTouch(element, eventType, handler) {
	var self = this;


	var bindDomOnTouch = function bindDomOnTouch(ev) {
		var srcEventType = ev.type.toLowerCase();

		// onmouseup, but when touchend has been fired we do nothing.
		// this is for touchdevices which also fire a mouseup on touchend
		if(Utils.inStr(srcEventType, 'mouse') && touch_triggered) {
			return;
		}

		// mousebutton must be down or a touch event
		else if(Utils.inStr(srcEventType, 'touch') ||   // touch events are always on screen
			Utils.inStr(srcEventType, 'pointerdown') || // pointerevents touch
			(Utils.inStr(srcEventType, 'mouse') && ev.which === 1)   // mouse is pressed
			) {
			should_detect = true;
		}

		// mouse isn't pressed
		else if(Utils.inStr(srcEventType, 'mouse') && !ev.which) {
			should_detect = false;
		}


		// we are in a touch event, set the touch triggered bool to true,
		// this for the conflicts that may occur on ios and android
		if(Utils.inStr(srcEventType, 'touch') || Utils.inStr(srcEventType, 'pointer')) {
			touch_triggered = true;
		}

		// count the total touches on the screen
		var count_touches = 0;

		// when touch has been triggered in this detection session
		// and we are now handling a mouse event, we stop that to prevent conflicts
		if(should_detect) {
			// update pointerevent
			if(Hammer.HAS_POINTEREVENTS && eventType != EVENT_END) {
				count_touches = PointerEvent.updatePointer(eventType, ev);
			}
			// touch
			else if(Utils.inStr(srcEventType, 'touch')) {
				count_touches = ev.touches.length;
			}
			// mouse
			else if(!touch_triggered) {
				count_touches = Utils.inStr(srcEventType, 'up') ? 0 : 1;
			}


			// if we are in a end event, but when we remove one touch and
			// we still have enough, set eventType to move
			if(count_touches > 0 && eventType == EVENT_END) {
				eventType = EVENT_MOVE;
			}
			// no touches, force the end event
			else if(!count_touches) {
				eventType = EVENT_END;
			}

			// store the last move event
			if(count_touches || last_move_event === null) {
				last_move_event = ev;
			}


			// trigger the handler
			handler.call(Detection, self.collectEventData(element, eventType,
																self.getTouchList(last_move_event, eventType),
																ev) );

			// remove pointerevent from list
			if(Hammer.HAS_POINTEREVENTS && eventType == EVENT_END) {
				count_touches = PointerEvent.updatePointer(eventType, ev);
			}
		}

		// on the end we reset everything
		if(!count_touches) {
			last_move_event = null;
			should_detect = false;
			touch_triggered = false;
			PointerEvent.reset();
		}
	};

	this.bindDom(element, Hammer.EVENT_TYPES[eventType], bindDomOnTouch);

	// return the bound function to be able to unbind it later
	return bindDomOnTouch;
},


/**
 * we have different events for each device/browser
 * determine what we need and set them in the Hammer.EVENT_TYPES constant
 */
determineEventTypes: function determineEventTypes() {
	// determine the eventtype we want to set
	var types;

	// pointerEvents magic
	if(Hammer.HAS_POINTEREVENTS) {
		types = PointerEvent.getEvents();
	}
	// on Android, iOS, blackberry, windows mobile we dont want any mouseevents
	else if(Hammer.NO_MOUSEEVENTS) {
		types = [
			'touchstart',
			'touchmove',
			'touchend touchcancel'];
	}
	// for non pointer events browsers and mixed browsers,
	// like chrome on windows8 touch laptop
	else {
		types = [
			'touchstart mousedown',
			'touchmove mousemove',
			'touchend touchcancel mouseup'];
	}

	Hammer.EVENT_TYPES[EVENT_START] = types[0];
	Hammer.EVENT_TYPES[EVENT_MOVE] = types[1];
	Hammer.EVENT_TYPES[EVENT_END] = types[2];
},


/**
 * create touchlist depending on the event
 * @param   {Object}    ev
 * @param   {String}    eventType   used by the fakemultitouch plugin
 */
getTouchList: function getTouchList(ev/*, eventType*/) {
	// get the fake pointerEvent touchlist
	if(Hammer.HAS_POINTEREVENTS) {
		return PointerEvent.getTouchList();
	}

	// get the touchlist
	if(ev.touches) {
		return ev.touches;
	}

	// make fake touchlist from mouse position
	ev.identifier = 1;
	return [ev];
},


/**
 * collect event data for Hammer js
 * @param   {HTMLElement}   element
 * @param   {String}        eventType        like EVENT_MOVE
 * @param   {Object}        eventData
 */
collectEventData: function collectEventData(element, eventType, touches, ev) {
	// find out pointerType
	var pointerType = POINTER_TOUCH;
	if(Utils.inStr(ev.type, 'mouse') || PointerEvent.matchType(POINTER_MOUSE, ev)) {
		pointerType = POINTER_MOUSE;
	}

	return {
		center     : Utils.getCenter(touches),
		timeStamp  : Date.now(),
		target     : ev.target,
		touches    : touches,
		eventType  : eventType,
		pointerType: pointerType,
		srcEvent   : ev,

		/**
		 * prevent the browser default actions
		 * mostly used to disable scrolling of the browser
		 */
		preventDefault: function() {
			var srcEvent = this.srcEvent;
			srcEvent.preventManipulation && srcEvent.preventManipulation();
			srcEvent.preventDefault && srcEvent.preventDefault();
		},

		/**
		 * stop bubbling the event up to its parents
		 */
		stopPropagation: function() {
			this.srcEvent.stopPropagation();
		},

		/**
		 * immediately stop gesture detection
		 * might be useful after a swipe was detected
		 * @return {*}
		 */
		stopDetect: function() {
			return Detection.stopDetect();
		}
	};
}
};

var PointerEvent = Hammer.PointerEvent = {
/**
 * holds all pointers
 * @type {Object}
 */
pointers: {},

/**
 * get a list of pointers
 * @returns {Array}     touchlist
 */
getTouchList: function getTouchList() {
	var touchlist = [];
	// we can use forEach since pointerEvents only is in IE10
	Utils.each(this.pointers, function(pointer){
		touchlist.push(pointer);
	});

	return touchlist;
},

/**
 * update the position of a pointer
 * @param   {String}   type             EVENT_END
 * @param   {Object}   pointerEvent
 */
updatePointer: function updatePointer(type, pointerEvent) {
	if(type == EVENT_END) {
		delete this.pointers[pointerEvent.pointerId];
	}
	else {
		pointerEvent.identifier = pointerEvent.pointerId;
		this.pointers[pointerEvent.pointerId] = pointerEvent;
	}

	// it's save to use Object.keys, since pointerEvents are only in newer browsers
	return Object.keys(this.pointers).length;
},

/**
 * check if ev matches pointertype
 * @param   {String}        pointerType     POINTER_MOUSE
 * @param   {PointerEvent}  ev
 */
matchType: function matchType(pointerType, ev) {
	if(!ev.pointerType) {
		return false;
	}

	var pt = ev.pointerType
		, types = {};

	types[POINTER_MOUSE] = (pt === POINTER_MOUSE);
	types[POINTER_TOUCH] = (pt === POINTER_TOUCH);
	types[POINTER_PEN] = (pt === POINTER_PEN);
	return types[pointerType];
},


/**
 * get events
 */
getEvents: function getEvents() {
	return [
		'pointerdown MSPointerDown',
		'pointermove MSPointerMove',
		'pointerup pointercancel MSPointerUp MSPointerCancel'
	];
},

/**
 * reset the list
 */
reset: function resetList() {
	this.pointers = {};
}
};


var Detection = Hammer.detection = {
// contains all registred Hammer.gestures in the correct order
gestures: [],

// data of the current Hammer.gesture detection session
current : null,

// the previous Hammer.gesture session data
// is a full clone of the previous gesture.current object
previous: null,

// when this becomes true, no gestures are fired
stopped : false,


/**
 * start Hammer.gesture detection
 * @param   {Hammer.Instance}   inst
 * @param   {Object}            eventData
 */
startDetect: function startDetect(inst, eventData) {
	// already busy with a Hammer.gesture detection on an element
	if(this.current) {
		return;
	}

	this.stopped = false;

	// holds current session
	this.current = {
		inst              : inst, // reference to HammerInstance we're working for
		startEvent        : Utils.extend({}, eventData), // start eventData for distances, timing etc
		lastEvent         : false, // last eventData
		lastVelocityEvent : false, // last eventData for velocity.
		velocity          : false, // current velocity
		name              : '' // current gesture we're in/detected, can be 'tap', 'hold' etc
	};

	this.detect(eventData);
},


/**
 * Hammer.gesture detection
 * @param   {Object}    eventData
 */
detect: function detect(eventData) {
	if(!this.current || this.stopped) {
		return;
	}

	// extend event data with calculations about scale, distance etc
	eventData = this.extendEventData(eventData);

	// hammer instance and instance options
	var inst = this.current.inst,
			inst_options = inst.options;

	// call Hammer.gesture handlers
	Utils.each(this.gestures, function triggerGesture(gesture) {
		// only when the instance options have enabled this gesture
		if(!this.stopped && inst_options[gesture.name] !== false && inst.enabled !== false ) {
			// if a handler returns false, we stop with the detection
			if(gesture.handler.call(gesture, eventData, inst) === false) {
				this.stopDetect();
				return false;
			}
		}
	}, this);

	// store as previous event event
	if(this.current) {
		this.current.lastEvent = eventData;
	}

	// end event, but not the last touch, so dont stop
	if(eventData.eventType == EVENT_END && !eventData.touches.length - 1) {
		this.stopDetect();
	}

	return eventData;
},


/**
 * clear the Hammer.gesture vars
 * this is called on endDetect, but can also be used when a final Hammer.gesture has been detected
 * to stop other Hammer.gestures from being fired
 */
stopDetect: function stopDetect() {
	// clone current data to the store as the previous gesture
	// used for the double tap gesture, since this is an other gesture detect session
	this.previous = Utils.extend({}, this.current);

	// reset the current
	this.current = null;

	// stopped!
	this.stopped = true;
},


/**
 * calculate velocity
 * @param   {Object}  ev
 * @param   {Number}  delta_time
 * @param   {Number}  delta_x
 * @param   {Number}  delta_y
 */
getVelocityData: function getVelocityData(ev, delta_time, delta_x, delta_y) {
	var cur = this.current
		, velocityEv = cur.lastVelocityEvent
		, velocity = cur.velocity;

	// calculate velocity every x ms
	if (velocityEv && ev.timeStamp - velocityEv.timeStamp > Hammer.UPDATE_VELOCITY_INTERVAL) {
		velocity = Utils.getVelocity(ev.timeStamp - velocityEv.timeStamp,
																 ev.center.clientX - velocityEv.center.clientX,
																ev.center.clientY - velocityEv.center.clientY);
		cur.lastVelocityEvent = ev;
	}
	else if(!cur.velocity) {
		velocity = Utils.getVelocity(delta_time, delta_x, delta_y);
		cur.lastVelocityEvent = ev;
	}

	cur.velocity = velocity;

	ev.velocityX = velocity.x;
	ev.velocityY = velocity.y;
},


/**
 * calculate interim angle and direction
 * @param   {Object}  ev
 */
getInterimData: function getInterimData(ev) {
	var lastEvent = this.current.lastEvent
		, angle
		, direction;

	// end events (e.g. dragend) don't have useful values for interimDirection & interimAngle
	// because the previous event has exactly the same coordinates
	// so for end events, take the previous values of interimDirection & interimAngle
	// instead of recalculating them and getting a spurious '0'
	if(ev.eventType == EVENT_END) {
		angle = lastEvent && lastEvent.interimAngle;
		direction = lastEvent && lastEvent.interimDirection;
	}
	else {
		angle = lastEvent && Utils.getAngle(lastEvent.center, ev.center);
		direction = lastEvent && Utils.getDirection(lastEvent.center, ev.center);
	}

	ev.interimAngle = angle;
	ev.interimDirection = direction;
},


/**
 * extend eventData for Hammer.gestures
 * @param   {Object}   evData
 * @returns {Object}   evData
 */
extendEventData: function extendEventData(ev) {
	var cur = this.current
		, startEv = cur.startEvent;

	// if the touches change, set the new touches over the startEvent touches
	// this because touchevents don't have all the touches on touchstart, or the
	// user must place his fingers at the EXACT same time on the screen, which is not realistic
	// but, sometimes it happens that both fingers are touching at the EXACT same time
	if(ev.touches.length != startEv.touches.length || ev.touches === startEv.touches) {
		// extend 1 level deep to get the touchlist with the touch objects
		startEv.touches = [];
		Utils.each(ev.touches, function(touch) {
			startEv.touches.push(Utils.extend({}, touch));
		});
	}

	var delta_time = ev.timeStamp - startEv.timeStamp
		, delta_x = ev.center.clientX - startEv.center.clientX
		, delta_y = ev.center.clientY - startEv.center.clientY;

	this.getVelocityData(ev, delta_time, delta_x, delta_y);
	this.getInterimData(ev);

	Utils.extend(ev, {
		startEvent: startEv,

		deltaTime : delta_time,
		deltaX    : delta_x,
		deltaY    : delta_y,

		distance  : Utils.getDistance(startEv.center, ev.center),
		angle     : Utils.getAngle(startEv.center, ev.center),
		direction : Utils.getDirection(startEv.center, ev.center),

		scale     : Utils.getScale(startEv.touches, ev.touches),
		rotation  : Utils.getRotation(startEv.touches, ev.touches)
	});

	return ev;
},


/**
 * register new gesture
 * @param   {Object}    gesture object, see gestures.js for documentation
 * @returns {Array}     gestures
 */
register: function register(gesture) {
	// add an enable gesture options if there is no given
	var options = gesture.defaults || {};
	if(options[gesture.name] === undefined) {
		options[gesture.name] = true;
	}

	// extend Hammer default options with the Hammer.gesture options
	Utils.extend(Hammer.defaults, options, true);

	// set its index
	gesture.index = gesture.index || 1000;

	// add Hammer.gesture to the list
	this.gestures.push(gesture);

	// sort the list by index
	this.gestures.sort(function(a, b) {
		if(a.index < b.index) { return -1; }
		if(a.index > b.index) { return 1; }
		return 0;
	});

	return this.gestures;
}
};


/**
* Drag
* Move with x fingers (default 1) around on the page. Blocking the scrolling when
* moving left and right is a good practice. When all the drag events are blocking
* you disable scrolling on that area.
* @events  drag, drapleft, dragright, dragup, dragdown
*/
Hammer.gestures.Drag = {
name     : 'drag',
index    : 50,
defaults : {
	drag_min_distance            : 10,

	// Set correct_for_drag_min_distance to true to make the starting point of the drag
	// be calculated from where the drag was triggered, not from where the touch started.
	// Useful to avoid a jerk-starting drag, which can make fine-adjustments
	// through dragging difficult, and be visually unappealing.
	correct_for_drag_min_distance: true,

	// set 0 for unlimited, but this can conflict with transform
	drag_max_touches             : 1,

	// prevent default browser behavior when dragging occurs
	// be careful with it, it makes the element a blocking element
	// when you are using the drag gesture, it is a good practice to set this true
	drag_block_horizontal        : false,
	drag_block_vertical          : false,

	// drag_lock_to_axis keeps the drag gesture on the axis that it started on,
	// It disallows vertical directions if the initial direction was horizontal, and vice versa.
	drag_lock_to_axis            : false,

	// drag lock only kicks in when distance > drag_lock_min_distance
	// This way, locking occurs only when the distance has become large enough to reliably determine the direction
	drag_lock_min_distance       : 25
},

triggered: false,
handler  : function dragGesture(ev, inst) {
	var cur = Detection.current;

	// current gesture isnt drag, but dragged is true
	// this means an other gesture is busy. now call dragend
	if(cur.name != this.name && this.triggered) {
		inst.trigger(this.name + 'end', ev);
		this.triggered = false;
		return;
	}

	// max touches
	if(inst.options.drag_max_touches > 0 &&
		ev.touches.length > inst.options.drag_max_touches) {
		return;
	}

	switch(ev.eventType) {
		case EVENT_START:
			this.triggered = false;
			break;

		case EVENT_MOVE:
			// when the distance we moved is too small we skip this gesture
			// or we can be already in dragging
			if(ev.distance < inst.options.drag_min_distance &&
				cur.name != this.name) {
				return;
			}

			var startCenter = cur.startEvent.center;

			// we are dragging!
			if(cur.name != this.name) {
				cur.name = this.name;
				if(inst.options.correct_for_drag_min_distance && ev.distance > 0) {
					// When a drag is triggered, set the event center to drag_min_distance pixels from the original event center.
					// Without this correction, the dragged distance would jumpstart at drag_min_distance pixels instead of at 0.
					// It might be useful to save the original start point somewhere
					var factor = Math.abs(inst.options.drag_min_distance / ev.distance);
					startCenter.pageX += ev.deltaX * factor;
					startCenter.pageY += ev.deltaY * factor;
					startCenter.clientX += ev.deltaX * factor;
					startCenter.clientY += ev.deltaY * factor;

					// recalculate event data using new start point
					ev = Detection.extendEventData(ev);
				}
			}

			// lock drag to axis?
			if(cur.lastEvent.drag_locked_to_axis ||
					( inst.options.drag_lock_to_axis &&
						inst.options.drag_lock_min_distance <= ev.distance
					)) {
				ev.drag_locked_to_axis = true;
			}
			var last_direction = cur.lastEvent.direction;
			if(ev.drag_locked_to_axis && last_direction !== ev.direction) {
				// keep direction on the axis that the drag gesture started on
				if(Utils.isVertical(last_direction)) {
					ev.direction = (ev.deltaY < 0) ? DIRECTION_UP : DIRECTION_DOWN;
				}
				else {
					ev.direction = (ev.deltaX < 0) ? DIRECTION_LEFT : DIRECTION_RIGHT;
				}
			}

			// first time, trigger dragstart event
			if(!this.triggered) {
				inst.trigger(this.name + 'start', ev);
				this.triggered = true;
			}

			// trigger events
			inst.trigger(this.name, ev);
			inst.trigger(this.name + ev.direction, ev);

			var is_vertical = Utils.isVertical(ev.direction);

			// block the browser events
			if((inst.options.drag_block_vertical && is_vertical) ||
				(inst.options.drag_block_horizontal && !is_vertical)) {
				ev.preventDefault();
			}
			break;

		case EVENT_END:
			// trigger dragend
			if(this.triggered) {
				inst.trigger(this.name + 'end', ev);
			}

			this.triggered = false;
			break;
	}
}
};

/**
* Hold
* Touch stays at the same place for x time
* @events  hold
*/
Hammer.gestures.Hold = {
name    : 'hold',
index   : 10,
defaults: {
	hold_timeout  : 500,
	hold_threshold: 2
},
timer   : null,

handler : function holdGesture(ev, inst) {
	switch(ev.eventType) {
		case EVENT_START:
			// clear any running timers
			clearTimeout(this.timer);

			// set the gesture so we can check in the timeout if it still is
			Detection.current.name = this.name;

			// set timer and if after the timeout it still is hold,
			// we trigger the hold event
			this.timer = setTimeout(function() {
				if(Detection.current.name == 'hold') {
					inst.trigger('hold', ev);
				}
			}, inst.options.hold_timeout);
			break;

		// when you move or end we clear the timer
		case EVENT_MOVE:
			if(ev.distance > inst.options.hold_threshold) {
				clearTimeout(this.timer);
			}
			break;

		case EVENT_END:
			clearTimeout(this.timer);
			break;
	}
}
};

/**
* Release
* Called as last, tells the user has released the screen
* @events  release
*/
Hammer.gestures.Release = {
name   : 'release',
index  : Infinity,
handler: function releaseGesture(ev, inst) {
	if(ev.eventType == EVENT_END) {
		inst.trigger(this.name, ev);
	}
}
};

/**
* Swipe
* triggers swipe events when the end velocity is above the threshold
* for best usage, set prevent_default (on the drag gesture) to true
* @events  swipe, swipeleft, swiperight, swipeup, swipedown
*/
Hammer.gestures.Swipe = {
name    : 'swipe',
index   : 40,
defaults: {
	swipe_min_touches: 1,
	swipe_max_touches: 1,
	swipe_velocity   : 0.7
},
handler : function swipeGesture(ev, inst) {
	if(ev.eventType == EVENT_END) {
		// max touches
		if(ev.touches.length < inst.options.swipe_min_touches ||
			ev.touches.length > inst.options.swipe_max_touches) {
			return;
		}

		// when the distance we moved is too small we skip this gesture
		// or we can be already in dragging
		if(ev.velocityX > inst.options.swipe_velocity ||
			ev.velocityY > inst.options.swipe_velocity) {
			// trigger swipe events
			inst.trigger(this.name, ev);
			inst.trigger(this.name + ev.direction, ev);
		}
	}
}
};

/**
* Tap/DoubleTap
* Quick touch at a place or double at the same place
* @events  tap, doubletap
*/
Hammer.gestures.Tap = {
name    : 'tap',
index   : 100,
defaults: {
	tap_max_touchtime : 250,
	tap_max_distance  : 10,
	tap_always        : true,
	doubletap_distance: 20,
	doubletap_interval: 300
},

has_moved: false,

handler : function tapGesture(ev, inst) {
	var prev, since_prev, did_doubletap;

	// reset moved state
	if(ev.eventType == EVENT_START) {
		this.has_moved = false;
	}

	// Track the distance we've moved. If it's above the max ONCE, remember that (fixes #406).
	else if(ev.eventType == EVENT_MOVE && !this.moved) {
		this.has_moved = (ev.distance > inst.options.tap_max_distance);
	}

	else if(ev.eventType == EVENT_END &&
			ev.srcEvent.type != 'touchcancel' &&
			ev.deltaTime < inst.options.tap_max_touchtime && !this.has_moved) {

		// previous gesture, for the double tap since these are two different gesture detections
		prev = Detection.previous;
		since_prev = prev && prev.lastEvent && ev.timeStamp - prev.lastEvent.timeStamp;
		did_doubletap = false;

		// check if double tap
		if(prev && prev.name == 'tap' &&
				(since_prev && since_prev < inst.options.doubletap_interval) &&
				ev.distance < inst.options.doubletap_distance) {
			inst.trigger('doubletap', ev);
			did_doubletap = true;
		}

		// do a single tap
		if(!did_doubletap || inst.options.tap_always) {
			Detection.current.name = 'tap';
			inst.trigger(Detection.current.name, ev);
		}
	}
}
};

/**
* Touch
* Called as first, tells the user has touched the screen
* @events  touch
*/
Hammer.gestures.Touch = {
name    : 'touch',
index   : -Infinity,
defaults: {
	// call preventDefault at touchstart, and makes the element blocking by
	// disabling the scrolling of the page, but it improves gestures like
	// transforming and dragging.
	// be careful with using this, it can be very annoying for users to be stuck
	// on the page
	prevent_default    : false,

	// disable mouse events, so only touch (or pen!) input triggers events
	prevent_mouseevents: false
},
handler : function touchGesture(ev, inst) {
	if(inst.options.prevent_mouseevents &&
			ev.pointerType == POINTER_MOUSE) {
		ev.stopDetect();
		return;
	}

	if(inst.options.prevent_default) {
		ev.preventDefault();
	}

	if(ev.eventType == EVENT_START) {
		inst.trigger(this.name, ev);
	}
}
};


/**
* Transform
* User want to scale or rotate with 2 fingers
* @events  transform, pinch, pinchin, pinchout, rotate
*/
Hammer.gestures.Transform = {
name     : 'transform',
index    : 45,
defaults : {
	// factor, no scale is 1, zoomin is to 0 and zoomout until higher then 1
	transform_min_scale      : 0.01,
	// rotation in degrees
	transform_min_rotation   : 1,
	// prevent default browser behavior when two touches are on the screen
	// but it makes the element a blocking element
	// when you are using the transform gesture, it is a good practice to set this true
	transform_always_block   : false,
	// ensures that all touches occurred within the instance element
	transform_within_instance: false
},

triggered: false,

handler  : function transformGesture(ev, inst) {
	// current gesture isnt drag, but dragged is true
	// this means an other gesture is busy. now call dragend
	if(Detection.current.name != this.name && this.triggered) {
		inst.trigger(this.name + 'end', ev);
		this.triggered = false;
		return;
	}

	// at least multitouch
	if(ev.touches.length < 2) {
		return;
	}

	// prevent default when two fingers are on the screen
	if(inst.options.transform_always_block) {
		ev.preventDefault();
	}

	// check if all touches occurred within the instance element
	if(inst.options.transform_within_instance) {
		for(var i=-1; ev.touches[++i];) {
			if(!Utils.hasParent(ev.touches[i].target, inst.element)) {
				return;
			}
		}
	}

	switch(ev.eventType) {
		case EVENT_START:
			this.triggered = false;
			break;

		case EVENT_MOVE:
			var scale_threshold = Math.abs(1 - ev.scale);
			var rotation_threshold = Math.abs(ev.rotation);

			// when the distance we moved is too small we skip this gesture
			// or we can be already in dragging
			if(scale_threshold < inst.options.transform_min_scale &&
				rotation_threshold < inst.options.transform_min_rotation) {
				return;
			}

			// we are transforming!
			Detection.current.name = this.name;

			// first time, trigger dragstart event
			if(!this.triggered) {
				inst.trigger(this.name + 'start', ev);
				this.triggered = true;
			}

			inst.trigger(this.name, ev); // basic transform event

			// trigger rotate event
			if(rotation_threshold > inst.options.transform_min_rotation) {
				inst.trigger('rotate', ev);
			}

			// trigger pinch event
			if(scale_threshold > inst.options.transform_min_scale) {
				inst.trigger('pinch', ev);
				inst.trigger('pinch' + (ev.scale<1 ? 'in' : 'out'), ev);
			}
			break;

		case EVENT_END:
			// trigger dragend
			if(this.triggered) {
				inst.trigger(this.name + 'end', ev);
			}

			this.triggered = false;
			break;
	}
}
};

// AMD export
if(typeof define == 'function' && define.amd) {
define(function(){
	return Hammer;
});
}
// commonjs export
else if(typeof module == 'object' && module.exports) {
module.exports = Hammer;
}
// browser export
else {
window.Hammer = Hammer;
}

})(window);

// Here

function Carousel(element)
	{
			var self = this;
			element = $(element);

			var container = $(">ul", element);
			var panes = $(">ul>li", element);

			var pane_width = 0;
			var pane_count = panes.length;

			var current_pane = 0;


			/**
			 * initial
			 */
			this.init = function() {
					setPaneDimensions();

					$(window).on("load resize orientationchange", function() {
							setPaneDimensions();
					})
			};


			/**
			 * set the pane dimensions and scale the container
			 */
			function setPaneDimensions() {
					pane_width = element.width();
					panes.each(function() {
							$(this).width(pane_width);
					});
					container.width(pane_width*pane_count);
			};


			/**
			 * show pane by index
			 */
			this.showPane = function(index, animate) {
					// between the bounds
					index = Math.max(0, Math.min(index, pane_count-1));
					current_pane = index;

					var offset = -((30/pane_count)*current_pane);
					setContainerOffset(offset, animate);
			};


			function setContainerOffset(percent, animate) {
					container.removeClass("animate");

					if(animate) {
							container.addClass("animate");
					}

					if(Modernizr.csstransforms3d) {
							container.css("transform", "translate3d("+ percent +"%,0,0) scale3d(1,1,1)");
					}
					else if(Modernizr.csstransforms) {
							container.css("transform", "translate("+ percent +"%,0)");
					}
					else {
							var px = ((pane_width*pane_count) /30) * percent;
							container.css("left", px+"px");
					}
			}

			this.next = function() { return this.showPane(current_pane+1, true); };
			this.prev = function() { return this.showPane(current_pane-1, true); };


			function handleHammer(ev) {
					// disable browser scrolling
					ev.gesture.preventDefault();

					switch(ev.type) {
							case 'dragright':
							case 'dragleft':
									// stick to the finger
									var pane_offset = -(30/pane_count)*current_pane;
									var drag_offset = ((30/pane_width)*ev.gesture.deltaX) / pane_count;

									// slow down at the first and last pane
									if((current_pane == 0 && ev.gesture.direction == "right") ||
											(current_pane == pane_count-1 && ev.gesture.direction == "left")) {
											drag_offset *= .4;
									}

									setContainerOffset(drag_offset + pane_offset);
									break;

							case 'swipeleft':
									self.next();
									ev.gesture.stopDetect();
									break;

							case 'swiperight':
									self.prev();
									ev.gesture.stopDetect();
									break;

							case 'release':
									// more then 50% moved, navigate
									if(Math.abs(ev.gesture.deltaX) > pane_width/2) {
											if(ev.gesture.direction == 'right') {
													self.prev();
											} else {
													self.next();
											}
									}
									else {
											self.showPane(current_pane, true);
									}
									break;
					}
			}

			new Hammer(element[0], { drag_lock_to_axis: true }).on("release dragleft dragright swipeleft swiperight", handleHammer);
	}

var carousel = new Carousel("#carousel");
carousel.init(); 

carousel.showPane(1, false);

$(document).ready(function(){
	$('#carousel ul').attr('style', 'transform: translate3d(-15%, 0px, 0px) scale3d(1, 1, 1);');
		
	$('a.menu-icon').click(function(){
		$(this).toggleClass('active');
		carousel.showPane(0, true);
		return false;
	});
	
});	

              
            
!
999px

Console