1. 程式人生 > 實用技巧 >馮-諾依曼體系結構

馮-諾依曼體系結構

技術標籤:JavaScriptjscssajaxsetInterval

左右版輪播圖

js實現左右輪播圖,實現效果有自動播放、點選分頁器切換和點選左右按鈕切換等。

原理

將一些圖片在一行中平鋪,然後計算偏移量再利用定時器實現定時輪播。

實現效果

  • 多張圖片自動輪換展示,對應分頁器小圓點高亮顯示

  • 圖片無縫切換(圖片列表中第一張和最後一張圖片一致)

  • 滑鼠滑入/滑出停止/開啟圖片輪換展示

  • 點選前進/後退按鈕檢視當前圖片前一張/後一張圖片

  • 點選分頁器小圓點切換對應圖片

實現思路

  • 獲取操作物件

  • 請求資料

  • 渲染資料

  • 封裝函式autoMove,將其傳入定時器,實現圖片自動輪換展示

  • 封裝函式changeFocus,實現圖片對應分頁器小圓點高亮顯示

  • 繫結滑鼠滑入/滑出事件,滑入(滑出)清除(開啟)定時器

  • 給左右按鈕繫結點選事件

index.js

//獲取外層的視窗
let outer = document.getElementById('outer');
//獲取圖片的容器
let wrapper = document.getElementById('wrapper');
//獲取焦點的容器
let list = document.getElementById('list');
let data = null; //用來接收請求的資料
let timer = null;//用來接收定時器的返回值

