本篇博文實現的是一個原生js寫的輪播圖,含括了大部分輪播圖的功能,有的同學問前端框架那么多干嘛要用原生寫,傷神費腦.
個人感覺程序世界里的框架,是讓大牛更牛,小白也永遠只是小白.框架是死的,需求是不斷更新的,我們只有知道了原理,才能不斷利用原理滿足別人的需求,總會有那么個時候框架滿足不了的.所以,不要依賴框架,為了不讓自己一直做小白,最近一直在用原生js寫bootstrap的一些效果.(剛入坑不久,大佬輕噴)
由於輪播圖在網站中的應用比比皆是,在此分享和總結之前原生js實現的輪播圖.
注:文中代碼只是片段,具體可在CSDN下載或者去我的GitHub倉庫下載,記得給star哦,3q~
首先我們需要了解輪播圖一些基本原理,和輪播圖的一些功能:
輪播圖原理:
並排的一組照片,放在父盒子的框里,父盒子overflow設置隱藏;
- 輪播圖必須注意的一個問題:
第一張跳最后一張或者相反的時候,怎么解決中間的空窗期(不處理會很難看)?
輪播圖功能:
自輪播:用於展示,固定時間間隔自動跳下一張;
兩翼輪播:用於用戶點擊兩側的箭頭,跳向前后一張;
點選:通常位於下方用於標識當前所在張,也有點擊跳向對應張的功能
無外乎,大多數輪播圖也就這些功能,先看一下效果圖:
接下來我們就一一實現這些功能
1 ) HTML視圖:
注意container里的img,需要在首尾各多加一張,為了首位跳轉的時候沒有空窗:
原理:以末尾跳向第一張為例,
當我們在最后一張時候點擊下一張,視圖顯示最后一張的我們額外加的一張,也就是第一張的替代,此時顯示的是第一張圖片,確實不是真正位置的第一張,同時,在跳向這假第一張的時候將開始位置重置.
大家可以結合后面js代碼理解.
<div id="container">
<!-- 圖片 -->
<div id="list" style="left: -800px;">
<img src="img/5.jpg" alt="1" />
<img src="img/1.jpg" alt="1" />
<img src="img/2.jpg" alt="2" />
<img src="img/3.jpg" alt="3" />
<img src="img/4.jpg" alt="4" />
<img src="img/5.jpg" alt="5" />
<img src="img/1.jpg" alt="5" />
</div>
<div id="buttons"> <!-- 點選小圈圈 -->
<span index="1" class="on"></span>
<span index="2"></span>
<span index="3"></span>
<span index="4"></span>
<span index="5"></span>
</div>
<!-- 上一張下一張 -->
<a href="javascript:;" id="prev" class="arrow"><</a>
<a href="javascript:;" id="next" class="arrow">></a>
</div>
2 ) CSS樣式:(片段)
幫助大家理解下面樣式,在此概述一下:
- 點選圓圈,當前張所對應的圈高亮顯示;
- 兩翼,鼠標滑過才顯示,鼠標放上去高亮顯示;
- 層級問題:除了父級的展示框盒子,上面是圖片層,最上面是兩翼和點選圈.
#container { position: relative; width: 800px; height: 600px; border: 3px solid black; overflow: hidden; }
#buttons{ position: absolute; left: 320px; bottom: 25px; width: 160px; height: 10px; z-index: 6; }
#buttons span{ float: left; margin: 0 10px; border: 1px solid #fff; width: 10px; height: 10px; border-radius: 50%; background: #333; cursor: pointer; }
.arrow{ position: absolute; top: 260px; z-index: 2; width: 40px; height: 50px; font-size: 40px; font-weight: bold; line-height: 48px; text-align: center; color:#fff; background-color: rgb(0,0,0,0.3); cursor: pointer; }
#container:hover .arrow { display: block; }
3 ) js代碼:
- 關於動畫,只有跳下一張上一張,無外乎就方向不一樣,我們封裝到一個函數,方向傳參控制;
- 定時器的間隔控制函數,停止輪播函數;
- 小圓點的實現比較麻煩,我們循環給每個圓加事件,通過屬性標簽index獲取用戶點擊的標簽,用的是getAttribute();
- 還有具體地看代碼注釋吧,注釋的比較詳細.
function animate(offset) {
//獲取的是style.left,是相對左邊獲取距離,所以第一張圖后style.left都為負值,
//且style.left獲取的是字符串,需要用parseInt()取整轉化為數字。
var newLeft = parseInt(list.style.left) + offset;
list.style.left = newLeft + 'px';
//無限滾動判斷
if (newLeft > -600) {
list.style.left = -3000 + 'px';
}
if (newLeft < -3000) {
list.style.left = -600 + 'px';
}
}
function buttonsShow() {
// //將之前的小圓點的樣式清除
for (var i = 0; i < buttons.length; i++) {
if (buttons[i].className == "on") {
buttons[i].className = "";
}
}
//數組從0開始,故index需要減1
buttons[index - 1].className = "on";
console.log(index-1);
}
for (var i = 0; i < buttons.length; i++) {
buttons[i].onclick = function () {
/* 這里獲得鼠標移動到小圓點的位置,用this把index綁定到對象buttons[i]上,去谷歌this的用法 */
/* 由於這里的index是自定義屬性,需要用到getAttribute()這個DOM2級方法,去獲取自定義index的屬性*/
var clickIndex = parseInt(this.getAttribute('index'));//this指向當前點擊圈
var offset = 600 * (index - clickIndex); //這個index是當前圖片停留時的index
index = clickIndex; //存放鼠標點擊后的位置,用於小圓點的正常顯示
animate(offset);
buttonsShow();
}
}
container.onmouseover = stop;
container.onmouseout = play;
play(); //初始化