使用小程序bindscroll实现联动
-
需求分析
要求实现的功能是左侧展示分类名,右侧展示商品,点击任意分类可以跳转分类所包含的商品的第一个,滑动商品列表至下一分类时左侧所属分类高亮。 -
思路
首先实现点击左侧分类右侧商品滑动,这里使用小程序提供的 scroll-into-view方法,官方文档
https://developers.weixin.qq.com/miniprogram/dev/component/scroll-view.html
右侧商品滚动页的框
<scroll-view scroll-y='true' style="height:784rpx" scroll-with-animation="true" scroll-into-view="m_{{toView}}" bindscroll='scroll'>
<view id=' m_1'></view>
<view id=' m_2'></view>
</scroll-view>
其他先不管 这里只看scroll-into-view="{{toView}}" 他代表这一滚动页,滚动到 其下id为toView的组件,在左侧用bindtap=‘clickMenu’ 实现对toView的动态控制,
//分类栏的wxml代码,
<scroll-view class='store-menu' style="height:784rpx" scroll-y='true'>
<view wx:for='{{menulist}}' wx:key="{{item.id}}" data-id="{{item.id}}" bindtap='clickMenu' class="menu-item {{curId == item.id ? 'menu-active': ''}}">
<text>{{item.name}}</text>
</view>
<view style='height:90rpx'></view>
</scroll-view>
//点击左侧,控制右侧滑动 js代码
clickMenu:function(e){
var id = e.currentTarget.dataset.id;
var name = e._relatedInfo.anchorTargetText;
this.setData({
curId: id,
toView: id,
menu_name: name,
})
},
上述实现左侧控制右侧的需求,接下来实现右侧控制左侧,右侧商品栏代码中 有提到的bindscroll=‘scroll’ 这是官方给的滚动时触发的方法。
思路:首先我想控制左侧的商品所属的分类就要知道,这个分类所属的所有商品块有多长,这个长度往上滑动过去了我就知道不是这个分类了是下一个,这里的长度计算为距离顶部的长度,因为要根据 对比属性scrollTop判断 这一分类块 有没有过去,scrollTop为滚动块往上滚动的长度,
实现:
//wxml
在左侧分类栏里加一个高亮方法,curId用来控制被选择时候高亮
class="menu-item {{curId == item.id ? 'menu-active': ''}}"
bindscroll=‘scroll’ 中方法
scroll:function(e){
var scrolltop = e.detail.scrollTop //获取滚动的长度,单位为px,
var h=0 //h为每个模块的长度 ,px
var selectedid; // 用来控制curId
var coefficient = this.data.widthcoefficient //根据机型的不同 商品展示长度不同,我在这里用了rpx转换px系数
this.data.foodlist.forEach(function (item, i){
var list_height = (item.food.length * 208) / coefficient //这里list_height为每个分类的高度, 208 是rpx 单位商品展示长度
// console.log('移动了'+scrolltop)
// console.log('循环判断模块高度h为'+h)
h += list_height; //给每个分类计算距离顶部的高度,那这个对比滚动的长度
if(scrolltop>=h){ // 判断滚动长度有没有超过分类的长度,
selectedid=item.id //如果超过了就给左侧的控制高亮的flag 赋值
}
});
this.setData({
curId:selectedid
})
- 数据结构
//商品数据
foodlist: {
[x: string]: any;
id: string;
food: {
[x: string]: any;
id: string;
img: string;
name: string;
}[];
}[]
//分类数据
menulist: {
[x: string]: any;
name: string;
id: string;
}[]
foodlist.id 和menulist.id 必须相同, 把俩结合起来也可以的自己看需求,这是上述代码的数据结构