//1.資料請求
function getData(url)
{ let xhr = new XMLHttpRequest; xhr.open('get', url, false); xhr.onreadystatechange = function () { if (xhr.readyState === 4 && /^2\d{2}/.test(xhr.status)) { data = JSON.parse(xhr.responseText); } } xhr.send(); // console.log(data); } getData('banner.json'); //2.資料渲染 function
renderHtml() { let wrapperItems = ''; let listItems = ''; data.forEach((item, index) => { wrapperItems += `<li><img src="${item.img}" alt=""></li>`; listItems += `<li></li>`; }); //再複製第一張圖片放到末尾(讓第一張和最後一張一樣) wrapperItems += `<li><img src="${data[0].img}" alt=""></li>`; // console.log(wrapperItems); //把動態生成的圖片插入到頁面 wrapper.innerHTML = wrapperItems; //把動態生成的焦點插入到頁面 list.innerHTML = listItems; } renderHtml(); //儲存當前展示圖片的索引 let step = 0; /*autoMove 圖片索引自增(切換下一張圖片) 如果當前索引是最後一張圖片,將圖片列表ul(絕對定位)的left值設定為0,將索引值設為1 一定時間內修改圖片列表ul(絕對定位)的left值為 負的每張圖片長度*索引(動畫) */ function autoMove(index) { step++; //如果當前的函式執行的時候index沒有值,那就什麼都不做,如果index有值,那就把index的值賦值給step即可 typeof index === 'undefined' ? null : step = index; //如果當前的step大於等於5,說明當前已經運動到最後一張圖片了,這時候需要馬上把wrapper的left值改為0(因為第一張和最後一張一樣,所以看不見這個變化) //這時候再把step改為1,正常展示第二張 if (step >= data.length+1) { wrapper.style.left = 0; step = 1; } changeFocus(); utils.animate(wrapper, { left: -step * 800 }, 500); } timer = setInterval(autoMove, 2000); //使用者滑鼠滑上outer輪播停止,滑鼠離開輪播繼續 outer.onmouseover = function () { clearInterval(timer); } outer.onmouseout = function () { timer = setInterval(autoMove, 2000); } let tips = document.querySelectorAll('#list li');//querySelectorAll獲取的元素沒有對映 //實現焦點跟隨 /*changeFocus 如果當前圖片索引與分頁器索引一致則給當前分頁器新增類名active,其他分頁器刪除類名active(迴圈) 如果圖片索引是最後一張圖片,給第一個分頁器新增類名active */ function changeFocus() { //切換焦點的顯示 //迴圈所有的焦點,判斷一下當前的step和哪個焦點的索引相等,和誰相等就給誰加上active類名,其餘的清除active類名 for (let i = 0; i < tips.length; i++) { //tips[i] //每一個焦點 i就是每一個焦點的索引 if (step === i) { tips[i].classList.add('active'); } else { tips[i].classList.remove('active'); } } //如果當前的step是4,說明當前頁面顯示的是最後一張圖片,他和第一張圖片共用一個焦點,這時候讓第一個焦點高亮就可以了 if (step === 4) { tips[0].classList.add('active'); } } //頁面初始化的時候執行一次,為了讓第一張圖片的焦點高亮 changeFocus(); //點選焦點,實現切換對應的圖片 function bindClick() { for (let i = 0; i < tips.length; i++) { tips[i].onclick = function () { /* //方式一 //因為autoMove內部有step++,所以這這裡要減一,這樣就會跟autoMove內部的step++相互抵消 step=i-1; autoMove(); */ //方式二 autoMove(i); } } } bindClick(); //點選小耳朵實現圖片切換 right.onclick = function () { autoMove(); } //左按鈕點選事件 left.onclick = function () { step -= 2;//圖片索引減2(autoMove中索引 會自增) if (step == -2) { //如果索引等於-2,說明現在要顯示倒數第二張圖片,需要將left設定為負的總圖片長度(負的單張圖片長度*data.length) wrapper.style.left = -data.length * 800 + 'px'; step = data.length - 2;//索引設定為data.length-2 } autoMove(); }

utils.js

let utils = (function(){
    function linear(t,b,c,d){
        return c/d*t+b;
    }
 // move
    function animate(curEle,target,duration,callBack){
        let begin = {};
        let change = {};
        for(var key in target){
            begin[key] = parseFloat(getComputedStyle(curEle)[key]);
            change[key] =  target[key] - begin[key];
        }
        let interval = 0;
        let timer = setInterval(function(){
            interval+=20;
            for(var key in target){
                let cur = linear(interval,begin[key],change[key],duration);
                // console.log(interval,begin[key],change[key],duration)
                curEle.style[key] = cur+'px';
            }
            if(interval>=duration){
                clearInterval(timer);
                typeof callBack === 'function'? callBack():null
            }
        },20)
    };
    function debounce(fn,wait){
        let timer;
        return function(){
            clearInterval(timer);
            timer = setTimeout(()=>{
                fn.call(this);
            },wait)
        }
    }
    return {animate,debounce}
})()

index.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Document</title>
  <link rel="stylesheet" href="index.css">
</head>
<body>
  <div id="outer">
    <!-- 圖片 -->
    <ul id="wrapper">
      <li><img src="img/banner1.jpg" alt=""></li>
      <!-- <li><img src="img/banner2.jpg" alt=""></li>
      <li><img src="img/banner3.jpg" alt=""></li> -->
    </ul>
    <!-- 焦點 -->
    <ul id="list">
      <li class="active"></li>
      <li></li>
      <li></li>
      <li></li>
    </ul>
    <!--  -->
    <a href="javascript:;" id="left"> < </a>
    <a href="javascript:;" id="right"> > </a>
  </div>

  <script src="https://ajax.aspnetcdn.com/ajax/jquery/jquery-1.11.3.min.js"></script>
  <script src="utils.js"></script>
  <script src="index.js"></script>
</body>
</html>

index.css

*{
    margin: 0;
    padding: 0;
}
#outer{
    width: 800px;
    height: 300px;
    margin: 100px auto;
    border: 1px solid red;
    overflow: hidden;
    position: relative;
    cursor: pointer;
}
#wrapper{
    display: flex;
    /* width: 2400px; */
    height: 300px;
    background: orangered;
    position: absolute;
    left: 0;
    list-style: none;
}
#wrapper li{
    width: 800px;
    height: 300px;
}
#wrapper li img{
    display: block;
    width: 100%;
    height: 100%;
}
/* -------------------------- */
#list{
    /* width: 250px; */
    height: 30px;
    /* background: palevioletred; */
    position: absolute;
    left: 50%;
    list-style: none;
    display: flex;
    /* justify-content: space-around; */
    align-items: center;
    transform: translate(-50%,0);
    bottom: 10px;
}
#list li{
    width: 25px;
    height: 25px;
    margin: 0 5px;
    border-radius: 50%;
    background: rgba(0, 0, 0, .5);
}
#list li.active{
    background: orangered;
}
/* ------------------------------ */
#outer a{
    width: 30px;
    height: 50px;
    text-align: center;
    line-height: 50px;
    background: rgba(0,0,0,.5);
    position: absolute;
    top: 50%;
    text-decoration: none;
    color: #fff;
}
#left{
    left: 0;
}
#right{
    right: 0;
}

banner.json

[
  {
    "id": 1,
    "img": "img/banner1.jpg",
    "desc": "廣闊的就業推薦機會",
    "link": "http://www.zhufengpeixun.cn/"
  },
  {
    "id": 2,
    "img": "img/banner2.jpg",
    "desc": "夢想起飛從選擇珠峰培訓開始",
    "link": "http://www.zhufengpeixun.cn/"
  },
  {
    "id": 3,
    "img": "img/banner3.jpg",
    "desc": "把握未來,掌握先機",
    "link": "http://www.zhufengpeixun.cn/"
  },
  {
    "id": 4,
    "img": "img/banner4.jpg",
    "desc": "先學習,後交費,學不好,不收費",
    "link": "http://www.zhufengpeixun.cn/"
  }
]