移动端触屏滑动的效果其实就是图片轮播,在PC的页面上很好实现,绑定click和mouseover等事件来完成。但是在移动设备上,要实现这种轮播的效果,就需要用到核心的touch事件。处理touch事件能跟踪到屏幕滑动的每根手指。
以下是四种touch事件
touchstart: //手指放到屏幕上时触发
touchmove: //手指在屏幕上滑动式触发
touchend: //手指离开屏幕时触发
touchcancel: //系统取消touch事件的时候触发,这个比较少用
每个触摸事件被触发后,会生成一个event对象,event对象里额外包括以下三个触摸列表
touches: //当前屏幕上所有手指的列表
targetTouches: //当前dom元素上手指的列表,尽量使用这个代替touches
changedTouches: //涉及当前事件的手指的列表,尽量使用这个代替touches
废话不多说,直接上代码。
1 <!DOCTYPE html> 2 <html> 3 <head lang="en"> 4 <meta charset="UTF-8"> 5 <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=2.0, minimum-scale=1.0,user-scalable=no"> 6 <meta name="format-detection" content="email=no,telephone=no"/> 7 <title></title> 8 <style> 9 *{margin: 0;padding: 0} 10 ul li{list-style: none;} 11 /*清除浮动*/ 12 .fix { 13 zoom: 1; 14 } 15 .fix:after { 16 display: block; 17 content: 'clear'; 18 clear: both; 19 line-height: 0; 20 font-size: 0; 21 visibility: hidden; 22 } 23 #container_box{ 24 100%; 25 overflow: hidden; 26 } 27 .box{ 400%;height: 200px;overflow: hidden;} 28 .box li{ 29 float: left; 30 25%; 31 height: 200px; 32 line-height: 200px; 33 font-size: 40px; 34 text-align: center; 35 cursor: pointer; 36 } 37 </style> 38 </head> 39 <body> 40 <div id="container_box"> 41 <ul id="container" class="box fix"> 42 <li style="background: #f7bac5">swipe</li> 43 </ul> 44 </div> 45 46 <script> 47 var initSwipe = { 48 init:function(id){ 49 initSwipe.addLoadEvent(initSwipe.mathFun(id)); 50 }, 51 mathFun:function(id){ 52 initSwipe.swipe(initSwipe.getById(id)); 53 }, 54 //可以加载多个onload事件 55 addLoadEvent:function(fn){ 56 var oldonload=window.onload; 57 if(typeof window.onload!='function'){ 58 window.onload=fn; 59 }else{ 60 window.onload=function(){ 61 oldonload(); 62 fn(); 63 } 64 } 65 }, 66 //解决 getElementsByClassName 兼容问题 67 getByClass:function(className,obj){// obj : 父元素 68 var obj = obj || document; 69 if (obj.getElementsByClassName) // 支持 getElementsByClassName 方法的使用 70 { 71 return obj.getElementsByClassName(className); 72 } 73 /* 不支持 getElementsByClassName 方法的使用 */ 74 var result = [];// 保存所有查找到的元素的数组结构 75 // 查找出 obj 对象后代所有元素 76 var tags = obj.getElementsByTagName("*"); 77 for (var i = 0, len = tags.length; i < len; i++) {// 遍历每个元素 78 var classNames = tags[i].className.split(" ");// 获取到当前遍历元素所使用的所有类名 79 for (var j = 0, l = classNames.length; j < l; j++) {// 遍历当前元素的每个类名 80 if ( classNames[j] === className ) { // 说明当前遍历到的元素使用过要查找的类名 81 result.push(tags[i]); 82 break; 83 } 84 } 85 } 86 // 返回结果集 87 return result; 88 }, 89 getById:function(idSelect,obj){ 90 var obj = obj || document; 91 return obj.getElementById(idSelect); 92 }, 93 getByTagName:function(TagName,obj){ 94 var obj = obj || document; 95 return obj.getElementsByTagName(TagName); 96 }, 97 // 事件绑定 98 bindHandler:function(elem, type, handler) { 99 if (window.addEventListener) {// 标准浏览器 100 return elem.addEventListener(type, handler, false); 101 } else if (window.attachEvent) {// IE浏览器 102 return elem.attachEvent("on" + type, handler); 103 } 104 }, 105 // 事件解除 106 removeHandler:function(elem, type, handler) { 107 if (window.removeEventListener) {// 标准浏览器108 109 elem.removeEventListener(type, handler, false);110 111 } else if (window.detachEvent) {// IE浏览器112 113 elem.detachEvent("on" + type, handler);114 115 } 116 }, 117 //滑动事件 118 swipe:function(container){ 119 var container = container; 120 var index = 1; 121 var flag = false;//判断是否发生滑动事件 122 var swipe_distance = 30;//移动30px之后才认为swipe事件 123 var swipe_time = 500;//swipe最大经历时间 124 var point_start,point_end, time_start,time_end; 125 // 判断是PC还是移动设备 126 var startEvt,moveEvt,endEvt; 127 if('ontouchstart' in window){ 128 startEvt = 'touchstart'; 129 moveEvt = 'touchmove'; 130 endEvt = 'touchend'; 131 }else{ 132 startEvt = 'mousedown'; 133 moveEvt = 'mousemove'; 134 endEvt = 'mouseup'; 135 } 136 // 获取touch的点(兼容mouse事件) 137 var getTouchPos = function(e){ 138 var touches = e.touches; 139 if(touches && touches[0]){ 140 return{ 141 x: touches[0].clientX, 142 y: touches[0].clientY 143 }; 144 } 145 return {x: e.clientX,y: e.clientY}; 146 }; 147 // 计算两点之间的距离 148 var getDist = function(p1,p2){ 149 if(!p1 || !p2){return 0;} 150 return Math.sqrt((p1.x-p2.x)*(p1.x-p2.x)+(p1.y-p2.y)*(p1.y-p2.y)); 151 }; 152 // 计算两点之间的角度 153 var getAngle = function(p1,p2){ 154 var r = Math.atan2(p2.y-p1.y,p2.x-p1.x);//这里获取的是幅度 155 var a = r*180 / Math.PI;//幅度转角度 156 return a; 157 }; 158 // 获取swipe方向 159 var getSwipeDirection = function(p2,p1){ 160 var dx = p2.x-p1.x; 161 var dy = -p2.y+p1.y; 162 var angle = Math.atan2(dy,dx)*180/Math.PI; 163 if(angle < 45 && angle > -45){return 'right';} 164 if(angle >= 45 && angle < 135){return 'top';} 165 if(angle >= 135 || angle < -135){return 'left';} 166 if(angle >= -135 && angle <= -45){return 'bottom';} 167 }; 168 // 记录touchstart开始时间和位置 169 var startEvtHandler = function(e){ 170 flag = false; 171 var date = new Date(); 172 var touches = e.touches; 173 if(!touches || touches.length==1){//touches为空,代表鼠标点击 174 point_start = getTouchPos(e); 175 time_start = date.getTime(); 176 } 177 }; 178 // touchmove 179 var moveEvtHandler = function(e){ 180 point_end = getTouchPos(e); 181 flag = true; 182 return false; 183 }; 184 // touchend的touches和targetTouch没有对象,只有changeTouches才有 185 var endEvtHandler = function(e){ 186 var date = new Date(); 187 time_end = date.getTime(); 188 //距离和时间都符合 189 if(getDist(point_start,point_end)>swipe_distance && time_end-time_start<swipe_time){ 190 var dir = getSwipeDirection(point_end,point_start); 191 var objHtml = initSwipe.getByTagName('li',container)[0]; 192 if(dir=='left' && flag == true){//向左滑 193 objHtml.innerHTML = 'swipe left'; 194 }else if(dir=='right' && flag == true){//向右滑 195 objHtml.innerHTML = 'swipe right'; 196 }else if(dir=='top' && flag == true){//向上滑 197 objHtml.innerHTML = 'swipe top'; 198 }else if(dir=='bottom' && flag == true){//向下滑 199 objHtml.innerHTML = 'swipe bottom'; 200 } 201 } 202 flag = false; 203 }; 204 initSwipe.bindHandler(container,startEvt,startEvtHandler); 205 initSwipe.bindHandler(container,moveEvt,moveEvtHandler); 206 initSwipe.bindHandler(container,endEvt,endEvtHandler); 207 } 208 }; 209 initSwipe.init('container'); 210 </script> 211 </body> 212 </html>
本人测试兼容IE8+,
container