多尺寸圖片左右切換功能前端實現


一、需求描述

標題“多尺寸圖片左右切換功能”,概括的不知道是否恰當,具體是需求如下。

  • 一次點擊按鈕,向左或向右移動一個圖片。
  • 切換到盡頭時不顯示按鈕
  • 頁面有三個尺寸

可以一睹為快,看一下最終效果。

二、切圖代碼

1、代碼

html代碼如下:

<!DOCTYPE HTML>
<html>

<head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <title></title>
    <link rel="stylesheet" href="http://static9.pplive.cn/pub/flagment/v_20150114110035/header.min.css" />
    <!--頁面初始化CSS和頁面公用頭部的css-->
    <link rel="stylesheet" href="css/vipgrowth.css">
    <!--新增樣式的css,名稱可根據具體需求修改-->
    <script type="text/javascript" src="http://static9.pplive.cn/vip/201508/center/v_20150901140940/js/jquery-1.9.1.min.js"></script>
    <script>
    window.onresize = function() {
        var winWidth = document.body.clientWidth;
        if (winWidth <= 1230) {
            body.className = "grid-1010";
        } else if (winWidth <= 1410) {
            body.className = "grid-1230";
        } else if (winWidth > 1410) {
            body.className = "grid-1410";
        } else {
            alert("do not know!");
        }
    }
    </script>
</head>

<body id="body">
    <script>
    //初始化狀態顯示樣式判斷,放在body后面
    var winWidth = document.body.clientWidth;
    if (winWidth <= 1230) {
        body.className = "grid-1010";
    } else if (winWidth <= 1410) {
        body.className = "grid-1230";
    } else if (winWidth > 1410) {
        body.className = "grid-1410";
    } else {
        alert("do not know!");
    }
    </script>
    <div class="vg-body">
        <!--任務成長值 開始-->
        <div class="vg_title">
            <p>任務成長值</p>
        </div>
        <div class="vg_task">
            <div class="arrowbtn-left"></div>
            <div class="arrowbtn-right"></div>
            <div class="vg_tasklist">
                <ul class="cf" id="switchPic">
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>開通年費會員</h3>
                            <p>獎勵成長值<span>200</span></p>
                            <a href="javascript:;">已完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;" class="done">已完成</a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_lianxubaoyue.png">
                        <div class="rightinfo">
                            <h3>開通連續包月</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>升級成為SVIP</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>關注微信公眾號</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>任務555555555</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>任務666666666</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                    <li>
                        <img src="images/task_year.png">
                        <div class="rightinfo">
                            <h3>任務7777777</h3>
                            <p>獎勵成長值<span>10</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                        <div class="task_hover">
                            <p class="task_desc">一次性開通年費會員(12個月及以上)</p>
                            <p class="task_limittimes">月限<span>1</span></p>
                            <a href="javascript:;">去完成></a>
                        </div>
                    </li>
                </ul>
            </div>
        </div>
        <!--任務成長值 結束-->
    </div>
</body>
<script>
//task growth
var switchPic = (function() {

    /*
now:當前第幾個li
linum:總共幾個li
shownum:要展示幾個li
w_li:li的寬度
marginR_li:li的右邊距
*/
    var now = 1;
    var linum, shownum, offset, w_li, marginR_li, pre, next, wrap;

    function init(o) {
        pre = o.preBtn;
        next = o.nextBtn;
        wrap = o.wrap;
        bindBtn();
    }

    function btnShow() {
        getInfo();
        if (linum <= shownum) { //如果li總個數小於要展示的個數,pre和next都不顯示
            pre.hide();
            next.hide();
        } else if (now == 1) { //初始化,只顯示next
            pre.hide();
            next.show();
        } else if (now == linum - shownum + 1) { //到最后一組,只顯示pre
            pre.show();
            next.hide();
        } else { //中間pre,next都顯示。
            pre.show();
            next.show();
        }
    }

    function getInfo() {
        linum = $("#switchPic").find("li").size();
        if ($("#body").hasClass("grid-1010")) {
            shownum = 3;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        } else if ($("#body").hasClass("grid-1230")) {
            shownum = 4;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        } else if ($("#body").hasClass("grid-1410")) {
            shownum = 4;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        }
    }

    function bindBtn() {
        btnShow();
        next.on("click", function() {
            now++;
            btnShow();
            wrap.stop(true).animate({
                "margin-left": -(now - 1) * offset
            });
        });
        pre.on("click", function() {
            now--;
            btnShow();
            wrap.stop(true).animate({
                "margin-left": -(now - 1) * offset
            });
        });

        $(window).resize(function() {
            now = 1;
            btnShow();
            wrap.animate({
                "margin-left": 0
            });
        });
    }
    return {
        init: init
    }
})();

