移動web--滾動(可以滑動的)導航欄的製作
阿新 • • 發佈:2019-01-09
滑動的導航欄
- 有時候導航欄的長度過於長,我們為了介面的美觀和使用者體驗,會將導航欄在一行(或則一列)顯示,超出部分隱藏,而且不用管內容的長短,有利於前後臺數據的互動,大部分情況是:在移動web網站中,容器中的ul過長,我們通常會將ul超出容器的部分隱藏
- 移動網站上的橫向導航欄
-
某直播平臺的橫向滾動導航欄–效果瀏覽:https://m.douyu.com/
-
某新聞平臺的橫向滾動導航欄–效果瀏覽:https://m.toutiao.com/?W2atIF=1
-
電商網站:https://pro.m.jd.com/mall/active/3YvKJrc4e4WK7aZ46j3h5UMCvEn4/index.html
- 移動網站上的縱向滾動導航欄
- 控制導航欄滾動的重要性
電商,問答,直播,新聞…大部分平臺都會使用到移動導航欄,特別是在移動web,典型的應用場景位於移動裝置App和web,如何控制導航欄的滾動
iScroll
iScroll是一個高效能,資源佔用少,無依賴,多平臺的javascript滾動外掛
- 文件教程
http://caibaojian.com/iscroll-5/ - 下載地址
https://github.com/cubiq/iscroll - 簡單的使用(這裡以橫向導航欄滾動為例子),具體效果可以看上面推薦的網站
- 我們儘可能保持DOM結構的簡潔
- IScroll是一個類,每個需要使用滾動功能的區域均要進行初始化
- 檢視文件的基本功能可知,預設情況下只有縱向滾動條可以使用。如果你需要使用橫向滾動條,需要將scrollX 屬性值設定為 true
- 當然,isScroll有更強大的作用,我們使用它是為了解決我們的需求和提高我們的開發效率
HTML
<div id="wrapper">
<ul>
<li class=""><a href="javascript:;">熱門推薦</a></li>
<li class="active"><a href="javascript:;">潮流女裝</a></li>
<li class=""><a href="javascript:;">品牌男裝</a></li>
<li class=""><a href="javascript:;">內衣配飾</a></li>
<li class=""><a href="javascript:;">家用電器</a></li>
<li class=""><a href="javascript:;">電腦辦公</a></li>
<li class=""><a href="javascript:;">手機數碼</a></li>
<li class=""><a href="javascript:;">母嬰頻道</a></li>
<li class=""><a href="javascript:;">圖書</a></li>
<li class=""><a href="javascript:;">家居家紡</a></li>
<li class=""><a href="javascript:;">居家生活</a></li>
<li class=""><a href="javascript:;">傢俱建材</a></li>
<li class=""><a href="javascript:;">熱門推薦</a></li>
<li class=""><a href="javascript:;">潮流女裝</a></li>
<li class=""><a href="javascript:;">品牌男裝</a></li>
<li class=""><a href="javascript:;">內衣配飾</a></li>
<li class=""><a href="javascript:;">家用電器</a></li>
<li class=""><a href="javascript:;">電腦辦公</a></li>
<li class=""><a href="javascript:;">手機數碼</a></li>
<li class=""><a href="javascjavascript:;ript:;">母嬰頻道</a></li>
<li class=""><a href="javascript:;">圖書</a></li>
<li class=""><a href="javascript:;">家居家紡</a></li>
<li class=""><a href="javascript:;">居家生活</a></li>
<li class=""><a href="javascript:;">傢俱建材</a></li>
</ul>
</div>
我們這裡是移動web上的使用,所以需要做適配方案
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
CSS
<style>
#wrapper{
height: 300px;
background: red;
overflow: hidden;
}
*{
margin: 0;
padding: 0;
font-size: 13px;
list-style: none;
}
ul{
width: 2400px;
}
li{
width: 100px;
height: 50px;
background: #ccc;
float: left;
text-align: center;
line-height: 50px;
cursor: pointer;
}
li.active{
background: hotpink;
color: red;
}
</style>
JS的呼叫(初始化)
<script src="js/iscroll.js"></script>
// 引入我們的外掛
<script type="text/javascript">
var myScroll = new IScroll('#wrapper',{
mouseWheel: true,
scrollbars: true,
scrollX: true
// 橫向滾動導航欄
});
// 初始化
</script>
效果
原生JS實現滑動的導航欄
- iScroll只能稱之為工具,它可能會出現一些bug,當然可以選擇更優的外掛,但是,原生JS還是必不可少的
- 這裡以縱向的導航欄為例子,並綜合到案例中去
- 實現左邊的滑動
HTML
html和上面的橫向例子一樣
CSS設定li不浮動,ul的寬度和li一樣即可,超出父盒子隱藏,父盒子(#wrapper)相對定位(relative),子盒子(ul)絕對定位(absolute)效果一樣即可
- JS的封裝
// 1. ulMove跟隨著滑鼠的移動
// 2. 當上面移動超過0時,手指離開時移動到原位
// 3. 當下面移動超過ul的高度時,手指離開時移動到原位
// 4. 限制ul的移動,不能讓它移動得太過
// 4.1 往下拉時,不能讓其距離頂部(jd_bar)超過一定距離,這裡限制為100
// 4.2 往上拉,不能讓其距離頂部(jd_bar)超過一定距離,這裡限制為100
// ele是滑動的容器,一般是需要移動的導航欄ul,fartherEle是裝著它的容器,一般是ul的父元素
function touchScroll(ele,fartherEle){
//開始觸碰距離手指距離螢幕頂端的位置,初始化為0
var startDistance = 0
//記錄再次移動ul時上次ul定位的位置
var endDistance = 0
//手指移動的距離
var moveDistance = 0
//需要移動元素的高度
var ulHeight = ele.offsetHeight
//容器(父元素)的高度
var barH = fartherEle.offsetHeight
//barHide,當ele向上滑時,ul滑到底部隱藏的距離
var barHide = ulHeight - barH
//開始觸碰ul時
ele.addEventListener('touchstart',function(e){
//手指距離螢幕頂端的距離
startDistance = e.touches[0].clientY
})
//手指在螢幕上滑動
ele.addEventListener('touchmove',function(e){
//這是限制ul距離上下都只能是100px,後面用到
var maxTop = 100
//手指在ul移動的距離(endDistance)
moveDistance = e.touches[0].clientY - startDistance + endDistance
//限制ul定位的位置,距離父盒子頂部不能超過100
if(moveDistance>=maxTop){
moveDistance = maxTop
}
//限制ul定位的位置,距離父盒子底部部不能超過100
if(moveDistance<=-(barHide + maxTop)){
moveDistance = -(barHide + maxTop)
}
//移動時取消後面的過渡效果
this.style.transition = 'none'
//此時,ul的移動範圍(定位)已經設定,可以跟隨著手指的移動而移動
this.style.top = moveDistance + 'px'
})
ele.addEventListener('touchend',function(e){
//當移動ul距離頂部超過0時(top>0),使其ul緩動滑動到父盒子頂部
if(moveDistance>=0){
moveDistance = 0
this.style.transition = 'top 1s'
}
//當移動ul距離底部超過0時(top>0),使其ul底部緩動滑動到父盒子底部
if(moveDistance <= -barHide){
moveDistance = -barHide
this.style.transition = 'top 1s'
}
//記錄此時ul的定位位置,用於下次
endDistance = moveDistance
//範圍限制好。可以滑動了
this.style.top = endDistance + 'px'
})
}
呼叫
touchScroll(document.querySelector('ul'),document.querySelector('#wrapper'))