demo : http://dsj-666.gitee.io/swiper
源码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<link rel="stylesheet" href="index.css">
<script src="index.js"></script>
</head>
<body>
<div id="banner">
</div>
</body>
<script>
var banner = document.getElementById('banner');
createBanner(banner, [{
imgUrl: 'images/1.jfif',
link: 'https://www.baidu.com/'
}, {
imgUrl: 'images/2.jfif',
link: 'https://www.baidu.com/'
}, {
imgUrl: 'images/3.jfif',
link: 'https://www.baidu.com/'
}, {
imgUrl: 'images/4.jfif',
link: 'https://www.baidu.com/'
}])
</script>
</html>
#banner {
width: 600px;
height: 300px;
outline: 10px solid;
margin: 0 auto;
}
/**
* @param {*} area 轮播图区域
* @param {*} options 轮播图的数组
* @param {*} IsArrow 是否需要左右箭头
*/
function createBanner(area, options, IsArrow) {
var imgArea = document.createElement('div'); //图片区域的div
var numberArea = document.createElement('div'); //圆点区域的div
var curIndex = 0; //当前的是第几长图片
var changeTimer = null; //该变curIndex计时器
area.style.position = 'relative';
var control = true;
//1.创建区域来显示图片
initImgs();
//2,创建圆点
initNumbers();
//3,设置圆圈,图片状态
setStatus();
//4,自动播放
autoChange();
//5,是否需要左右箭头
if (IsArrow === undefined || IsArrow === true) {
arrow(); //不传参数默认是true
}
/**
* 下面是局部函数,为了避免用户不知道,用了同名的函数 将这个插件里面里的函数覆盖
* 避免全局变量污染
*/
function initImgs() {
imgArea.style.width = '100%';
imgArea.style.height = '100%';
imgArea.style.display = 'flex';
//imgArea.style.overflow = 'hidden';
imgArea.style.overflow = 'hidden';
//初始化图片
options.forEach(function(item) {
//let a = document.createElement('a');
// a.style.display = 'inline-block';
// a.href = item.link;
let img = document.createElement('img')
img.src = item.imgUrl;
//a.appendChild(img);
img.style.width = '100%';
img.style.height = '100%';
img.style.marginLeft = '0';
img.style.transition = "1s ease";
img.addEventListener('click', function() {
location.href = item.link;
})
imgArea.appendChild(img);
})
// var last = imgArea.children[0].cloneNode(true);
// last.style.transition = '0s';
// imgArea.appendChild(last);
imgArea.addEventListener('mouseenter', function() {
clearInterval(changeTimer);
changeTimer = null;
})
imgArea.addEventListener('mouseleave', function() {
autoChange();
})
area.appendChild(imgArea);
area.appendChild(numberArea);
}
function initNumbers() {
// numberArea.style.width = '100%';
// numberArea.style.height = '100%';
numberArea.style.textAlign = 'center';
numberArea.style.marginTop = '-6%';
let len = options.length;
for (let i = 0; i < len; i++) {
const span = document.createElement('span');
span.style.display = 'inline-block';
span.style.width = "3%";
span.style.height = getWidth(3); //让不同大小的容器也不影响圆点的大小
span.style.marginLeft = '3%';
span.style.borderRadius = '50%';
span.style.background = "gray";
span.style.cursor = 'pointer';
span.addEventListener('click', function() {
clearInterval(changeTimer);
changeTimer = null;
curIndex = i; //用let的作用就在这
setStatus();
})
numberArea.appendChild(span);
}
}
function getWidth(index) {
if (area.currentStyle) { //兼容IE
return parseInt(window.currentStyle(area, null).width) * index / 100 + 'px';
} else {
//兼容其他
return parseInt(window.getComputedStyle(area, false).width) * index / 100 + 'px';
}
}
function setStatus() {
if (control) {
//1.设置圆圈的背景颜色
control = false;
for (let i = 0; i < options.length; i++) {
if (i === curIndex) {
numberArea.children[i].style.background = '#FFF';
numberArea.children[i].style.border = "2px solid #00aadc"
} else {
numberArea.children[i].style.background = 'gray';
numberArea.children[i].style.border = '';
}
}
//2,图片状态
//var start = parseInt(imgArea.children[0].style.marginLeft); //默认是auto所以开始设置为0
var end = curIndex * -100;
imgArea.children[0].style.marginLeft = end + '%';
// var duration = 1000; //轮播玩一张图片时间
// var distance = end - start;
// var speed = distance / duration;
// if (timer) {
// clearInterval(timer);
// }
// timer = setInterval(function() { //缓动效果
// start += speed * 20;
// imgArea.children[0].style.marginLeft = start + '%';
// if (Math.abs(end - start) < 1) {
// imgArea.children[0].style.marginLeft = end + '%';
// clearInterval(timer);
// }
// }, 20);
control = true;
}
}
/**
* 自动切换轮播图
*/
function autoChange() {
changeTimer = setInterval(function() {
if (curIndex === options.length - 1) {
move(false);
curIndex = 0;
} else {
move(true);
curIndex++;
}
setStatus();
}, 2000)
}
function move(flag) {
if (!flag) {
for (var i = 0; i < options.length; i++) {
area.children[0].children[i].style.transition = '';
}
} else {
for (var i = 0; i < options.length; i++) {
area.children[0].children[i].style.transition = '1s ease';
}
}
}
function arrow() {
//1,产生箭头,并设置状态
var l_arrow = document.createElement('div');
l_arrow.innerHTML = '<';
arrow_status(l_arrow);
var r_arrow = document.createElement('div');
r_arrow.innerHTML = '>';
r_arrow.style.right = '0';
arrow_status(r_arrow);
//2,箭头的点击事件
l_arrow.addEventListener('click', function() {
clearInterval(changeTimer);
changeTimer = null;
if (curIndex == 0) {
move(false);
curIndex = options.length - 1;
} else {
move(true);
curIndex--;
}
setStatus();
})
r_arrow.addEventListener('click', function() {
clearInterval(changeTimer);
changeTimer = null;
if (curIndex == options.length - 1) {
move(false);
curIndex = 0;
} else {
move(true);
curIndex++;
}
setStatus();
})
function arrow_status(item) {
//设置俩个箭头的公共样式
item.style.width = '8%';
item.style.height = getWidth(8);
item.style.background = 'rgba(0,0,0,.3)';
item.style.top = '50%';
item.style.borderRadius = '50%';
item.style.border = '2px solid #fff'
item.style.transform = 'translateY(-50%)';
item.style.position = 'absolute';
item.style.color = '#FFF';
item.style.textAlign = 'center';
item.style.lineHeight = getWidth(8);
item.style.fontSize = '25px';
item.style.cursor = 'pointer';
item.style.display = 'none';
item.style.userSelect = 'none';
area.addEventListener('mouseenter', function() {
item.style.display = 'block';
});
area.addEventListener('mouseleave', function() {
item.style.display = 'none';
});
item.addEventListener('mouseenter', function() {
item.style.border = '2px solid #00aadc'
item.style.color = '#00aadc';
})
item.addEventListener('mouseleave', function() {
item.style.border = '2px solid #fff'
item.style.color = '#FFF';
})
area.appendChild(item);
}
}
}
案列要点:
- 既然是轮播图插件,尽可能多的去简化用户使用,更多的由js完成,可以看出html,css模块的内容是非常少的
- createBanner()函数 参数一:需要使用改插件的DOM对象 参数二:图片相对路径+地址 参数三: 是否需要左右箭头,默认需要
- 按百分比布局,在使用这个插件的时候,可以随便设置放置轮播图插件的宽高,不影响布局
- 主要围绕curIndex参数来实现,要值得注意的是,在手动点击左右箭头按钮还是下面的小点的时候,都要停止计时器,否则自己点击的事件和自动轮播的事件同时进行,就会乱,点击完了 再重启计时器
- 为了不让轮播图到在最后一张到第一张出现后退效果,在最后一张的时候,停止清空过度效果,闪现到第一张图片的位置,再开启过度效果