<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Vue轮播图</title>
<style>
* {
padding: 0;
margin: 0;
touch-action: pan-y;
}
ul {
position: relative;
overflow: hidden;
}
ul li {
list-style: none;
position: absolute;
right: -600px;
opacity: 0;
-webkit-transition: all .8s ease-in-out;
-moz-transition: all .8s ease-in-out;
-o-transition: all .8s ease-in-out;
}
ol li {
list-style: none;
}
#map {
width: 600px;
height: 300px;
position: relative;
}
ul,
ul li,
ul li img {
width: 100%;
height: 100%;
}
.img-active {
top: 0;
left: 0;
opacity: 1;
}
.slider-nav {
position: absolute;
text-align: center;
width: 100%;
bottom: 20px;
}
.slider-nav li {
background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAQAAAAngNWGAAAAAmJLR0QA/4ePzL8AAAAJcEhZcwAAAEgAAABIAEbJaz4AAAAJdnBBZwAAABQAAAAUAKM7KtEAAADISURBVCjPjdI9T8JQFIDhp6cKTRz4mFpmFwz+//9hgk4YJ0sMJiKSlKVxwFo/Au07ndz7TPeeRFvI5SYytcrW2lrdXCbfLHfjyu/2HpTHMf3ic7cG/jYwk3pt4dy1U02FzREWFs41tfMRooPBQoRC1gkzs1B0MsjDuBcch2EvOIz27c8XDr3cIbz3gm/R/GVH61CqOlnlOdSWnXCpTrFzYXqGrTw227NxaXKCPbmngbzYGf3byL07q+OY/DgOhcJIhspWqWy/4xO4VSw4B3jzAwAAACV0RVh0ZGF0ZTpjcmVhdGUAMjAxNS0wOS0zMFQxNjowMTo1NyswODowMCbyI8YAAAAldEVYdGRhdGU6bW9kaWZ5ADIwMTUtMDktMzBUMTY6MDE6NTcrMDg6MDBXr5t6AAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAABJRU5ErkJggg==) no-repeat;
width: 14px;
height: 14px;
border-radius: 11px;
display: inline-block;
padding: 2px;
overflow: hidden;
margin-left: 10px;
cursor: pointer;
font-size: 0px;
line-height: 0px;
}
.slider-nav li.slider-active {
/* background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAQAAAAngNWGAAAAAmJLR0QA/4ePzL8AAAAJcEhZcwAAAEgAAABIAEbJaz4AAAAJdnBBZwAAABQAAAAUAKM7KtEAAAFdSURBVCjPfZK/TsJQFIe/cxNoY40KDLZuJg4WjXHAmOoTyOTkm+hL6LOoizG6C4uDgwiDJk4UBkERSGu114Eo+Kf9ppPcL+ck9/cTxihsbHKYxAS80KJF/PUooEeDTRGLnwyoa3+kKQARcdnA8jjOtnPv8+/z7dxx1gOLkrgi3xvFZSmjT8xyXibWaS67e0EP7nVdEMChlNE3M8Vp/tDor/Ui4RpfoViFU/M/DZanT0xgFaVwMD128iRQzntgsqBwYD8rSR7CfhawFXOwbZHCtgXMKQwoGGliwQAMNf77JD7iUWwhPIVpYjcCQkUPrgZpYnUIPCt8OHrTiZrmMARaCp+gwnknSTzvVCCgqYipwW5w1/9Pa/R3A6BGrEA3eYhkvXfW0b+OXnQ3XyPhQTe/2iOssAgeB8bWVMGIdeetOjwMKwCP3GotE8V1cNOKOxmywsFhFhMIeMHHH8fxCfqkeQDbcjvwAAAAJXRFWHRkYXRlOmNyZWF0ZQAyMDE1LTA5LTMwVDE2OjAxOjU3KzA4OjAwJvIjxgAAACV0RVh0ZGF0ZTptb2RpZnkAMjAxNS0wOS0zMFQxNjowMTo1NyswODowMFevm3oAAAAZdEVYdFNvZnR3YXJlAEFkb2JlIEltYWdlUmVhZHlxyWU8AAAAAElFTkSuQmCC) no-repeat; */
background-color: #009688;
}
</style>
</head>
<body>
<div id="app">
<div id="map">
<ul>
<li v-for="(item,index) in images" :class="[index==Iindex ? active1:'']">
<a href="www.baidu.com" style="display: inline-block">
<img v-bind:src="item" />
</a>
</li>
</ul>
<ol class="slider-nav">
<li v-for="(item,index) in images" :class="[index==Iindex? active2 :'']"
v-on:mouseenter='sliderMove' v-on:mouseleave='sliderOut' :data-id='index'></li>
</ol>
</div>
</div>
<script src="js/vue.min.js"></script>
<script src="js/touchUtil.js"></script>
<script>
var app = new Vue({
el: '#map',
data: {
images: ["images/01.jpg", "images/02.jpg", "images/03.jpg", "images/01.jpg", "images/03.jpg"],
// Zindex: 1,
Iindex: 0,
isMove: false,
active1: 'img-active',
active2: 'slider-active'
},
created: function () {
var that = this;
setInterval(function () {
var length = that.images.length;
if (!that.isMove) {
if (that.Iindex == length - 1) {
that.Iindex = 0;
} else {
that.Iindex = parseInt(that.Iindex) + 1;
}
}
}, 3000);
},
mounted:function(){
var that=this;
function up() {
//console.log("上");
}
function down() {
//console.log("下");
}
function right() {
console.log("右滑...");
console.log(that.Iindex);
if(that.Iindex==that.images.length-1){
that.Iindex = 0;
}else{
that.Iindex = parseInt(that.Iindex) +1;
}
}
function left() {
console.log("左滑...");
console.log(that.Iindex);
if(that.Iindex==0){
that.Iindex = 0;
}else{
that.Iindex = parseInt(that.Iindex)-1;
}
}
EventUtil.listenTouchDirection(document, true, up, right, down, left)
},
methods: {
sliderMove: function (obj) {
var nowIndex = obj.target.attributes[0].value;
// console.log(nowIndex);
this.Iindex = nowIndex;
this.isMove = true;
},
sliderOut: function (obj) {
this.isMove = false;
}
}
})
</script>
</body>
</html>
touchUtil.js
var EventUtil = {
addHandler: function (element, type, handler) {
if (element.addEventListener)
element.addEventListener(type, handler, false);
else if (element.attachEvent)
element.attachEvent("on" + type, handler);
else
element["on" + type] = handler;
},
removeHandler: function (element, type, handler) {
if (element.removeEventListener)
element.removeEventListener(type, handler, false);
else if (element.detachEvent)
element.detachEvent("on" + type, handler);
else
element["on" + type] = handler;
},
/**
* 监听触摸的方向
* @param target 要绑定监听的目标元素
* @param isPreventDefault 是否屏蔽掉触摸滑动的默认行为(例如页面的上下滚动,缩放等)
* @param upCallback 向上滑动的监听回调(若不关心,可以不传,或传false)
* @param rightCallback 向右滑动的监听回调(若不关心,可以不传,或传false)
* @param downCallback 向下滑动的监听回调(若不关心,可以不传,或传false)
* @param leftCallback 向左滑动的监听回调(若不关心,可以不传,或传false)
*/
listenTouchDirection: function (target, isPreventDefault, upCallback, rightCallback, downCallback, leftCallback) {
this.addHandler(target, "touchstart", handleTouchEvent);
this.addHandler(target, "touchend", handleTouchEvent);
this.addHandler(target, "touchmove", handleTouchEvent);
var startX;
var startY;
function handleTouchEvent(event) {
switch (event.type) {
case "touchstart":
startX = event.touches[0].pageX;
startY = event.touches[0].pageY;
break;
case "touchend":
var spanX = event.changedTouches[0].pageX - startX;
var spanY = event.changedTouches[0].pageY - startY;
if (Math.abs(spanX) > Math.abs(spanY)) { //认定为水平方向滑动
if (spanX > 30) { //向右
if (rightCallback)
rightCallback();
} else if (spanX < -30) { //向左
if (leftCallback)
leftCallback();
}
} else { //认定为垂直方向滑动
if (spanY > 30) { //向下
if (downCallback)
downCallback();
} else if (spanY < -30) {//向上
if (upCallback)
upCallback();
}
}
break;
case "touchmove":
//阻止默认行为
if (isPreventDefault)
event.preventDefault();
break;
}
}
}
};