switchPic.init({
    preBtn: $(".arrowbtn-left"),
    nextBtn: $(".arrowbtn-right"),
    wrap: $("#switchPic")
});
</script>

</html>
View Code

css代碼如下:

@charset "utf-8";
html,body{
    background-color: #f6f5f5;
}
.vg-body{
    width: 1390px;
    margin:0 auto;
}

/*任務成長值*/
.vg_title{
    font-size: 24px;
    line-height: 24px;
    padding:20px 0;
    color:#464646;
}
.vg_task{
    background-color: #fff;
    position: relative;
}
.vg_task .arrowbtn-left,.vg_task .arrowbtn-right{
    position: absolute;
    top:70px;
    width: 16px;
    height: 20px;
    cursor: pointer;
}
.vg_task .arrowbtn-left{
    left: 40px;
    background:url(../images/arrow-left.png) no-repeat;;
}
.vg_task .arrowbtn-right{
    right: 40px;
    background:url(../images/arrow-right.png) no-repeat;;
}
.vg_tasklist{
    width: 1200px;
    overflow: hidden;
    margin:0 auto;
}
.vg_tasklist ul{width: 999%;}
.vg_tasklist li{
    width: 258px;
    height: 130px;
    float: left;
    border:1px solid #c8c8c8;
    margin:15px  53px 15px 0;
    position: relative;
}
.vg_tasklist li .task_hover{
    position: absolute;
    left: -1px;
    top: -1px;
    width: 212px;
    padding:20px 25px 20px 23px;
    height: 90px;
    border-bottom: 2px solid #e65a5a;
    overflow: hidden;
    background-color: #f0f0f0;
    display: none;
}
.vg_tasklist li:hover .task_hover{
    display: block;
}

.task_hover .task_desc{
    font-size: 16px;
    line-height: 20px;
    color:#646464;    
}

.task_hover  .task_limittimes{
    font-size: 14px;
    color: #787878;
    float: left;
    padding-top: 12px;
}

.vg_tasklist li img{
    float: left;
    margin: 22px 8px 20px 20px;
}
.vg_tasklist li .rightinfo{
    width: 136px;
    float: left;
    text-align: center;
}
.rightinfo h3{
    font-size: 16px;
    color: #646464;
    padding-top: 15px;
}
.rightinfo p{
    font-size: 14px;
    line-height: 26px;
    color: #787878;
}
.rightinfo a,.task_hover  a{
    display: block;
    text-align: center;
    width: 96px;
    height: 30px;
    line-height: 30px;
    border:2px solid #e65a5a;
    border-radius: 5px;
    font-size: 16px;
    font-weight: 700;
    color: #e65a5a;
}
.task_hover a.done,.task_hover a.done:hover{
    background-color: #b4b4b4;
    color: #fff;
    border-color: #b4b4b4;
    cursor: default;
}

.rightinfo a{
    margin: 12px  auto 0;
}
.task_hover  a{
    float: right;
    margin-top: 18px;
    margin-right: -4px;
}
.task_hover  a:hover{
    text-decoration: none;
    background-color: #e65a5a;
    color: #fff;
}

/*grid-1230*/
.grid-1230 .vg-body{
    width: 1210px;
}
.grid-1230 .vg_tasklist{
    width: 1090px;
}
.grid-1230 .vg_tasklist li{
    margin-right: 16px;
}

