【JS顶部导航吸顶】实现导航与列表的子项同步联动

今天写项目遇到了这个,就记录下来了实现的关键代码。
吸顶的效果在Android原生里面非常简单就可以实现,因为原生组件使用Toolbar+Tabbar就自动完成了。

在web端,实现这个效果,最重要的监听页面滚动,计算好tab与子项列表的位置高度。

假设我们有四个分类tab在顶部,下面是一个包含四个分类子项的综合列表,我们需要实现

1.点击tab子项,列表滚动到对应分类。
2.滑动列表,当前子项应该与顶部tab同步显示【tab颜色随着列表子项的更改而变化】
3.向上滚动列表,tab吸顶。

看一下效果图

Video20200428103116942.gif

关键代码

1
2
3
4
5
6
7
//data 分类数据
Object.keys(data).map(function (row, index) {
//计算每个分类所在的位置,我这里是每行两个,一会计算高度的时候可以除以2就行了
let count = res.data[row].length;
order += res.data[row].length;
navInfo.push({name: row, count: count, order: order - count });
});
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
//分类吸顶
let sort = document.getElementById("sort_list");
let ot = sort.offsetTop;
// 页面容器,比如body
$('.pub-wrapper').on('scroll', function () {
let st = $('.pub-wrapper').scrollTop();
let h = $('.goods_type_item').height();
sort.setAttribute("data-fixed", st >= ot ? "fixed" : "");
//动态更改分类标签
for(let n=0;n<navInfo.length;n++){
//navInfo是分类信息
if(st > navInfo[n].order / 2 * h){
$('.type_item span').removeClass('select_type');
$('span[data-type='+ navInfo[n].name + ']').addClass('select_type');
}
}


});
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
//滚动到指定分类
function scrollNav(nav) {
// console.log('首次加载滚动到指定分类' + nav);
let anchor = null;
navInfo.forEach(function (e) {
if(e.name === nav){
anchor = e
}
});
// console.log(anchor);
// console.log()
$(".pub-wrapper").animate({
scrollTop: anchor.order * $('.goods_type_item').height()
}, 1500);
}

主要就是监听滚动的距离与tab对应子项的高度差,如果滚动过了,就把对应的tab颜色改变,而子项距离顶部的高度,通过子项的索引【注意是在整个分类中的索引位置,不是个数!!!】除以每行的个数【这里是2】然后乘上行元素的高度。这个距离就是对应tab子项与顶部的距离。