最近剛好重新看了一下前端的內容,在做網頁banner的時候實現輪播圖上遇到了問題。
本着不想用輪子的心態,在網上查了半天很多實現有點問題(逼死強迫症
於是對着淘寶和京東首頁兩種不同的輪播圖做了一個實現。
循環式(淘寶首頁)
大概思路:
-
為了實現無限循環,在第一張圖前放一個最后一張圖,最后一張圖后面放一個第一張圖
<li><img src="image3.jpg" alt=""></li> <li><img src="image1.jpg" alt=""></li> <li><img src="image2.jpg" alt=""></li> <li><img src="image3.jpg" alt=""></li> <li><img src="image1.jpg" alt=""></li>
-
不用left來做,用translate3d來做,雖然不知道為什么,但是確實很絲滑,而且也解決了快速點擊的時候多事件沖突的問題
-
邏輯鏈如下:
- 鼠標移入的時候,頁面不輪播;移出后開始輪播
- click左右或者鼠標移入下面小圓圈的時候進行跳轉
- 其余見JS注釋
總體布局
DIV | position |
---|---|
.banner 總的div | 相對布局 |
.screen 放圖像的 | 相對布局 |
.dot 圓點 | 絕對布局 |
.arr 箭頭 | 絕對布局 |
- HTML
<!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>Document</title>
<link rel="stylesheet" type="text/css" href="lbt_tb.css" />
<script src="lbt_tb.js"> </script>
</head>
<body>
<div class="banner" id ="banner">
<div class="screen">
<ul id="img" style="transform: translate3d(-700px,0px,0px) ;transition-duration: 0.3s;">
<li><img src="image3.jpg" alt=""></li>
<li><img src="image1.jpg" alt=""></li>
<li><img src="image2.jpg" alt=""></li>
<li><img src="image3.jpg" alt=""></li>
<li><img src="image1.jpg" alt=""></li>
</ul>
</div>
<div class="dot">
<ul id="circles">
<li class="active"></li>
<li></li>
<li></li>
</ul>
</div>
<div class="leftArr" id="left">
<</div> <div class="rightArr" id="right">>
</div>
</div>
</body>
</html>
- JS
window.onload = function () {
var step = -700; //步距
var banner = document.getElementById("banner");
var img = document.getElementById("img")
var circles = document.getElementById("circles").children;
var left = document.getElementById("left");
var right = document.getElementById("right");
var index = 0;
var len = circles.length;
var run;
function turn() {
run = setInterval(function () {
circles[index].removeAttribute("class");
index++;
move(index);
console.log(index);
if (index == len) {
index = 0;
}
circles[index].className = "active";
console.log("change" + index);
}, 4000);
}
//啟動時,調用函數
turn();
// 設置鼠標移入時暫停
banner.onmouseenter = function () {
//當鼠標移入容器中,停止輪播
clearInterval(run);
}
banner.onmouseleave = function () {
//當鼠標移出容器時,繼續開始輪播
turn();
}
// 設置鼠標移到圓點上時候的事件
for (let i = 0; i < len; i++) {
circles[i].onmouseenter = (function (i) {
return function () {
circles[index].removeAttribute("class");
index = i;
move(index);
circles[index].className = "active";
console.log("mouse circle change" + index);
}
})(i);
}
// 設置左箭頭事件
left.onclick = function () {
circles[index].removeAttribute("class");
index--;
move(index);
if (index < 0) {
index = len - 1;
}
circles[index].className = "active";
console.log("left change" + index);
}
// 設置右箭頭事件
right.onclick = function () {
circles[index].removeAttribute("class");
index++;
move(index);
if (index == len) {
index = 0;
}
circles[index].className = "active";
console.log("right change" + index);
}
function move(index) {
img.style.transform = 'translate3d(' + (index + 1) * step + 'px,0px,0px)';
img.style.transitionDuration = '0.3s';
// 為了實現無限輪播的一些處理
if (index < 0) {
setTimeout(function () {
img.style.transitionDuration = '0s';
img.style.transform = 'translate3d(' + len * step + 'px,0px,0px)';
}, 300);
}
if (index == len) {
setTimeout(function () {
img.style.transitionDuration = '0s';
img.style.transform = 'translate3d(' + -700 + 'px,0px,0px)';
}, 300);
}
}
}
- CSS
* {
margin: 0px;
padding: 0px;
border: 0px;
}
div.banner {
width: 700px;
height: 420px;
padding: 7px;
position: relative;
border: solid 1px gray;
}
.screen {
width: 700px;
height: 420px;
overflow: hidden;
position: relative;
}
.screen ul {
position: absolute;
top: 0px;
width: 3500px;
}
.screen li {
width: 700px;
height: 420px;
float: left;
overflow: hidden;
}
img {
height: 100%;
width: 100%;
z-index: 0;
}
.leftArr {
cursor: pointer;
width: 30px;
height: 50px;
position: absolute;
top: 150px;
left: 20px;
background-color: rgba(0, 0, 0, 0.5);
color: #fff;
text-align: center;
line-height: 50px;
}
.rightArr {
cursor: pointer;
width: 30px;
height: 50px;
position: absolute;
top: 150px;
right: 20px;
background-color: rgba(0, 0, 0, 0.5);
color: #fff;
text-align: center;
line-height: 50px;
}
.icon-dot {
display: inline-block;
width: 40px;
height: 40px;
background-color: #333;
background-clip: content-box;
padding: 8px;
border-radius: 50%;
border: 8px solid #333;
z-index: 1000;
}
.dot {
cursor: pointer;
position: absolute;
width: 93px;
height: 30px;
bottom: 7px;
right: 300px;
background-color: rgba(0, 0, 0, 0.3);
border-radius: 15px;
}
.dot ul li {
list-style: none;
width: 15px;
height: 15px;
border-radius: 100%;
background-color: #fff;
float: left;
margin: 7px 8px;
}
.dot ul li.active {
transition: 0.5s;
background-color: #fff;
background-clip: content-box;
padding: 2px;
width: 11px;
height: 11px;
border-radius: 50%;
border: 2px solid #Fff;
margin: 5px 6px;
}
跳躍式(京東首頁)
實現起來比第一種簡單很多,頁面布局稍有變化,不多贅述。
大概思路:
- 每個圖片和小圓點所在的li設置一個.active的類,表示當前展示的
- 頁面加載完以后用一個定時器開始輪播,如果鼠標移入的話停止輪播
- 點擊箭頭和移入圓點的話會切換頁面
- 切換邏輯為:將當前index所指的li的.active去掉,找到目標index,將目標圖片和圓點設為active
注:暫不實現漸變效果,具體實現見后續3
- HTML
<body>
<div class="banner" id="banner">
<div class="screen">
<ul id="imgs">
<li class="active"><img id="slide1" src="image1.jpg" alt=""></li>
<li><img id="slide2" src="image2.jpg" alt=""></li>
<li><img id="slide3" src="image3.jpg" alt=""></li>
</ul>
</div>
<div class="dot">
<ul id="circles">
<li class="active"></li>
<li></li>
<li></li>
</ul>
</div>
<div class="leftArr" id="left">
<</div> <div class="rightArr" id="right">>
</div>
</div>
</body>
- JS
window.onload = function () {
var banner = document.getElementById("banner");
var imgs = document.getElementById("imgs").children;
var circles = document.getElementById("circles").children;
var left = document.getElementById("left");
var right = document.getElementById("right");
var index = 0;
var len = imgs.length;
var run;
console.log('onload');
function turn() {
run = setInterval(function () {
imgs[index].removeAttribute("class");
circles[index].removeAttribute("class");
index++;
console.log(index);
if (index == len) {
index = 0;
}
imgs[index].className = "active";
circles[index].className = "active";
console.log("change" + index);
}, 2000);
}
//啟動時,調用函數
turn();
//設置鼠標移入移出容器事件
banner.onmouseenter = function () {
//當鼠標移入容器中,停止輪播
clearInterval(run);
}
banner.onmouseleave = function () {
//當鼠標移出容器時,繼續開始輪播
turn();
}
// 設置鼠標移到圓點上時候的事件
for (let i = 0; i < len; i++) {
circles[i].onmouseenter = (function (i) {
return function () {
imgs[index].removeAttribute("class");
circles[index].removeAttribute("class");
index = i;
imgs[index].className = "active";
circles[index].className = "active";
console.log("mouse circle change" + index);
}
})(i);
}
// 設置左箭頭事件
left.onclick = function () {
imgs[index].removeAttribute("class");
circles[index].removeAttribute("class");
index--;
if(index<0){
index = len-1;
}
imgs[index].className = "active";
circles[index].className = "active";
console.log("left change" + index);
}
// 設置右箭頭事件
right.onclick = function () {
imgs[index].removeAttribute("class");
circles[index].removeAttribute("class");
index++;
if(index==len){
index = 0;
}
imgs[index].className = "active";
circles[index].className = "active";
console.log("right change" + index);
}
}
- CSS布局
* {
margin: 0px;
padding: 0px;
border: 0px;
}
div.banner {
width: 700px;
height: 420px;
padding: 7px;
position: relative;
border: solid 1px gray;
}
.screen {
width: 700px;
height: 420px;
overflow: hidden;
position: relative;
}
.screen ul {
position: absolute;
top: 0px;
left: 0px;
width: 700px;
}
.screen li {
width: 700px;
height: 420px;
float: left;
display: none;
overflow: hidden;
}
.screen li.active {
display: block;
}
img {
height: 100%;
width: 100%;
z-index: 0;
}
.leftArr {
cursor: pointer;
width: 30px;
height: 50px;
position: absolute;
top: 150px;
left: 20px;
background-color: rgba(0, 0, 0, 0.5);
color: #fff;
text-align: center;
line-height: 50px;
}
.rightArr {
cursor: pointer;
width: 30px;
height: 50px;
position: absolute;
top: 150px;
right: 20px;
background-color: rgba(0, 0, 0, 0.5);
color: #fff;
text-align: center;
line-height: 50px;
}
.icon-dot {
display: inline-block;
width: 40px;
height: 40px;
background-color: #333;
background-clip: content-box;
padding: 8px;
border-radius: 50%;
border: 8px solid #333;
z-index: 1000;
}
.dot {
cursor: pointer;
position: absolute;
width: 93px;
height: 30px;
bottom: 7px;
right: 300px;
background-color: rgba(0, 0, 0, 0.3);
border-radius: 15px;
}
.dot ul li {
list-style: none;
width: 15px;
height: 15px;
border-radius: 100%;
background-color: #fff;
float: left;
margin: 7px 8px;
}
.dot ul li.active {
transition: 0.5s;
background-color: #fff;
background-clip: content-box;
padding: 2px;
width: 11px;
height: 11px;
border-radius: 50%;
border: 2px solid #Fff;
margin: 5px 6px;
}
三、在跳躍式的基礎上實現漸變
用JQ的fadeIn()
實現,注意使用前要用加個stop()
,不然在快速點幾下會錯亂
-
把CSS中的該段刪去
.screen li.active { display: block; }
-
把對HTML中的
<body>
進行修改<li class="active"><img id="slide1" src="image1.jpg" alt=""></li>
改為
<li style="display: block;"><img id="slide1" src="image1.jpg" alt=""></li>
來使得一開始第一張圖片會顯示
-
引用JQ,分別替換JS中的
imgs[index].removeAttribute("class"); imgs[index].className = "active";
為
$("#imgs").find("li").hide(); $("#imgs").find("li").eq(index).stop().fadeIn("1000");
-
最終效果如圖
-
HTML+JS代碼
<!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>Document</title>
<link rel="stylesheet" type="text/css" href="lbt_jd.css" />
<script src="jquery-3.4.1.min.js"></script>
<script>
window.onload = function () {
var banner = document.getElementById("banner");
var imgs = document.getElementById("imgs").children;
var circles = document.getElementById("circles").children;
var left = document.getElementById("left");
var right = document.getElementById("right");
var index = 0;
var len = imgs.length;
var run;
console.log('onload');
function turn() {
run = setInterval(function () {
var imgs = $("#imgs");
imgs.find("li").hide();
circles[index].removeAttribute("class");
index++;
console.log(index);
if (index == len) {
index = 0;
}
imgs.find("li").eq(index).stop().fadeIn("1000");
circles[index].className = "active";
console.log("change" + index);
}, 2000);
}
//啟動時,調用函數
turn();
//設置鼠標移入移出容器事件
banner.onmouseenter = function () {
//當鼠標移入容器中,停止輪播
clearInterval(run);
}
banner.onmouseleave = function () {
//當鼠標移出容器時,繼續開始輪播
turn();
}
// 設置鼠標移到圓點上時候的事件
for (let i = 0; i < len; i++) {
circles[i].onmouseenter = (function (i) {
return function () {
$("#imgs").find("li").hide();
circles[index].removeAttribute("class");
index = i;
$("#imgs").find("li").eq(index).stop().fadeIn("1000");
circles[index].className = "active";
console.log("mouse circle change" + index);
}
})(i);
}
// 設置左箭頭事件
left.onclick = function () {
$("#imgs").find("li").hide();
circles[index].removeAttribute("class");
index--;
if (index < 0) {
index = len - 1;
}
$("#imgs").find("li").eq(index).stop().fadeIn("1000");
circles[index].className = "active";
console.log("left change" + index);
}
// 設置右箭頭事件
right.onclick = function () {
$("#imgs").find("li").hide();
circles[index].removeAttribute("class");
index++;
if (index == len) {
index = 0;
}
$("#imgs").find("li").eq(index).stop().fadeIn("1000");
circles[index].className = "active";
console.log("right change" + index);
}
}</script>
</head>
<body>
<div class="banner" id="banner">
<div class="screen">
<ul id="imgs">
<li style="display: block;"><img id="slide1" src="image1.jpg" alt=""></li>
<li><img id="slide2" src="image2.jpg" alt=""></li>
<li><img id="slide3" src="image3.jpg" alt=""></li>
</ul>
</div>
<div class="dot">
<ul id="circles">
<li class="active"></li>
<li></li>
<li></li>
</ul>
</div>
<div class="leftArr" id="left">
<</div> <div class="rightArr" id="right">>
</div>
</div>
</body>
</html>