.grid-1230 .vg_task .arrowbtn-left{
    left: 33px;
}
.grid-1230 .vg_task .arrowbtn-right{
    right: 33px;
}
.grid-1230 .vg_growth_table {
    padding:24px 30px;
}
/*grid-1010*/
.grid-1010 .vg-body{
    width: 990px;
}
.grid-1010 .vg_tasklist{
    width: 850px;
}
.grid-1010 .vg_tasklist li{
    margin-right: 35px;
}

.grid-1010 .vg_task .arrowbtn-left{
    left: 30px;
}
.grid-1010 .vg_task .arrowbtn-right{
    right: 30px;
}

.grid-1010 .vg_growth_table {
    padding:24px;
}
View Code

2、切圖分析

根據切好的圖,向右切換的時候,margin需要向左移動的距離為(li的width+2*border+margin-right)。

width+2*border在jquery中可用用outerWidth()獲取。

margin-right的值在jquery中用css("marginRight")獲取。

二、js交互部分

1、思路

總共就一個響應事件,就是點擊按鈕,以next按鈕為例。點按鈕發生了哪些事件。點擊按鈕—》ul產生位移—》更新按鈕狀態。或者點擊按鈕—》更新按鈕狀態—》ul產生位移。順序可以改變

第一步:分析ul產生位移的過程。

抽象2個變量

now:表示當前頁面第一個展示位展示的是第幾個li,默認為1,向右切換now++,向左切換now--。

offset:表示i的width+2*border+margin-right。

這樣點擊按鈕時的響應就變成了設置margin-left為-(now-1)*offset。

因為頁面有三個尺寸,所以點擊按鈕時ul產生位移時需要根據尺寸計算出offset的值。

第二步,分析更新按鈕狀態的過程。

分析一下這句話“切換到盡頭時不顯示按鈕”,頁面默認只顯示向右的按鈕,切換到到最左邊只顯示向左的按鈕,中間過程兩個按鈕都要顯示。

抽象出幾個變量:

linum:總共有幾個li,一次切換一個。

shownum:頁面需要展示幾個li。

now:當前頁面第一個展示位展示的是第幾個li,默認為1,向右切換now++,向左切換now--。

分析幾種情況:

  • 如果li的總數小於要展示的數,即linum<shownum,pre和next按鈕都不顯示。
  • 初始化,判斷now為1,只顯示next按鈕。
  • 展示到最后shownum個li的時候,即判斷now==linum-shownum+1時,只顯示next按鈕。
  • 否則pre和next按鈕都顯示。

因為頁面有三個尺寸,所以點擊按鈕更新按鈕狀態時需要根據尺寸計算出shownum的值。

第三步:提取方法

把第一步和第二步中涉及通過尺寸獲取信息的部分封裝成一個函數。getInfo

第二步更新按鈕狀態的封裝成一個函數。btnShow

第一步中給按鈕綁定事件的過程封裝成一個函數。bindBtn

同時要注意,頁面縮放的時候,需要重置一些狀態。

 2、代碼實現

<script>
//task growth
var switchPic = (function() {
    /*
now:當前第幾個li
linum:總共幾個li
shownum:要展示幾個li
w_li:li的寬度
marginR_li:li的右邊距
*/
    var now = 1;
    var linum, shownum, offset, w_li, marginR_li, pre, next, wrap;

    function init(o) {
        pre = o.preBtn;
        next = o.nextBtn;
        wrap = o.wrap;
        bindBtn();
    }

    function btnShow() {
        getInfo();
        if (linum <= shownum) { //如果li總個數小於要展示的個數,pre和next都不顯示
            pre.hide();
            next.hide();
        } else if (now == 1) { //初始化,只顯示next
            pre.hide();
            next.show();
        } else if (now == linum - shownum + 1) { //到最后一組,只顯示pre
            pre.show();
            next.hide();
        } else { //中間pre,next都顯示。
            pre.show();
            next.show();
        }
    }

    function getInfo() {
        linum = $("#switchPic").find("li").size();
        if ($("#body").hasClass("grid-1010")) {
            shownum = 3;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        } else if ($("#body").hasClass("grid-1230")) {
            shownum = 4;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        } else if ($("#body").hasClass("grid-1410")) {
            shownum = 4;
            w_li = wrap.find("li").outerWidth(); //算上了border的寬度
            marginR_li = parseInt(wrap.find("li").css("marginRight"));
            offset = w_li + marginR_li;
        }
    }

    function bindBtn() {
        btnShow();
        next.on("click", function() {
            now++;
            btnShow();
            wrap.stop(true).animate({"margin-left": -(now - 1) * offset});
        });
        pre.on("click", function() {
            now--;
            btnShow();
            wrap.stop(true).animate({"margin-left": -(now - 1) * offset});
        });

        $(window).resize(function() {
            now = 1;
            btnShow();
            wrap.animate({"margin-left": 0});
        });
    }
    return {init: init}
})();

