原生js圖片輪播效果實現(xiàn)代碼
現(xiàn)在很多javascript的插件都可以實現(xiàn)圖片輪播的功能,這篇文章,主要是通過這個domo來解析javascript圖片輪播的原理。
老規(guī)矩,先上代碼。至于代碼中的圖片,隨便找三張即可,最核心的還是理解其思想。
html:
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title>滾動圖</title> <link rel="stylesheet" type="text/css" href="css/scroll.css"/> </head> <body> <div id="wrapper"> <div id="box"> <img src="img/banner0.png"/> <img src="img/banner1.png"/> <img src="img/banner2.png"/> </div> <div id="pointer"> <span class="active"></span> <span></span> <span></span> </div> </div> <script src="js/scroll.js" type="text/javascript" charset="utf-8"></script> </body> </html>
css:
*{
margin: 0;
padding: 0;
}
#wrapper{
position: relative;
width: 1200px;
margin: 50px auto;
overflow: hidden;
}
#pointer{
clear: both;
position: absolute;
right: 500px;
bottom: 15px;
width: 180px;
height: 2px;
}
#pointer span{
display: block;
box-sizing: border-box;
float: left;
width: 50px;
height: 1.5px;
margin-right: 10px;
border-radius: .5px;
background: #fff;
opacity: .5;
-webkit-opacity: .5;
-moz-opacity: .5;
filter:alpha(opacity=50);
}
#pointer .active{
opacity: .8;
-webkit-opacity: .8;
-moz-opacity: .8;
filter:alpha(opacity=80);
}
#box{
position: relative;
width: 3600px;
clear: both;
}
img{
display: block;
float: left;
width: 1200px;
height: 337px;
}
javascript:
window.onload = function(){
//獲取裝圖片的盒子
var box = document.getElementById('box');
//獲取裝頁碼的盒子
var pointer = document.getElementById('pointer');
//獲取盒子中的所有圖片
var imglist = box.getElementsByTagName('img')
//獲取盒子中的所有頁碼
var pointerList = pointer.getElementsByTagName('span');
//圖片的寬度,正負(fù)用于左右的循環(huán)
var n = -1200;
//增加一倍的圖片用于循環(huán)
box.innerHTML = box.innerHTML+box.innerHTML;
//設(shè)置盒子的寬
box.style.width = imglist[0].offsetWidth*imglist.length+"px";
var timer = null;
timer = setInterval(function(){
scroll(box,n,pointerList);
},3000);
box.onmouseover = function(){
clearInterval(timer);
}
pointer.onmouseover = function(){
clearInterval(timer);
}
box.onmouseout = function(){
timer = setInterval(function (){
// console.log(new Date());
scroll(box,n,pointerList);
},3000);
}
//設(shè)置頁碼的點擊事件
for(var i=0;i<pointerList.length;i++){
pointerList[i].index=i;//設(shè)置一個參數(shù),用下面調(diào)用某個頁碼
//如果不設(shè)置參數(shù),在調(diào)用頁碼的時候會直接調(diào)用最后一個,因為我們使用了循環(huán)
pointerList[i].onclick=function (){
for(var j=0;j<pointerList.length;j++){
pointerList[j].className='';//清空激活的class
}
move(box,n*(this.index));//移動圖片
this.className='active';//激活點擊的頁碼
}
}
}
/**
* 循環(huán)滾動函數(shù)
* @param {Object} box
* @param {Object} n
*/
function scroll(box,n,page){
//判斷是否到達(dá)臨界點,即box的中間部分
if(box.offsetLeft<=-box.offsetWidth/2){
box.style.left = "0px";//重新從頭開始
console.log('0');
}
if(box.offsetLeft%n!=0){
//因為在我們切換瀏覽器標(biāo)簽頁或者切換去其他軟件界面的時候,
//會影響到setInterval,有時候setInterval會增加好幾秒,在這里我們必須加一個判斷
//只有當(dāng)它走完了一個整個的圖片寬度時,我們才進(jìn)行下一次滾動。
}
else{
pageScroll(box,n,page);
move(box,n+box.offsetLeft);
}
}
/**
* 滾動頁碼函數(shù)
* @param {Object} box
* @param {Object} n
* @param {Object} page
*/
function pageScroll(box,n,page){
//直接通過圖片盒子的定位判斷頁碼值,但是此時的頁碼值是滾動之前的,所以后面的值要+1使用
var index = Math.abs(box.offsetLeft/n);
console.log(index);
for(var i=0;i<page.length;i++){
page[i].className='';
}
//判斷是不是最后一頁,是最后一頁的話+1要變成0;
if(index<page.length-1){
page[index+1].className='active';
}
else{
page[0].className='active';
}
}
/**
* 變速移動
* @param {Object} ele
* @param {Object} target
*/
function move(ele,target){
clearInterval(ele.timer);
console.log(new Date());
ele.timer = setInterval(function () {
var step = (target-ele.offsetLeft)/10;
step = step>0?Math.ceil(step):Math.floor(step);
if(target==ele.offsetLeft){
console.log(new Date());
clearInterval(ele.timer);
}
else{
ele.style.left = ele.offsetLeft + step + "px";
}
},30);
}
html和css部分依舊比較簡單,直接跳過。javascript部分的代碼注釋寫的也比較詳細(xì),下面主要講解邏輯部分。
圖片滾動的原理是利用setInterval函數(shù)進(jìn)行背景圖片的不斷循環(huán)。為了避免圖片循環(huán)的過程中出現(xiàn)間斷,首先是在javascript中進(jìn)行圖片的復(fù)制(增加一倍),然后當(dāng)?shù)竭_(dá)臨界點時,瞬間將圖片移動到初始的位置,然后開始下一輪循環(huán)。
在這個domo中,主要包含四個函數(shù):
1、外層控制間隔時間的函數(shù)。這個比較容易理解,通過setInterval函數(shù)每隔幾秒循環(huán)執(zhí)行一次圖片滾動的函數(shù)。
2、中間層滾動函數(shù)。判斷圖片盒子是否到達(dá)臨界點,判斷當(dāng)前狀態(tài)是否符合進(jìn)入下一次滾動(這個條件主要是為了防止切換界面對setInterval函數(shù)的影響,具體原因在最后)。
3、中間層頁碼滾動函數(shù)。基本沒有難點,主要是理解頁碼為什么+1即可。
4、圖片滾動函數(shù)。這個在之前寫過的一篇文章有詳細(xì)講解,不再贅述,參考:http://chabaoo.cn/article/95211.htm
最后,一點關(guān)于setInterval底層機(jī)制的擴(kuò)展。
我們內(nèi)層函數(shù)的執(zhí)行事件正常情況下為1-2s(測試過),而外層的循環(huán)需要3s才進(jìn)行一次,正常的情況是沒有問題的。但是,當(dāng)你切換界面的時候,瀏覽器就會對setInterval函數(shù)產(chǎn)生影響,此時執(zhí)行事件的事件就會超過3面,在沒移動結(jié)束的情況下開啟另一個定時器進(jìn)行下一次圖片滾動,所以就會發(fā)生錯亂。
javascript是單線程的,當(dāng)你使用setInterval函數(shù)的時候并不是真正暫停,而是先掛起這個事件,繼續(xù)執(zhí)行下面的事件,而當(dāng)這個事件要執(zhí)行時,如果瀏覽器當(dāng)前沒有任務(wù),那么它會立馬執(zhí)行,但是如果瀏覽器有任務(wù),那么就會有一定的延遲,這也是為什么切換界面會對setInterval函數(shù)的時間產(chǎn)生影響。
(關(guān)于setInterval函數(shù)的理解如有錯誤,歡迎指正!如果大家想要深入理解,也可以去一些大神的博客看一下setInterval函數(shù)的文章)
精彩專題分享:jQuery圖片輪播 JavaScript圖片輪播 Bootstrap圖片輪播
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
拖動table標(biāo)題實現(xiàn)改變td的大小(css+js代碼)
拖動列寬的表格table標(biāo)題同時改變td的大小,本文將以實例演示為大家呈現(xiàn),感興趣的朋友可以參考下哈,希望對你學(xué)習(xí)js或者css有所幫助2013-04-04
原生JS實現(xiàn)圖片輪播 JS實現(xiàn)小廣告插件
這篇文章主要為大家詳細(xì)介紹了原生JS實現(xiàn)圖片輪播、小廣告插件,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下2021-09-09

