1. // index.html
    2. ...
    3. <div class="demo">
    4. <ul id="bannerWrap">
    5. <li class="bannerItem"><a href=""><img src="" /></a></li>
    6. <li class="bannerItem"><a href=""><img src="" /></a></li>
    7. <li class="bannerItem"><a href=""><img src="" /></a></li>
    8. <li class="bannerItem"><a href=""><img src="" /></a></li>
    9. </ul>
    10. <ul id="pointsWrap">
    11. <li class="pointItem on"></li>
    12. <li class="pointItem"></li>
    13. <li class="pointItem"></li>
    14. <li class="pointItem"></li>
    15. </ul>
    16. </div>
    17. ...
    1. // banner.css
    2. //轮播图 ul 建议采用flex布局
    3. #bannerWrap {
    4. width: 100%;
    5. display: flex;
    6. }
    7. .bannerItem{
    8. flex: 0 0 100%;
    9. align-items: center;
    10. }
    1. // main.js中使用
    2. BSlider({
    3. checkTime: 3000,
    4. transTime: 600,
    5. bannerWrap: '#bannerWrap',
    6. childBanner: '.bannerItem',
    7. points: '.pointItem',
    8. pointOn: 'on'
    9. });
    10. // BSlider.js
    11. /* @name: BSlider.js
    12. * @version: 1.1.0
    13. * @author: liyang
    14. * @Created: 2016-12-27
    15. * @Edited: 2017-03-07
    16. * @description 轮播图组件
    17. * @params: {
    18. * checkTime: [Number], //轮播图切换频率,单位ms,选填,默认值 3000
    19. * transTime: [Number], //轮播图过渡频率,单位ms,选填,默认值 500
    20. * bannerWrap: [String], //轮播图父容器选择器(例如'#bannerWrap'),必填
    21. * childBanner: [String], //轮播图子图选择器,必填
    22. * points: [String], //焦点圆钮选择器,必填
    23. * pointOn: [String] //焦点激活类名,必填
    24. * }
    25. */
    26. (function(name, def) {
    27. //检测上下文环境是否为AMD或者CMD
    28. var hasDefine = typeof define === 'function',
    29. hasExports = typeof module !== 'undefined' && module.exports;
    30. if (hasDefine) {
    31. // AMD环境或CMD环境
    32. define(def);
    33. } else if (hasExports) {
    34. //定义为普通Node模块
    35. module.exports = def();
    36. } else {
    37. //将模块的执行结果挂在window变量中,在浏览器中this指向window对象
    38. this[name] = def();
    39. }
    40. })('BSlider', function() {
    41. var BSlider = function(o) {
    42. var defaults = {
    43. checkTime: 2000,
    44. transTime: 500,
    45. bannerWrap: '',
    46. childBanner: '',
    47. points: '',
    48. pointOn: ''
    49. };
    50. for (key in o) {
    51. defaults[key] = o[key];
    52. }
    53. var bw = defaults.bannerWrap,
    54. cb = defaults.childBanner,
    55. pts = defaults.points,
    56. ptOn = defaults.pointOn;
    57. //bannerWrap, childBanner, points, pointOn必填
    58. if (o === null || typeof o !== 'object' || !bw || !cb || !pts || !ptOn) {
    59. throw new Error('【 bannerWrap, childBanner, points, pointOn are necessary 】');
    60. return false;
    61. }
    62. //轮播图父容器
    63. var bannerBox = document.querySelector(defaults.bannerWrap),
    64. width = bannerBox.offsetWidth,
    65. //轮播图 子图
    66. banners = bannerBox.querySelectorAll(defaults.childBanner),
    67. //圆点 && 计时器
    68. timer,
    69. count = 1,
    70. checkTime = defaults.checkTime,
    71. transTime = defaults.transTime,
    72. points = document.querySelectorAll(defaults.points),
    73. //触摸点
    74. moveX = 0,
    75. startX = 0,
    76. distanceX = 0,
    77. //判断是否滑动
    78. isMove = false;
    79. // 轮播对象
    80. var Bn = {
    81. doInit: function() {
    82. Bn.initBannerImg();
    83. Bn.setTimer();
    84. Bn.TOUCH();
    85. },
    86. //混合器
    87. _extend: function(targetObj, utilObj) {
    88. for (key in utilObj) {
    89. targetObj[key] = utilObj[key];
    90. }
    91. },
    92. //初始化轮播图数量
    93. initBannerImg: function() {
    94. Bn.setTranslateX(bannerBox, -count * width);
    95. var cloneFirst = banners[0].cloneNode(true);
    96. var cloneLast = banners[banners.length - 1].cloneNode(true);
    97. //复制第一张放末尾,复制最后一张放最前
    98. bannerBox.appendChild(cloneFirst);
    99. bannerBox.insertBefore(cloneLast, bannerBox.childNodes[0]);
    100. Bn.setTranslateX(bannerBox, -count * width);
    101. },
    102. //监听过渡结束
    103. transitionEnd: function(el, cb) {
    104. if (el && typeof el === 'object') {
    105. el.addEventListener('webkitTransitionEnd', function() {
    106. cb && cb();
    107. })
    108. el.addEventListener('transitionEnd', function() {
    109. cb && cb();
    110. })
    111. }
    112. //解除禁止页面上下滚动
    113. document.querySelector('body').removeEventListener('touchstart', Bn.forbidScroll);
    114. },
    115. //添加过渡
    116. addTransition: function(el) {
    117. var cs1 = {
    118. webkitTransition: "all " + transTime + "ms",
    119. transition: "all " + transTime + "ms"
    120. }
    121. Bn._extend(el.style, cs1);
    122. },
    123. //删除过渡
    124. removeTransition: function(el) {
    125. var cs2 = {
    126. webkitTransition: "none",
    127. transition: "none"
    128. }
    129. Bn._extend(el.style, cs2);
    130. },
    131. //设置位移
    132. setTranslateX: function(el, w) {
    133. var cs3 = {
    134. webkitTransform: "translateX(" + w + "px)",
    135. transform: "translateX(" + w + "px)"
    136. }
    137. Bn._extend(el.style, cs3);
    138. },
    139. //初始化定时器
    140. setTimer: function() {
    141. timer = setInterval(function() {
    142. count++;
    143. //开始轮播
    144. Bn.addTransition(bannerBox);
    145. Bn.setTranslateX(bannerBox, -count * width);
    146. Bn.setPoint();
    147. }, checkTime);
    148. Bn.transitionEnd(bannerBox, function() {
    149. //设置当前点
    150. Bn.getCount();
    151. //动画结束刷新状态
    152. Bn.removeTransition(bannerBox);
    153. Bn.setTranslateX(bannerBox, -count * width);
    154. });
    155. },
    156. //限制当前 count
    157. getCount: function() {
    158. if (count >= points.length + 1) {
    159. count = 1;
    160. } else if (count <= 0) {
    161. count = points.length;
    162. }
    163. },
    164. hasClass: function(el, cls) {
    165. cls = cls || '';
    166. if (cls.replace(/\s/g, '').length == 0)
    167. return false; //当cls没有参数时,返回false
    168. return new RegExp(' ' + cls + ' ').test(' ' + el.className + ' ');
    169. },
    170. addClass: function(el, cls) {
    171. if (!Bn.hasClass(el, cls)) {
    172. el.className = el.className == ''
    173. ? cls
    174. : el.className + ' ' + cls;
    175. }
    176. },
    177. removeClass: function(el, cls) {
    178. if (Bn.hasClass(el, cls)) {
    179. var newClass = ' ' + el.className.replace(/[\t\r\n]/g, '') + ' ';
    180. while (newClass.indexOf(' ' + cls + ' ') >= 0) {
    181. newClass = newClass.replace(' ' + cls + ' ', ' ');
    182. }
    183. el.className = newClass.replace(/^\s+|\s+$/g, '');
    184. }
    185. },
    186. //点动
    187. setPoint: function() {
    188. var arrs = [];
    189. for (var i = 0; i < points.length; i++) {
    190. arrs.push(points[i]);
    191. }
    192. arrs.forEach(function(v, i) {
    193. Bn.removeClass(v, 'on');
    194. // v.className = "";
    195. })
    196. Bn.getCount();
    197. Bn.addClass(arrs[count - 1], defaults.pointOn);
    198. // arrs[count - 1].className = defaults.pointOn;
    199. },
    200. //触摸焦点图时禁止页面滚动
    201. forbidScroll: function(evt) {
    202. evt.preventDefault();
    203. },
    204. TOUCH: function() {
    205. bannerBox.addEventListener('touchstart', function(e) {
    206. //禁止页面滑动
    207. document.querySelector('body').addEventListener('touchstart', Bn.forbidScroll);
    208. //清除定时器
    209. clearInterval(timer);
    210. startX = e.touches[0].clientX;
    211. });
    212. bannerBox.addEventListener('touchmove', function(e) {
    213. isMove = true;
    214. moveX = e.touches[0].clientX;
    215. distanceX = moveX - startX;
    216. Bn.removeTransition(bannerBox);
    217. Bn.setTranslateX(bannerBox, -count * width + distanceX);
    218. });
    219. bannerBox.addEventListener('touchend', function(e) {
    220. //滑动距离超过十分之一屏即切换,否则回弹
    221. if (Math.abs(distanceX) > (width / 10) && isMove) {
    222. if (distanceX > 0) {
    223. count--;
    224. } else {
    225. count++;
    226. }
    227. }
    228. Bn.addTransition(bannerBox);
    229. Bn.setTranslateX(bannerBox, -count * width);
    230. //重置参数
    231. startX = moveX = distanceX = 0;
    232. isMove = false;
    233. //重置状态
    234. clearInterval(timer);
    235. Bn.setTimer();
    236. Bn.setPoint();
    237. });
    238. }
    239. }
    240. Bn.doInit();
    241. }
    242. return BSlider;
    243. })