switchPic.init({
    preBtn: $(".arrowbtn-left"),
    nextBtn: $(".arrowbtn-right"),
    wrap: $("#switchPic")
});
</script>

三、一個小tip

在寫動畫的時候,用了

wrap.stop(true).animate()

把當前元素涉及的所有動畫都停止了,讓后再觸發。否則當頁面快速resize,快速點擊按鈕多次,會產生“動畫積累”,觸發了下一個動畫,之前的動畫還沒完,就會有一個延遲,影響用戶體驗。

stop()參數說明:

$(selector).stop(stopAll,goToEnd)
  • stopAll,可選,規定是否停止被選元素的所有加入隊列的動畫。
  • goToEnd,可選,規定是否允許完成當前的動畫。該參數只能在設置了stopAll參數時使用。

具體用法:

  • stop(true)等價於stop(true,false): 停止被選元素的所有加入隊列的動畫。
  • stop(true,true):停止被選元素的所有加入隊列的動畫,但允許完成當前動畫。
  • stop()等價於stop(false,false):停止被選元素當前的動畫,但允許完成以后隊列的所有動畫。
  • stop(false,true):立即結束當前的動畫到最終效果,然后完成以后隊列的所有動畫。

在此提供一個小 demo,可以幫助理解stop()各個參數。

<!DOCTYPE html>
<html>

<head>
    <meta charset='utf-8'>
    <title>stop的用法案例</title>
    <style type="text/css">
    #animater {
        width: 150px;
        background: activeborder;
        border: 1px solid black;
        /*為了移動,需設置此屬性*/
        position: relative;
    }
    </style>
    <script src="http://code.jquery.com/jquery-3.1.0.js" integrity="sha256-slogkvB1K3VOkzAI8QITxV3VzpOnkeNVsKvtkYLMjfk=" crossorigin="anonymous"></script>
    <script type="text/javascript">
    $(function() {
        $("#start").click(function() {
            $("#box").animate({
                height: 300
            }, "slow");
            $("#box").animate({
                width: 300
            }, "slow");
            $("#box").animate({
                height: 100
            }, "slow");
            $("#box").animate({
                width: 100
            }, "slow");
        });
        //           點擊不同的button執行不同的操作
        $('#button1').click(function() {
            //默認參數是false,不管寫一個false還是兩個false還是沒寫false效果一樣
            $('#box').stop();
        });
        $('#button2').click(function() {
            //第二個參數默認false
            $('#box').stop(true);
        });
        $('#button3').click(function() {
            $('#box').stop(false, true);
        });
        $('#button4').click(function() {
            $('#box').stop(true, true);
        });
    })
    </script>
</head>

<body>
    <p>
        <input type='button' value='開始測試' id='start'>
    </p>
    <div id="button">
        <input type="button" id="button1" value="stop()" />
        <input type="button" id="button2" value="stop(true)" />
        <input type="button" id="button3" value="stop(false,true)" />
        <input type="button" id="button4" value="stop(true,true)" />
    </div>
    <div id="box" style="background:#98bf21;height:100px;width:100px;position:relative">stop運動參數測試</div>
</body>

</html>
View Code

本文作者starof,因知識本身在變化,作者也在不斷學習成長,文章內容也不定時更新,為避免誤導讀者,方便追根溯源,請諸位轉載注明出處:http://www.cnblogs.com/starof/p/5443445.html有問題歡迎與我討論,共同進步。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM