(function($) { 'use strict'; /** * helpers methods */ function supportcss3(prop) { var prefix = ['-webkit-', '-moz-', '']; var root = document.documentelement; function camelcase(str) { return str.replace(/\-([a-z])/gi, function(match, $1) { return $1.touppercase(); }); } for (var i = prefix.length - 1; i >= 0; i--) { var css3prop = camelcase(prefix[i] + prop); if (css3prop in root.style) { return css3prop; } } return false; } function transitionend() { var transitions = { 'transition': 'transitionend', 'webkittransition': 'webkittransitionend', 'moztransition': 'moztransitionend' }; var root = document.documentelement; for (var name in transitions) { if (root.style[name] !== undefined) { return transitions[name]; } } return false; } function support3d() { if (!window.getcomputedstyle) { return false; } var el = document.createelement('div'), has3d, transform = supportcss3('transform'); document.body.insertbefore(el, null); el.style[transform] = 'translate3d(1px,1px,1px)'; has3d = getcomputedstyle(el)[transform]; document.body.removechild(el); return (has3d !== undefined && has3d.length > 0 && has3d !== "none"); } var touch = { hastouch: !!(("ontouchstart" in window) || window.documenttouch && document instanceof documenttouch), event: function() { return { start: (this.hastouch) ? 'touchstart' : 'mousedown', move: (this.hastouch) ? 'touchmove' : 'mousemove', end: (this.hastouch) ? 'touchend' : 'mouseup', leave: (this.hastouch) ? 'touchleave' : 'mouseout' }; } }; function throttle(func, wait, options) { var context, args, result; var timeout = null; var previous = 0; if (!options) options = {}; var later = function () { previous = options.leading === false ? 0 : date.now(); timeout = null; result = func.apply(context, args); if (!timeout) context = args = null; }; return function () { var now = date.now(); if (!previous && options.leading === false) previous = now; var remaining = wait - (now - previous); context = this; args = arguments; if (remaining <= 0 || remaining > wait) { if (timeout) { cleartimeout(timeout); timeout = null; } previous = now; result = func.apply(context, args); if (!timeout) context = args = null; } else if (!timeout && options.trailing !== false) { timeout = settimeout(later, remaining); } return result; }; } var plugin = 'ikslider'; var ikslider = function(el, options) { var settings = $.extend({ touch: true, infinite: false, autoplay: true, pauseonhover: true, delay: 3000, responsive: true, controls: true, arrows: true, caption: true, speed: 300, cssease: 'ease-out' }, options || {}); var $container = el; var $slider = $container.find('.slider'); var $arrows = $container.find('.slider__switch'); var $caption = $slider.find('.slider__caption'); var $slide = $slider.find('.slider__item'); var sliderstyle = $slider.get(0).style; var slidelen = $slide.length; var slidewidth = $container.outerwidth(); var sliderwidth = slidelen * slidewidth; var current = 0; var offset = 0; var busy = false; var touchflag = false; var $controlpanel; var $navcontrol; var timer; var transformproperty = supportcss3('transform'); var transitionproperty = supportcss3('transition'); var has3d = support3d(); function init() { // calculate dimensions _dimmensions(); if (settings.responsive) { $(window).on('resize.' + plugin, throttle(_responsive, 50)); } // if caption false, hide caption !settings.caption && $caption.attr('cl', true); // create nav controls settings.controls && _controls(); if (settings.touch) { // if the image img tag set attribute graggable false $slide.find('img').attr('draggable', false); // binding touch events _touchenable(); } if (settings.autoplay) { _autoplay(); if (settings.pauseonhover) { $container.on('mouseenter.' + plugin, function() { clearinterval(timer); }); $container.on('mouseleave.' + plugin, _autoplay); } } if (settings.arrows) { // if infinite setting false hide arrows !settings.infinite && _stopinfinite('prev'); $arrows.on('click.' + plugin, function(e) { e.preventdefault(); if (this.getattribute('data-ikslider-dir') === 'next') { show(current + 1); } else { show(current - 1); } }); } else { $arrows.attr('cl', true); } } function _controls() { $controlpanel = $('
', { 'class': 'slider-nav' }) .appendto($container); var links = []; for (var i = 0; slidelen > i; i++) { var act = (current === i) ? 'is-active' : ''; links.push(''); } $controlpanel.html(links.join('')); $navcontrol = $controlpanel.find('.slider-nav__control'); $controlpanel.on('click.' + plugin, '.slider-nav__control', function(e) { e.preventdefault(); if ($(this).hasclass('is-active')) return; show(parseint(this.getattribute('data-ikslider-control'), 10)); }); } function _touchenable() { $slider.addclass('has-touch'); var touchx; var touchy; var delta; var target; $slider.on(touch.event().start + '.' + plugin, function(e) { if (touchflag || busy) return; var touch; if (e.originalevent.targettouches) { target = e.originalevent.targettouches[0].target; touch = e.originalevent.targettouches[0]; } else { touch = e.originalevent; e.preventdefault(); } delta = 0; touchx = touch.pagex || touch.clientx; touchy = touch.pagey || touch.clienty; touchflag = true; }); $slider.on(touch.event().move + '.' + plugin, function(e) { if (!touchflag) return; var touch; if (e.originalevent.targettouches) { if (e.originalevent.targettouches.length > 1 || target !== e.originalevent.targettouches[0].target) { return; } touch = e.originalevent.targettouches[0]; } else { e.preventdefault(); touch = e.originalevent; } var currentx = touch.pagex || touch.clientx; var currenty = touch.pagey || touch.clienty; if (math.abs(touchx - currentx) >= math.abs(touchy - currenty)) { delta = touchx - currentx; _move(parseint(offset, 10) - delta); } }); $slider.on(touch.event().end + '.' + plugin, function(e) { if (!touchflag) return; var swipeto = delta < 0 ? current - 1 : current + 1; if (math.abs(delta) < 50 || (!settings.infinite && (swipeto > slidelen - 1 || swipeto < 0))) { touchflag = false; _move(offset, true); return; } touchflag = false; target = null; show(swipeto); }); $slider.on(touch.event().leave + '.' + plugin, function() { if (touchflag) { _move(offset, true); touchflag = false; } }); } function show(slide) { if (busy) return; if (slide === current) return; current = (slide > slidelen - 1) ? 0 : slide; if (slide < 0) { current = slidelen - 1; } if (!settings.infinite) { $arrows.attr('cl', false); if (slide === slidelen - 1) { _stopinfinite('next'); } if (current === 0) { _stopinfinite('prev'); } } offset = -(slidewidth * (current)); if (settings.controls) { $navcontrol.removeclass('is-active') .eq(current) .addclass('is-active'); } busy = true; _move(offset, true); _triggerchange(); } function _move(value, hasanimate) { if (transitionproperty && transformproperty) { (hasanimate) ? sliderstyle[transitionproperty] = transformproperty + ' ' + settings.speed + 'ms ' + settings.cssease: sliderstyle[transitionproperty] = "none"; (has3d) ? sliderstyle[transformproperty] = 'translate3d(' + value + 'px, 0, 0)': sliderstyle[transformproperty] = 'translatex(' + value + 'px)'; if (hasanimate) { $slider.one(transitionend(), function(e) { busy = false; }); } else { busy = false; } } else { if (hasanimate) { $slider.animate({ 'margin-left': value }, settings.speed, 'linear', function() { busy = false; }); } else { $slider.css('margin-left', value); busy = false; } } } // change event trigger function _triggerchange() { var eventslide = $.event('changeslide.' + plugin, { currentslide: current }); $container.trigger(eventslide); } function _autoplay() { if (timer) clearinterval(timer); timer = setinterval(function() { if (!touchflag) { show(current + 1); } }, settings.delay); } function _stopinfinite(direction) { $container.find('.slider__switch--' + direction).attr('cl', true); } function _dimmensions() { slidewidth = $container.outerwidth(); sliderwidth = slidelen * slidewidth; $slide.css('width', slidewidth); sliderstyle['width'] = sliderwidth + 'px'; } function _responsive() { if (timer) clearinterval(timer); _dimmensions(); offset = -(slidewidth * current); _move(offset); settings.autoplay && _autoplay(); } function destroy() { sliderstyle['width'] = ''; sliderstyle[transformproperty] = ''; sliderstyle[transitionproperty] = ''; $slide.css('width', ''); if (settings.autoplay) { if (timer) clearinterval(timer); $container.off('mouseenter.' + plugin); $container.off('mouseleave.' + plugin); } if (settings.arrows) { $arrows.off('click.' + plugin); $arrows.attr('cl', false); } if (settings.controls) { $controlpanel.off('click.' + plugin).remove(); } $caption.attr('cl', false); if (settings.touch) { $slider .removeclass('has-touch') .off(touch.event().start + '.' + plugin) .off(touch.event().move + '.' + plugin) .off(touch.event().end + '.' + plugin) .off(touch.event().leave + '.' + plugin); touchflag = false; } if (settings.responsive) { $(window).off('resize.' + plugin); } $container.removedata(plugin); $container = null; $slider = null; $arrows = null; $caption = null; $slide = null; $controlpanel = null; $navcontrol = null; sliderstyle = null; slidelen = null; slidewidth = null; sliderwidth = null; current = null; offset = null; busy = null; timer = null; has3d = null; busy = false; transformproperty = null; transitionproperty = null; } /** * @return {methods} [public slider methods api] */ return { init: init, show: show, destroy: destroy }; }; $.fn[plugin] = function(opt) { var _this = this; this.each(function() { var $this = $(this); var slider = $this.data(plugin); var options = typeof opt === 'object' && opt; if (!slider && /(destroy|\d+)/.test(opt)) return; if (!slider) { slider = new ikslider($this, options); $this.data('ikslider', slider); slider.init(); } if (typeof opt === 'string' || typeof opt === 'number' && opt !== 'init') { if (typeof opt === 'number') { _this = slider.show(opt); } else { if(slider[opt]) { _this = slider[opt](); } else { throw new error('error:: ikslider has no method: ' + opt); } } } return _this; }); }; })(jquery);