diff --git a/bower.json b/bower.json new file mode 100644 index 0000000..79dec01 --- /dev/null +++ b/bower.json @@ -0,0 +1,16 @@ +{ + "name": "SlitSlider", + "version": "1.1.0", + "main": "js/jquery.slitslider.js", + "license": "MIT", + "ignore": [ + + ], + "keywords": [ + "slider" + ], + "dependencies": { + "jquery": ">=1.5", + "modernizr": "2.*" + } +} \ No newline at end of file diff --git a/css/style.css b/css/style.css index 46fc764..7df6ddf 100755 --- a/css/style.css +++ b/css/style.css @@ -22,7 +22,7 @@ height: 100%; top: 0; left: 0; -} +} .sl-slide { z-index: 1; @@ -63,7 +63,7 @@ padding: 200px 200px 0px 200px; } -.sl-slide-horizontal .sl-content-slice:nth-child(2) { +.sl-slide-horizontal .sl-content-slice:nth-of-type(2) { top: 50%; padding: 0px 200px 200px 200px; } @@ -86,7 +86,7 @@ padding: 200px 0px 200px 200px; } -.sl-slide-vertical .sl-content-slice:nth-child(2) { +.sl-slide-vertical .sl-content-slice:nth-of-type(2) { left: 50%; padding: 200px 200px 200px 0px; } diff --git a/js/jquery.slitslider.js b/js/jquery.slitslider.js index c1f0f3c..d5835cf 100755 --- a/js/jquery.slitslider.js +++ b/js/jquery.slitslider.js @@ -4,13 +4,30 @@ * * Licensed under the MIT license. * http://www.opensource.org/licenses/mit-license.php - * + * * Copyright 2012, Codrops * http://www.codrops.com */ +$.fn.slitsliderEmulateTransitionEnd = function (duration) { + var transEndEventNames = { + 'WebkitTransition' : 'webkitTransitionEnd', + 'MozTransition' : 'transitionend', + 'OTransition' : 'oTransitionEnd', + 'msTransition' : 'MSTransitionEnd', + 'transition' : 'transitionend' + }, + transEndEventName = transEndEventNames[ Modernizr.prefixed('transition') ]; + + var called = false, $el = this + $(this).one(transEndEventName, function () { called = true }) + + var callback = function () { if (!called) $($el).trigger(transEndEventName) } + setTimeout(callback, duration) + return this +} ;( function( $, window, undefined ) { - + 'use strict'; /* @@ -60,10 +77,10 @@ Modernizr = window.Modernizr; $.Slitslider = function( options, element ) { - + this.$elWrapper = $( element ); this._init( options ); - + }; $.Slitslider.defaults = { @@ -91,7 +108,7 @@ $.Slitslider.prototype = { _init : function( options ) { - + // options this.options = $.extend( true, {}, $.Slitslider.defaults, options ); @@ -124,9 +141,9 @@ this._loadEvents(); // slideshow if( this.options.autoplay ) { - + this._startSlideshow(); - + } }, @@ -140,35 +157,35 @@ }, _layout : function() { - + this.$slideWrapper = $( '
' ); - + // wrap the slides this.$slides.wrapAll( this.$slideWrapper ).each( function( i ) { - + var $slide = $( this ), // vertical || horizontal orientation = $slide.data( 'orientation' ); - + $slide.addClass( 'sl-slide-' + orientation ) .children() .wrapAll( '' ) .wrapAll( '' ); - + } ); - + // set the right size of the slider/slides for the current window size this._setSize(); // show first slide this.$slides.eq( this.current ).show(); - + }, _navigate : function( dir, pos ) { - + if( this.isAnimating || this.slidesCount < 2 ) { - + return false; - + } this.isAnimating = true; @@ -195,24 +212,24 @@ } this.options.onBeforeChange( $currentSlide, this.current ); - + // next slide to be shown var $nextSlide = this.$slides.eq( this.current ), // the slide we want to cut and animate $movingSlide = ( dir === 'next' ) ? $currentSlide : $nextSlide, - + // the following are the data attrs set for each slide configData = $movingSlide.data(), config = {}; - + config.orientation = configData.orientation || 'horizontal', config.slice1angle = configData.slice1Rotation || 0, config.slice1scale = configData.slice1Scale || 1, config.slice2angle = configData.slice2Rotation || 0, config.slice2scale = configData.slice2Scale || 1; - + this._validateValues( config ); - + var cssStyle = config.orientation === 'horizontal' ? { marginTop : -this.size.height / 2 } : { @@ -221,7 +238,7 @@ // default slide's slices style resetStyle = { 'transform' : 'translate(0%,0%) rotate(0deg) scale(1)', - opacity : 1 + opacity : 1 }, // slice1 style slice1Style = config.orientation === 'horizontal' ? { @@ -235,19 +252,19 @@ } : { 'transform' : 'translateX(' + this.options.translateFactor + '%) rotate(' + config.slice2angle + 'deg) scale(' + config.slice2scale + ')' }; - + if( this.options.optOpacity ) { - + slice1Style.opacity = 0; slice2Style.opacity = 0; - + } - + // we are adding the classes sl-trans-elems and sl-trans-back-elems to the slide that is either coming "next" // or going "prev" according to the direction. // the idea is to make it more interesting by giving some animations to the respective slide's elements //( dir === 'next' ) ? $nextSlide.addClass( 'sl-trans-elems' ) : $currentSlide.addClass( 'sl-trans-back-elems' ); - + $currentSlide.removeClass( 'sl-trans-elems' ); var transitionProp = { @@ -260,35 +277,35 @@ .wrap( $( '' ).css( transitionProp ) ) .parent() .cond( - dir === 'prev', + dir === 'prev', function() { - + var slice = this; this.css( slice1Style ); setTimeout( function() { - + slice.css( resetStyle ); }, 50 ); - - }, + + }, function() { - + var slice = this; setTimeout( function() { - + slice.css( slice1Style ); }, 50 ); - + } ) .clone() .appendTo( $movingSlide ) .cond( - dir === 'prev', + dir === 'prev', function() { - + var slice = this; this.css( slice2Style ); setTimeout( function() { @@ -301,7 +318,7 @@ self._onEndNavigate( slice, $currentSlide, dir ); - } ); + } ).slitsliderEmulateTransitionEnd( self.options.speed + 100); } else { @@ -311,22 +328,22 @@ } }, 50 ); - + }, function() { - + var slice = this; setTimeout( function() { $nextSlide.addClass( 'sl-trans-elems' ); - + if( self.support ) { slice.css( slice2Style ).on( self.transEndEventName, function() { self._onEndNavigate( slice, $currentSlide, dir ); - } ); + } ).slitsliderEmulateTransitionEnd( self.options.speed + 100); } else { @@ -336,95 +353,95 @@ } }, 50 ); - + } ) .find( 'div.sl-content-wrapper' ) .css( cssStyle ); - + $nextSlide.show(); - + }, _validateValues : function( config ) { - + // OK, so we are restricting the angles and scale values here. // This is to avoid the slices wrong sides to be shown. // you can adjust these values as you wish but make sure you also ajust the // paddings of the slides and also the options.translateFactor value and scale data attrs if( config.slice1angle > this.options.maxAngle || config.slice1angle < -this.options.maxAngle ) { - + config.slice1angle = this.options.maxAngle; - + } if( config.slice2angle > this.options.maxAngle || config.slice2angle < -this.options.maxAngle ) { - + config.slice2angle = this.options.maxAngle; - + } if( config.slice1scale > this.options.maxScale || config.slice1scale <= 0 ) { - + config.slice1scale = this.options.maxScale; - + } if( config.slice2scale > this.options.maxScale || config.slice2scale <= 0 ) { - + config.slice2scale = this.options.maxScale; - + } if( config.orientation !== 'vertical' && config.orientation !== 'horizontal' ) { - + config.orientation = 'horizontal' - + } - + }, _onEndNavigate : function( $slice, $oldSlide, dir ) { - + // reset previous slide's style after next slide is shown var $slide = $slice.parent(), removeClasses = 'sl-trans-elems sl-trans-back-elems'; - + // remove second slide's slice $slice.remove(); // unwrap.. $slide.css( 'z-index', 1 ) .find( 'div.sl-content-wrapper' ) .unwrap(); - + // hide previous current slide $oldSlide.hide().removeClass( removeClasses ); $slide.removeClass( removeClasses ); // now we can navigate again.. this.isAnimating = false; this.options.onAfterChange( $slide, this.current ); - + }, _setSize : function() { - + // the slider and content wrappers will have the window's width and height var cssStyle = { width : this.size.width, height : this.size.height }; - + this.$el.css( cssStyle ).find( 'div.sl-content-wrapper' ).css( cssStyle ); - + }, _loadEvents : function() { - + var self = this; - + $window.on( 'debouncedresize.slitslider', function( event ) { - + // update size values self._getSize(); // set the sizes again self._setSize(); - + } ); if ( this.options.keyboard ) { - + $document.on( 'keydown.slitslider', function(e) { var keyCode = e.keyCode || e.which, @@ -436,15 +453,15 @@ }; switch (keyCode) { - + case arrow.left : self._stopSlideshow(); self._navigate( 'prev' ); break; - + case arrow.right : - + self._stopSlideshow(); self._navigate( 'next' ); break; @@ -454,7 +471,7 @@ } ); } - + }, _startSlideshow: function() { @@ -485,7 +502,7 @@ }, _destroy : function( callback ) { - + this.$el.off( '.slitslider' ).removeData( 'slitslider' ); $window.off( '.slitslider' ); $document.off( '.slitslider' ); @@ -513,8 +530,8 @@ this.$slides = this.$slides.add( $slides ); var self = this; - - + + $slides.each( function( i ) { var $slide = $( this ), @@ -533,7 +550,7 @@ this._setSize(); this.slidesCount = this.$slides.length; - + if ( callback ) { callback.call( $items ); @@ -588,7 +605,7 @@ // public method: pauses the slideshow pause : function() { - if( this.isPlaying ) { + if( this.isPlaying || this.options.autoplay) { this._stopSlideshow(); @@ -605,72 +622,72 @@ destroy : function( callback ) { this._destroy( callback ); - + } }; - + var logError = function( message ) { if ( window.console ) { window.console.error( message ); - + } }; - + $.fn.slitslider = function( options ) { var self = $.data( this, 'slitslider' ); - + if ( typeof options === 'string' ) { - + var args = Array.prototype.slice.call( arguments, 1 ); - + this.each(function() { - + if ( !self ) { logError( "cannot call methods on slitslider prior to initialization; " + "attempted to call method '" + options + "'" ); return; - + } - + if ( !$.isFunction( self[options] ) || options.charAt(0) === "_" ) { logError( "no such method '" + options + "' for slitslider self" ); return; - + } - + self[ options ].apply( self, args ); - + }); - - } + + } else { - + this.each(function() { - + if ( self ) { self._init(); - + } else { self = $.data( this, 'slitslider', new $.Slitslider( options, this ) ); - + } }); - + } - + return self; - + }; - + } )( jQuery, window );