目录如下:
只有text 是用于测试,其他都是必须的,img下面有两个独立的slider,两个独立方便日后修改图片
以下是focus-slider中的 img/focus-slider是轮播图片直接下载即可:
以下是todays-slider的图片:
<!-- 轮播图两个思路: 1,把每个轮播对象看做一个对象进行轮播的 2,把所有轮播对象看做一个对象进行轮播的 每个轮播对象中只有一张图片的轮播图 直接加载 和 按需加载,基本一致,只有最后一点不同。 1,直接加载 使用轮播图对象调用slider插件 $focusSlider.slider({ css3: true, js: false, animation: 'fade', // fade淡入淡出 slide滑动 activeIndex: 0, //默认图片,圆点按钮显示的索引值 interval: 0 //自动轮播的时间间隔 }); 2,按需加载 需要额外写一段代码,具体查看index.js 中的代码 轮播必须步骤: 1,搭好结构,所有的类名必须保持一致。,谨记下载好图片放到指定文件夹中。 indicator /'ɪndɪkeɪtə/ 标志 2,导入css样式:base.css , common.css ,注意common.css中轮播图中 的非共性样式可以写到index.css中去,轮播图基本都是共性,复用时一些特性可以直接在index.css中覆盖。 3,导入以下js脚本 jquery.js transition.js //兼容:transitionend 动画结束时执行的操作 的写法 showHide.js //silent,css3,js,三种方式显示 move.js //指定一个物体移动到指定位置。 slider.js //轮播图脚本 index.js //特性脚本 注意点: 1,写样式时: .slider-control{ display:none;} 必须隐藏,否则加载时不用鼠标悬浮,左右按钮就会显示 .slider-fade .slider-item{ display:none;} 必须隐藏,否则加载时,没有把所有轮播图片都隐藏,所以点击前四次都是显示第一张图片 2,使用直接加载时, 使用轮播图对象调用slider插件 $focusSlider.slider({ css3: true, js: false, animation: 'fade', // fade淡入淡出 slide滑动 activeIndex: 0, //默认图片,圆点按钮显示的索引值 interval: 0 //自动轮播的时间间隔 }); 结构中的img标签改为: <img src="需要加载的图片地址" alt=""> 即: 把整个轮播图对象都修改为: <div class="slider-item"> <a href="javascript:;"><img src='img/focus-slider/1.png' alt="" ></a> </div> 3,其中以下几个字体的左右尖括号比较向,方向键: font-family: serif; font-family: simsum; 4, 在index.js中 //手动延迟一秒,模拟从其他服务器获取图片 //setTimeout(function(){ //image.src = url; //},1000); ===此外,每个轮播对象 .slider-item 中有多张图片时的做法:=== 1,写好结构如下:.todays整个结构,谨记下载好需要的图片 2,todays-slider 这可以写到index.css中,特有样式: .todays .slider{//设置整个轮播图的宽高 100%; height:158px; } .todays .slider-img{ //设置每个图片的宽度 240px; } 3,按需加载 的代码: //todays-slider var $todaysSlider = $('#todays-slider'); $todaysSlider.items = {}; $todaysSlider.loadedItemNum = 0; $todaysSlider.totalItemNum = $todaysSlider.find('.slider-img').length; $todaysSlider.on('slider-show', $todaysSlider.loadItem = function(e, index, elem) { console.log(1); if ($todaysSlider.items[index] !== 'loaded') { $todaysSlider.trigger('slider-loadItem', [index, elem]); } }); $todaysSlider.on('slider-loadItem', function(e, index, elem) { // 按需加载 var $imgs = $(elem).find('.slider-img'); $imgs.each(function (_,el) { // _ 相当占位,不使用该参数。 var $img=$(el); loadImg($img.data('src'), function(url) { $img.attr('src', url); $todaysSlider.items[index] = 'loaded'; $todaysSlider.loadedItemNum++; console.log(index + ': loaded'); if ($todaysSlider.loadedItemNum === $todaysSlider.totalItemNum) { // 全部加载完毕 $todaysSlider.trigger('slider-itemsLoaded'); } }, function(url) { console.log('从' + url + '加载图片失败'); // 多加载一次 // 显示备用图片 $img.attr('src', '../img/focus-slider/placeholder.png'); }); }); }); $todaysSlider.on('slider-itemsLoaded', function(e) { console.log('itemsLoaded'); // 清除事件 $todaysSlider.off('slider-show', $todaysSlider.loadItem); }); function loadImg(url, imgLoaded, imgFailed) { var image = new Image(); image.onerror = function() { if (typeof imgFailed === 'function') imgFailed(url); } image.onload = function() { if (typeof imgLoaded === 'function') imgLoaded(url); }; // image.src=url; setTimeout(function() { image.src = url; }, 1000); } $todaysSlider.slider({ css3: true, js: false, animation: 'slide', // fade slide activeIndex: 0, interval: 0 }); -->
slider.html
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>轮播图</title> <link rel="stylesheet" type="text/css" href="css/base.css"> <link rel="stylesheet" type="text/css" href="css/common.css"> </head> <body> <!-- focus-slider --> <div id="focus-slider" class="slider"> <div class="slider-container"> <div class="slider-item"> <a href="javascript:;"><img src="img/focus-slider/loading.gif" data-src='img/focus-slider/1.png' alt="" class="slider-img"></a> </div> <div class="slider-item"> <a href="javascript:;"><img src="img/focus-slider/loading.gif" data-src='img/focus-slider/2.png' alt="" class="slider-img"></a> </div> <div class="slider-item"> <a href="javascript:;"><img src="img/focus-slider/loading.gif" data-src='img/focus-slider/3.png' alt="" class="slider-img"></a> </div> <div class="slider-item"> <a href="javascript:;"><img src="img/focus-slider/loading.gif" data-src='img/focus-slider/4.png' alt="" class="slider-img"></a> </div> </div> <ol class="slider-indicator-wrap"> <li class="slider-indicator text-hidden fl">1</li> <li class="slider-indicator text-hidden fl">2</li> <li class="slider-indicator text-hidden fl">3</li> <li class="slider-indicator text-hidden fl">4</li> </ol> <a href="javascript:;" class="slider-control slider-control-left"><</a> <a href="javascript:;" class="slider-control slider-control-right">></a> </div> <!-- todays-slider --> <div class="todays"> <div class="container"> <div id="todays-slider" class="slider"> <div class="slider-container"> <div class="slider-item"> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/1.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/2.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/3.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/4.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/5.png" class="slider-img" /></a> </div> <div class="slider-item"> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/6.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/7.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/8.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/9.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/10.png" class="slider-img" /></a> </div> <div class="slider-item"> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/11.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/3.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/5.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/7.png" class="slider-img" /></a> <a href="###" target="_blank" class="fl"><img src="img/todays-slider/loading.gif" alt="" data-src="img/todays-slider/9.png" class="slider-img" /></a> </div> </div> <a href="javascript:;" class="slider-control slider-control-left"><</a> <a href="javascript:;" class="slider-control slider-control-right">></a> </div> </div> </div> <script type="text/javascript" src="js/jquery.js"></script> <script type="text/javascript" src="js/transition.js"></script> <script type="text/javascript" src="js/showHide.js"></script> <script type="text/javascript" src="js/move.js"></script> <script type="text/javascript" src="js/slider.js"></script> <script type="text/javascript" src="js/index.js"></script> </body> </html>
base.css
/*css reset*/ /*清除内外边距*/ body, h1, h2, h3, h4, h5, h6, p, hr, /*结构元素*/ ul, ol, li, dl, dt, dd, /*列表元素*/ form, fieldset, legend, input, button, select, textarea, /*表单元素*/ th, td, /*表格元素*/ pre { padding: 0; margin: 0; } /*重置默认样式*/ body, button, input, select, textarea { /*font: 12px/1 微软雅黑, Tahoma, Helvetica, Arial, 宋体, sans-serif;*/ color: #333; font: 12px/1 "Microsoft YaHei", Tahoma, Helvetica, Arial, SimSun, sans-serif; } h1, h2, h3, h4, h5, h6 { font-size: 100%; font-weight: normal; } em, i { font-style: normal; } a { text-decoration: none; } li { list-style-type: none; vertical-align: top; } img { border: none; /*display: block;*/ vertical-align: top; } textarea { overflow: auto; resize: none; } table { border-spacing: 0; border-collapse: collapse; } /*常用公共样式*/ .fl { float: left; display: inline; } .fr { float: right; display: inline; } .cf:before, .cf:after { content: " "; display: table; } .cf:after { clear: both; } .cf { *zoom: 1; }
common.css
/*公共样式*/ .container { /*站点导航*/ 1200px; margin: 0 auto; } a.link { /*链接正常颜色*/ color: #4d555d; } a.link:hover { /*链接经过颜色*/ color: #f01414 !important; } .transition { -o-transition: all 0.5s; -ms-transition: all 0.5s; -moz-transition: all 0.5s; -webkit-transition: all 0.5s; transition: all 0.5s; } .text-hidden{ text-indent: -9999px; overflow: hidden; } .text-ellipsis{ text-overflow: ellipsis; white-space: nowrap; overflow: hidden; } /*showhide*/ .fadeOut { visibility: hidden !important; opacity: 0 !important; } .slideUpDownCollapse { height: 0 !important; padding-top: 0 !important; padding-bottom: 0 !important; } .slideLeftRightCollapse { 0 !important; padding-left: 0 !important; padding-right: 0 !important; } /*slider 自己写的轮播图样式*/ .slider{ margin: 100px auto; height: 504px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ 728px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ position: relative; overflow: hidden; } .slider-container{ } .slider-item{ position: absolute; top: 0; left: 0; 100%; height: 100%; } .slider-indicator-wrap{ position: absolute; left: 50%; transform: translateX(-50%); bottom: 10px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ } .slider-indicator{ 8px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ height: 8px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ border-radius: 50%; background: #f7f8f9; border: 2px solid #858b92; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ margin-left: 8px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ } .slider-indicator-active { background: #000; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ border: 2px solid #858b92; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ } .slider-control{ /* 加载就隐藏,否则加载的时候就显示着 */ display: none; 28px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ height: 62px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ line-height: 62px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ position: absolute; top: 50%; transform: translateY(-50%); font-size: 22px; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ font-family: serif; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ background: #000; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ color: #fff; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ opacity: .8; /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ filter: alpha(opacity=80); /*非公共样式,可以写到index.css中,这里只存放公共样式或组件*/ text-align: center; } .slider-control-left{ left: 0; } .slider-control-right{ right: 0; } .slider-slide .slider-item{ position: absolute; top: 0; left: 100%;/* 通过移动left属性值来实现图片切换,每次移动都是图片的100%宽度 */ 100%; height: 100%; } .slider-fade .slider-item{ /* 加载就隐藏,否则会出现前面几次点击不会切换图片 */ display: none; position: absolute; top: 0; left: 0; 100%; height: 100%; } /*todays-slider 这可以写到index.css中,都是特性*/ .todays .slider{ 100%; height:158px; } .todays .slider-img{ 240px; }
jquery.js
<!-- 这里使用CDN引入jquery.js文件,仅用发布时使用,开发时比较慢 --> <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script> <script> /* 开发时使用本地效率比较高 判断如果上面的cdn引入的jquery.js文件没有成功(如:服务器不稳定导致) 则引入本地的jquery.js文件。 此外,结尾的的script标签使用反斜杠进行转义: / */ window.jQuery || document.write('<script src = "js/index.js"></script>') //也可以使用字符串拼接 // window.jQuery || document.write('<script src = "js/index.js"><' + '/script>') </script>
transition.js
(function () { // 'use strict';//在IE浏览器下,使用严格模式是不能定义多个变量的,所以不能使用严格模式 //判断样式是否支持该浏览器,可以在控制台输出 document.body.style[属性名] = ""; 则支持 //如果返回的 undefined 则不支持。 //因为调用未定义的对象,报错;使用未定义的属性,返回undefined var transitionEndEventName = { transition: 'transitionend', MozTransition: 'transitionend', WebkitTransition: 'webkitTransitionEnd', OTransition: 'oTransitionEnd otransitionend' }; var transitionEnd = '', isSupport = false; for (var name in transitionEndEventName) { if (document.body.style[name] !== undefined) { transitionEnd = transitionEndEventName[name]; isSupport = true; break; } } //暴露一个借口对象给外界调用 // window.mt = "" window.mt = undefined 进行隐式转换 都是false // 所以window.mt 只能是一个对象时才返回真 // 与找false,或找true window.mt = window.mt || {}; window.mt.transition = { end: transitionEnd, isSupport: isSupport }; })();
showHide.js
(function($) { var transition = window.mt.transition; // transition兼容解决,transition.js // 提取init公共部分 function init($elem, hiddenCallback) { if ($elem.is(':hidden')) { $elem.data('status', 'hidden'); if (typeof hiddenCallback === 'function') hiddenCallback(); } else { $elem.data('status', 'shown'); } } // 提取show公共部分 function show($elem, callback) { if ($elem.data('status') === 'show') return; if ($elem.data('status') === 'shown') return; $elem.data('status','show').trigger('show'); callback(); } function hide($elem, callback) { if ($elem.data('status') === 'hide') return; if ($elem.data('status') === 'hidden') return; $elem.data('status', 'hide').trigger('hide'); callback(); } // 正常显示和隐藏 var silent = { //初始化显示和隐藏的状态 // if ($elem.is(':hidden')) { // $elem.data('status', 'hidden'); // if(typeof hiddenCallback==='function') hiddenCallback(); // } else { // $elem.data('status', 'shown'); // } // 提取公共init后 init: init, // show: function($elem) { // //判断状态,解决重复触发事件 // if ($elem.data('status') === 'show') return; // if ($elem.data('status') === 'shown') return; // //给元素添加状态值 // $elem.data('status', 'show').trigger('show'); // $elem.show(); // $elem.data('status', 'shown').trigger('shown'); // }, show: function($elem) { show($elem, function() { $elem.show(); $elem.data('status', 'shown').trigger('shown'); }); }, // hide: function($elem) { // if ($elem.data('status') === 'hide') return; // if ($elem.data('status') === 'hidden') return; // $elem.data('status', 'hide').trigger('hide'); // $elem.hide(); // $elem.data('status', 'hidden').trigger('hidden'); // } hide: function($elem) { hide($elem, function() { $elem.hide(); $elem.data('status', 'hidden').trigger('hidden'); }); } }; // 带效果的显示和隐藏,css3实现方法 var css3 = { fade: { // 淡入淡出 // init: function($elem) { // $elem.addClass('transition'); // if ($elem.is(':hidden')) { // $elem.data('status', 'hidden'); // $elem.addClass('fadeOut'); // } else { // $elem.data('status', 'shown'); // } // 提取公共init后,独有的内容 // init: function($elem) { // $elem.addClass('transition'); // init($elem, function() { // $elem.addClass('fadeOut'); // }); init: function($elem) { css3._init($elem, 'fadeOut'); }, // show: function($elem) { // if ($elem.data('status') === 'show') return; // if ($elem.data('status') === 'shown') return; // //给元素添加状态值 // $elem.data('status', 'show').trigger('show'); // $elem.off('transitionend').one('transitionend', function() { // $elem.data('status', 'shown').trigger('shown'); // }); // $elem.show(); // setTimeout(function() { // $elem.removeClass('fadeOut'); // }, 20); // }, show: function($elem) { css3._show($elem, 'fadeOut'); }, // hide: function($elem) { // if ($elem.data('status') === 'hide') return; // if ($elem.data('status') === 'hidden') return; // $elem.data('status', 'hide').trigger('hide'); // $elem.off('transitionend').one('transitionend', function() { // $elem.hide(); // $elem.data('status', 'hidden').trigger('hidden'); // }); // $elem.addClass('fadeOut'); // } hide: function($elem) { css3._hide($elem, 'fadeOut'); } }, slideUpDown: { // 上下滚动 // init: function($elem) { // $elem.height($elem.height()); //设置高度,解决没有slideUpDown的过程。 // $elem.addClass('transition'); // init($elem, function() { // $elem.addClass('slideUpDownCollapse'); // }); init: function($elem) { $elem.height($elem.height()); css3._init($elem, 'slideUpDownCollapse'); }, show: function($elem) { css3._show($elem, 'slideUpDownCollapse'); }, hide: function($elem) { css3._hide($elem, 'slideUpDownCollapse'); } }, slideLeftRight: { // 左右滚动 init: function($elem) { $elem.width($elem.width()); css3._init($elem, 'slideLeftRightCollapse'); }, show: function($elem) { css3._show($elem, 'slideLeftRightCollapse'); }, hide: function($elem) { css3._hide($elem, 'slideLeftRightCollapse'); } }, fadeSlideUpDown: { // 淡入淡出上下滚动 init: function($elem) { $elem.height($elem.height()); css3._init($elem, 'fadeOut slideUpDownCollapse'); }, show: function($elem) { css3._show($elem, 'fadeOut slideUpDownCollapse'); }, hide: function($elem) { css3._hide($elem, 'fadeOut slideUpDownCollapse'); } }, fadeSlideLeftRight: { // 淡入淡出左右滚动 init: function($elem) { $elem.width($elem.width()); css3._init($elem, 'fadeOut slideLeftRightCollapse'); }, show: function($elem) { css3._show($elem, 'fadeOut slideLeftRightCollapse'); }, hide: function($elem) { css3._hide($elem, 'fadeOut slideLeftRightCollapse'); } } }; css3._init = function($elem, className) { $elem.addClass('transition'); init($elem, function() { $elem.addClass(className); }); }; css3._show = function($elem, className) { show($elem, function() { $elem.off(transition.end).one(transition.end, function() { $elem.data('status', 'shown').trigger('shown'); }); $elem.show(); setTimeout(function() { $elem.removeClass(className); }, 20); }); }; css3._hide = function($elem, className) { hide($elem, function() { $elem.off(transition.end).one(transition.end, function() { $elem.hide(); $elem.data('status', 'hidden').trigger('hidden'); }); $elem.addClass(className); }); } // 带效果的显示和隐藏,js实现方法 var js = { fade: { // 淡入淡出 init: function($elem) { js._init($elem); }, show: function($elem) { js._show($elem, 'fadeIn'); }, hide: function($elem) { js._hide($elem, 'fadeOut'); } }, slideUpDown: { // 上下滚动 init: function($elem) { js._init($elem); }, show: function($elem) { js._show($elem, 'slideDown'); }, hide: function($elem) { js._hide($elem, 'slideUp'); } }, slideLeftRight: { // 左右滚动 init: function($elem) { // var styles = {}; // styles['width'] = $elem.css('width'); // styles['padding-left'] = $elem.css('padding-left'); // styles['padding-right'] = $elem.css('padding-right'); // $elem.data('styles', styles); // $elem.removeClass('transition'); // init($elem, function() { // $elem.css({ // 'width': 0, // 'padding-left': 0, // 'padding-right': 0 // }); // }); js._customInit($elem, { 'width': 0, 'padding-left': 0, 'padding-right': 0 }); }, show: function($elem) { // var styles = $elem.data('styles'); // show($elem, function() { // $elem.show(); // $elem.stop().animate({ // 'width': styles['width'], // 'padding-left': styles['padding-left'], // 'padding-right': styles['padding-right'] // }, function() { // $elem.data('status', 'shown').trigger('shown'); // }); // }); js._customshow($elem); }, hide: function($elem) { // hide($elem, function() { // $elem.stop().animate({ // 'width': 0, // 'padding-left': 0, // 'padding-right': 0 // }, function() { // $elem.hide(); // $elem.data('status', 'hidden').trigger('hidden'); // }); // }); // } js._customHide($elem, { 'width': 0, 'padding-left': 0, 'padding-right': 0 }); } }, fadeSlideUpDown: { // 淡入淡出上下滚动 init: function($elem) { // var styles = {}; // styles['opacity'] = $elem.css('opacity'); // styles['height'] = $elem.css('height'); // styles['padding-top'] = $elem.css('padding-top'); // styles['padding-bottom'] = $elem.css('padding-bottom'); // $elem.data('styles', styles); // $elem.removeClass('transition'); // init($elem, function() { // $elem.css({ // 'opacity': 0, // 'height': 0, // 'padding-top': 0, // 'padding-bottom': 0 // }); // }); js._customInit($elem, { 'opacity': 0, 'height': 0, 'padding-top': 0, 'padding-bottom': 0 }); }, show: function($elem) { // var styles = $elem.data('styles'); // show($elem, function() { // $elem.show(); // $elem.stop().animate({ // 'opacity': styles['opacity'], // 'height': styles['height'], // 'padding-top': styles['padding-top'], // 'padding-bottom': styles['padding-bottom'] // }, function() { // $elem.data('status', 'shown').trigger('shown'); // }); // }); js._customshow($elem); }, hide: function($elem) { // hide($elem, function() { // $elem.stop().animate({ // 'opacity': 0, // 'height': 0, // 'padding-top': 0, // 'padding-bottom': 0 // }, function() { // $elem.hide(); // $elem.data('status', 'hidden').trigger('hidden'); // }); // }); // } js._customHide($elem, { 'opacity': 0, 'height': 0, 'padding-top': 0, 'padding-bottom': 0 }); } }, fadeSlideLeftRight: { // 淡入淡出左右滚动 init: function($elem) { // var styles = {}; // styles['opacity'] = $elem.css('opacity'); // styles['width'] = $elem.css('width'); // styles['padding-left'] = $elem.css('padding-left'); // styles['padding-right'] = $elem.css('padding-right'); // $elem.data('styles', styles); // $elem.removeClass('transition'); // init($elem, function() { // $elem.css({ // 'opacity': 0, // 'width': 0, // 'padding-left': 0, // 'padding-right': 0 // }); // }); js._customInit($elem, { 'opacity': 0, 'width': 0, 'padding-left': 0, 'padding-right': 0 }); }, show: function($elem) { // var styles = $elem.data('styles'); // show($elem, function() { // $elem.show(); // $elem.stop().animate({ // 'opacity': styles['opacity'], // 'width': styles['width'], // 'padding-left': styles['padding-left'], // 'padding-right': styles['padding-right'] // }, function() { // $elem.data('status', 'shown').trigger('shown'); // }); // }); js._customshow($elem); }, hide: function($elem) { // hide($elem, function() { // $elem.stop().animate({ // 'opacity': 0, // 'width': 0, // 'padding-left': 0, // 'padding-right': 0 // }, function() { // $elem.hide(); // $elem.data('status', 'hidden').trigger('hidden'); // }); // }); // } js._customHide($elem, { 'opacity': 0, 'width': 0, 'padding-left': 0, 'padding-right': 0 }); } } }; js._init = function($elem, hiddenCallback) { $elem.removeClass('transition'); // js和transition动画冲突,在执行js前,将transition去掉,屏蔽风险。 init($elem, hiddenCallback); }; js._customInit = function($elem, options) { var styles = {}; for (var p in options) { styles[p] = $elem.css(p); } $elem.data('styles', styles); js._init($elem, function() { $elem.css(options); }); }; js._customshow = function($elem) { var styles = $elem.data('styles'); show($elem, function() { $elem.show(); $elem.stop().animate($elem.data('styles'), function() { $elem.data('status', 'shown').trigger('shown'); }); }); }; js._customHide = function($elem, options) { hide($elem, function() { $elem.stop().animate(options, function() { $elem.hide(); $elem.data('status', 'hidden').trigger('hidden'); }); }); }; js._show = function($elem, mode) { show($elem, function() { $elem.stop()[mode](function() { $elem.data('status', 'shown').trigger('shown'); }); }); }; js._hide = function($elem, mode) { hide($elem, function() { $elem.stop()[mode](function() { $elem.data('status', 'hidden').trigger('hidden'); }); }); }; var defaults = { css3: true, js: true, animation: 'fade' }; function showHide($elem, options) { var mode = null; // options = $.extend({}, defaults, options); if (options.css3 && transition.isSupport) { //css3 transition // css3[options.animation].init($elem); mode = css3[options.animation] || css3[defaults.animation]; // return { // // show:css3[options.animation].show, // // hide:css3[options.animation].hide // }; } else if (options.js) { //js animation // js[options.animation].init($elem); // return { // show: js[options.animation].show, // hide: js[options.animation].hide // }; mode = js[options.animation] || js[defaults.animation]; } else { // no animation // silent.init($elem); // return { // show: silent.show, // hide: silent.hide // }; mode = silent; } mode.init($elem); return { // show: mode.show, // hide: mode.hide show: $.proxy(mode.show, this, $elem), hide: $.proxy(mode.hide, this, $elem), }; } $.fn.extend({ showHide: function (option) { return this.each(function () { var $this = $(this), options = $.extend({}, defaults, typeof option === 'object' && option), mode = $this.data('showHide'); if (!mode) { $this.data('showHide', mode = showHide($this, options)); } if (typeof mode[option] === 'function') { mode[option](); } }); } }); // window.mt = window.mt || {}; // window.mt.showHide = showHide; })(jQuery);
move.js
(function($) { 'use strict'; var transition = window.mt.transition; var init = function($elem) { this.$elem = $elem; this.curX = parseFloat(this.$elem.css('left')); this.curY = parseFloat(this.$elem.css('top')); } var to = function(x, y, callback) { x = (typeof x === 'number') ? x : this.curX; y = (typeof y === 'number') ? y : this.curY; if (this.curX === x && this.curY === y) return; this.$elem.trigger('move', [this.$elem]); if (typeof callback === 'function') { callback(); } this.curX = x; this.curY = y; } var Silent = function($elem) { init.call(this, $elem); //改变this的指向,这里this指外面的this,如不使用call,this指init。 this.$elem.removeClass('transition'); }; Silent.prototype.to = function(x, y) { var self = this; to.call(this, x, y, function() { self.$elem.css({ left: x, top: y }); self.$elem.trigger('moved', [self.$elem]); }); }; Silent.prototype.x = function(x) { // if(this.curX===x) return; // this.$elem.css({ // left:x // }); // this.curX=x; this.to(x); }; Silent.prototype.y = function(y) { // if(this.curY===y) return; // this.$elem.css({ // top:y // }); // this.curY=y; this.to(null, y); }; // css3 方式 var Css3 = function($elem) { this.$elem = $elem; this.$elem.addClass('transition'); this.curX = parseFloat(this.$elem.css('left')); this.curY = parseFloat(this.$elem.css('top')); this.$elem.css({ left: this.curX, top: this.curY }); }; Css3.prototype.to = function(x, y) { var self = this; to.call(this, x, y, function() { self.$elem.off(transition.end).one(transition.end, function() { self.$elem.trigger('moved', [self.$elem]); // self.$elem.data('status','moved'); // self.curX = x; // self.curY = y; }); self.$elem.css({ left: x, top: y }); }); // x = (typeof x === 'number') ? x : this.curX; // y = (typeof y === 'number') ? y : this.curY; // if (this.curX === x && this.curY === y) return; // // if(this.$elem.data('status')==='moving') return; // // this.$elem.data('status','moving'); // var self = this; // this.$elem.trigger('move', [this.$elem]); // this.$elem.off(transition.end).one(transition.end, function() { // self.$elem.trigger('moved', [self.$elem]); // // self.$elem.data('status','moved'); // // self.curX = x; // // self.curY = y; // }); // // console.log(1); // this.$elem.css({ // left: x, // top: y // }); // this.curX = x; // this.curY = y; }; Css3.prototype.x = function(x) { this.to(x); }; Css3.prototype.y = function(y) { this.to(null, y); }; // js方式 var Js = function($elem) { init.call(this, $elem); this.$elem.removeClass('transition'); }; Js.prototype.to = function(x, y) { var self = this; to.call(this, x, y, function() { self.$elem.stop().animate({ left: x, top: y }, function() { self.$elem.trigger('moved', [self.$elem]); }); }); }; Js.prototype.x = function(x) { this.to(x); }; Js.prototype.y = function(y) { this.to(null, y); }; // var $box = $('#box'), // $goBtn = $('#go-btn'), // $backBtn = $('#back-btn'), // move = new Js($box); // $box.on('move moved', function(e, $elem) { // console.log(e.type); // // console.log($elem); // }); // $goBtn.on('click', function() { // move.to(100, 50); // // move.to(100); // }); // $backBtn.on('click', function() { // move.to(0, 20); // // move.to(0); // }); var defaults = { css3: false, js: false }; var move = function ($elem, options) { var mode = null; if (options.css3 && transition.isSupport) { // css3 transition mode = new Css3($elem); } else if (options.js) { // js animation mode = new Js($elem); } else { // no animation mode = new Silent($elem); } return { to: $.proxy(mode.to, mode), //改变指针this指向mode. x: $.proxy(mode.x, mode), y: $.proxy(mode.y, mode) }; }; $.fn.extend({ move: function (option,x,y) { return this.each(function () { var $this = $(this), mode = $this.data('move'), options = $.extend({}, defaults, typeof option === 'object' && option); if (!mode) { // first time $this.data('move', mode = move($this, options)); } if (typeof mode[option] === 'function') { mode[option](x, y); } }); } }); })(jQuery);
slider.js
(function ($) { 'use strict'; function Slider($elem, options) { this.$elem = $elem; this.options = options; this.$items = this.$elem.find('.slider-item'); this.$indicators = this.$elem.find('.slider-indicator'); this.$controls = this.$elem.find('.slider-control'); this.itemNum = this.$items.length; this.curIndex = this._getCorrectIndex(this.options.activeIndex); this._init(); } Slider.DEFAULTS = { css3: false, js: false, animation: 'fade', // slide activeIndex: 0, interval: 0 }; Slider.prototype._init = function() { var self = this; this.$elem.trigger('slider-show',[this.curIndex,this.$items[this.curIndex]]); // init show this.$indicators.removeClass('slider-indicator-active'); this.$indicators.eq(this.curIndex).addClass('slider-indicator-active'); // to if (this.options.animation === 'slide') { this.$elem.addClass('slider-slide'); this.$items.eq(this.curIndex).css('left', 0); // send message this.$items.on('move moved', function (e) { var index = self.$items.index(this); if (e.type === 'move') { if (index === self.curIndex) { self.$elem.trigger('slider-hide', [index, this]); } else { self.$elem.trigger('slider-show', [index, this]); } } else { // moved if (index === self.curIndex) { // 指定的 self.$elem.trigger('slider-shown', [index, this]); } else { self.$elem.trigger('slider-hidden', [index, this]); } } }); // move init this.$items.move(this.options); this.to = this._slide; this.itemWidth = this.$items.eq(0).width(); this.transitionClass = this.$items.eq(0).hasClass('transition') ? 'transition' : ''; } else { // fade this.$elem.addClass('slider-fade'); this.$items.eq(this.curIndex).show(); // send message this.$items.on('show shown hide hidden', function (e) { self.$elem.trigger('slider-' + e.type, [self.$items.index(this), this]); }); // showHide init this.$items.showHide(this.options); this.to = this._fade; } // bind event this.$elem .hover(function () { self.$controls.show(); }, function () { self.$controls.hide(); }) .on('click', '.slider-control-left', function () { self.to(self._getCorrectIndex(self.curIndex - 1), 1); }) .on('click', '.slider-control-right', function () { self.to(self._getCorrectIndex(self.curIndex + 1), -1); }) .on('click', '.slider-indicator', function () { self.to(self._getCorrectIndex(self.$indicators.index(this))); }); // auto if (this.options.interval && !isNaN(Number(this.options.interval))) { this.$elem.hover($.proxy(this.pause, this), $.proxy(this.auto, this)); this.auto(); } }; Slider.prototype._getCorrectIndex = function(index) { if (isNaN(Number(index))) return 0; if (index < 0) return this.itemNum - 1; if (index > this.itemNum - 1) return 0; return index; }; Slider.prototype._activateIndicators = function(index) { this.$indicators.eq(this.curIndex).removeClass('slider-indicator-active'); this.$indicators.eq(index).addClass('slider-indicator-active'); }; Slider.prototype._fade = function(index) { if (this.curIndex === index) return; this.$items.eq(this.curIndex).showHide('hide'); this.$items.eq(index).showHide('show'); this._activateIndicators(index); this.curIndex = index; }; Slider.prototype._slide = function(index, direction) { if (this.curIndex === index) return; var self = this; // 确定滑入滑出的方向 if (!direction) { // click indicators if (this.curIndex < index) { direction = -1; } else if (this.curIndex > index) { direction = 1; } } // 设置指定滑入幻灯片的初始位置 this.$items.eq(index).removeClass(this.transitionClass).css('left', -1 * direction * this.itemWidth); // 当前幻灯片滑出可视区域,指定幻灯片滑入可视区域 setTimeout(function () { self.$items.eq(self.curIndex).move('x', direction * self.itemWidth); self.$items.eq(index).addClass(self.transitionClass).move('x', 0); self.curIndex = index; }, 20); // 激活indicator this._activateIndicators(index); }; Slider.prototype.auto = function() { var self = this; this.intervalId = setInterval(function () { self.to(self._getCorrectIndex(self.curIndex + 1), -1); }, this.options.interval); }; Slider.prototype.pause = function() { clearInterval(this.intervalId); }; $.fn.extend({ slider: function (option) { return this.each(function () { var $this = $(this), slider = $this.data('slider'), options = $.extend({}, Slider.DEFAULTS, $this.data(), typeof option === 'object' && option); if (!slider) { // first time $this.data('slider', slider = new Slider($this, options)); } if (typeof slider[option] === 'function') { slider[option](); } }); } }) })(jQuery);
index.js 以下代码是没有优化的,使用时,要使用最后的代码。
(function($) { 'use strict'; //focus-slider var $focusSlider = $('#focus-slider');//id效率最高,.类只用于css样式 /*$focusSlider.on('slider-show slider-shown slider-hide slider-hidden',function (e,i,elem) { console.log(i+':'+e.type); });*/ //暴露过多的全局变量。可以作为$focusSlider的属性进行优化 /*var items = {}; var loadedItemNum = 0; var totalItemNum = $focusSlider.find('.slider-img').length;//获取$focusSlider 下面有几个轮播对象 var loadItem;//已经加载*/ $focusSlider.items = {};//items[index],加载的赋值 loaded,没有加载就不进行操作 $focusSlider.loadedItemNum = 0;//已经加载几张图片 $focusSlider.totalItemNum = $focusSlider.find('.slider-img').length;//获取$focusSlider 下面有几个轮播对象需要加载 $focusSlider.loadItem;//已经加载 //监听轮播对象显示之前的操作 /* $focusSlider.on('slider-show',$focusSlider.loadItem = function(e,index,elem){ //只加载一次 if ($focusSlider.items[index]!=='loaded') { //按需加载 //找到elem下面的 .slider-img var $img = $(elem).find('.slider-img'); //图片加载 loadImg($img.data('src'),function(url){ $img.attr('src',url); $focusSlider.items[index] = 'loaded'; console.log(index + ':loaded'); if ($focusSlider.loadedItemNum === $focusSlider.totalItemNum) { //清除事件 $focusSlider.off('slider-show',$focusSlider.loadItem); } },function(url){ console.log('从' + url + '加载失败'); //显示备用图片 $img.attr('src','../img/focus-slider/placeholder.png'); }); } });*/ //把以上代码拆分成功能单一的自定义事件如下: $focusSlider.on('slider-show',function(e,index,elem){ //只加载一次 if ($focusSlider.items[index]!=='loaded') { $focusSlider.trigger('slider-loadItem',[index,elem]);//没有加载过的可以开始加载 } }); //开始加载 $focusSlider.on('slider-loadItem',function(e,index,elem){ //按需加载 //找到elem下面的 .slider-img var $img = $(elem).find('.slider-img'); //图片加载 loadImg($img.data('src'),function(url){ $img.attr('src',url); $focusSlider.items[index] = 'loaded'; console.log(index + ':loaded'); if ($focusSlider.loadedItemNum === $focusSlider.totalItemNum) { //全部加载完毕 $focusSlider.trigger('slider-itemsLoaded'); } },function(url){ console.log('从' + url + '加载失败'); //显示备用图片 $img.attr('src','../img/focus-slider/placeholder.png'); }); }) //清除事件 $focusSlider.on('slider-itemsLoaded',function(e){ console.log('itemsLoaded'); $focusSlider.off('slider-show',$focusSlider.loadItem); }) //图片加载成功,失败时处理。容错率高了。 function loadImg(url,imgLoaded,imgFailed){ var image = new Image(); //加载失败,图片加载失败触发,属于javascript事件 image.onerror = function(){ if (typeof imgFailed === 'function') imgFailed(url); } //加载成功,图片加载成功触发,属于javascript事件 image.onload = function(){ if (typeof imgLoaded === 'function') imgLoaded(url); } image.src = url; //手动延迟一秒,模拟从其他服务器获取图片 //setTimeout(function(){ //image.src = url; //},1000); } $focusSlider.slider({ css3: true, js: false, animation: 'fade', // fade slide activeIndex: 0, interval: 0 }); //todays-slider var $todaysSlider = $('#todays-slider'); $todaysSlider.items = {}; $todaysSlider.loadedItemNum = 0; $todaysSlider.totalItemNum = $todaysSlider.find('.slider-img').length; $todaysSlider.on('slider-show', $todaysSlider.loadItem = function(e, index, elem) { console.log(1); if ($todaysSlider.items[index] !== 'loaded') { $todaysSlider.trigger('slider-loadItem', [index, elem]); } }); $todaysSlider.on('slider-loadItem', function(e, index, elem) { // 按需加载 var $imgs = $(elem).find('.slider-img'); $imgs.each(function (_,el) { // _ 相当占位,不使用该参数。 var $img=$(el); loadImg($img.data('src'), function(url) { $img.attr('src', url); $todaysSlider.items[index] = 'loaded'; $todaysSlider.loadedItemNum++; console.log(index + ': loaded'); if ($todaysSlider.loadedItemNum === $todaysSlider.totalItemNum) { // 全部加载完毕 $todaysSlider.trigger('slider-itemsLoaded'); } }, function(url) { console.log('从' + url + '加载图片失败'); // 多加载一次 // 显示备用图片 $img.attr('src', '../img/focus-slider/placeholder.png'); }); }); }); $todaysSlider.on('slider-itemsLoaded', function(e) { console.log('itemsLoaded'); // 清除事件 $todaysSlider.off('slider-show', $todaysSlider.loadItem); }); function loadImg(url, imgLoaded, imgFailed) { var image = new Image(); image.onerror = function() { if (typeof imgFailed === 'function') imgFailed(url); } image.onload = function() { if (typeof imgLoaded === 'function') imgLoaded(url); }; // image.src=url; setTimeout(function() { image.src = url; }, 1000); } $todaysSlider.slider({ css3: true, js: false, animation: 'slide', // fade slide activeIndex: 0, interval: 0 }); })(jQuery);
优化后的最终版index.js
(function($) { 'use strict'; // foucs-slider var slider={}; slider.$focusSlider=$('#focus-slider'); slider.loadImg=function(url, imgLoaded, imgFailed) { var image = new Image(); image.onerror = function() { if (typeof imgFailed === 'function') imgFailed(url); } image.onload = function() { if (typeof imgLoaded === 'function') imgLoaded(url); }; image.src=url; // setTimeout(function() { // image.src = url; // }, 1000); }; //懒加载 slider.lazyLoad = function($elem) { $elem.items = {}; $elem.loadedItemNum = 0; $elem.totalItemNum = $elem.find('.slider-img').length; $elem.on('slider-show', $elem.loadItem = function(e, index, elem) { console.log(1); if ($elem.items[index] !== 'loaded') { $elem.trigger('slider-loadItem', [index, elem]); } }); $elem.on('slider-loadItem', function(e, index, elem) { // 按需加载 var $imgs = $(elem).find('.slider-img'); $imgs.each(function(_, el) { // _ 相当占位,不使用该参数。 var $img = $(el); slider.loadImg($img.data('src'), function(url) { $img.attr('src', url); $elem.items[index] = 'loaded'; $elem.loadedItemNum++; console.log(index + ': loaded'); if ($elem.loadedItemNum === $elem.totalItemNum) { // 全部加载完毕 $elem.trigger('slider-itemsLoaded'); } }, function(url) { console.log('从' + url + '加载图片失败'); // 多加载一次 // 显示备用图片 $img.attr('src', '../img/focus-slider/placeholder.png'); }); }); }); $elem.on('slider-itemsLoaded', function(e) { console.log('itemsLoaded'); // 清除事件 $elem.off('slider-show', $elem.loadItem); }); } slider.lazyLoad(slider.$focusSlider); slider.$focusSlider.slider({ css3: true, js: false, animation: 'fade', // fade slide activeIndex: 0, interval: 0 }); // todays-slider slider.$todaysSlider = $('#todays-slider'); slider.lazyLoad(slider.$todaysSlider); slider.$todaysSlider.slider({ css3: true, js: false, animation: 'fade', // fade slide activeIndex: 0, interval: 0 }); })(jQuery);