前言
公司小程序出了一个功能需要开发一个scroll-bar组件,自己看微信API文档造轮子,在效果完成后代码发出来供大家参考,有需要的直接拿去用(不会整理文档格式,看看就好)。
功能点
支持数据动态加载
支持默认值设置,在没有默认值情况下设置默认选中第一个
支持默认默认值后 跳转到相应的选中事件位置
效果图
imagewxml
<view class="b_tabs" bind:touchstart="touchstart" bind:touchmove="touchmove" style="{{style}}">
<view class="b_content" style="transform:translateX({{left}}px)">
<view class="b_tabs_item" wx:for="{{dataList}}" wx:key="value" bind:tap="setSelect" data-value="{{item.value}}">
<view class="text {{item.value == value?'b_tabs_item_active':''}}">{{item.name}}</view>
</view>
</view>
</view>
js
Component({
properties: {
dataList: {
type: Array,
value: [{
name:'最新',
value:0
},{
name:'西装',
value:1
},{
name:'鞋子',
value:2
},{
name:'外套',
value:3
},{
name:'短裤',
value:4
},{
name:'半身裙',
value:5
},{
name:'西装',
value:6
},{
name:'外套',
value:31
},{
name:'短裤',
value:422
},{
name:'半身裙',
value:51
},{
name:'西装',
value:61
},]
},
value: {
type: String,
value: ''
},
style:String,
},
data: {
left: 0,
// 触控移动移动距离
width: 0,
phoneWidth:0,
dom: {
left: 0,
width: 0,
}
},
ready() {
this.initTab()
},
methods: {
initTab() {
const query = wx.createSelectorQuery().in(this)
query
.select(".b_tabs")
.boundingClientRect(res => {
this.setData({
'dom.phoneWidth':res.width
})
this.data.phoneWidth = res.width
})
.selectAll(".b_tabs_item")
.boundingClientRect(res => {
if(!res ||this.data.dataList.length === 0)return
let domWidth = 0;
let selectDomWidth = 0;
this.data.dataList.forEach((element, index) => {
if (this.data.value == element.value) {
selectDomWidth = domWidth
}
domWidth+=res[index].width
});
if (this.data.value == "" || this.data.value == undefined) {
this.triggerEvent('cb', this.data.dataList[0].value)
}
this.setData({
'dom.width':domWidth
},()=>{
if(domWidth <= this.data.phoneWidth){
this.setValue(0);
}else if(domWidth > selectDomWidth && domWidth - selectDomWidth > this.data.phoneWidth){
// 可滑动面积大于0且可滑动面积大于滑动面积
this.setValue(-selectDomWidth);
}else if(domWidth > selectDomWidth && domWidth - selectDomWidth <= this.data.phoneWidth){
// 可滑动面积大于0且可滑动面积小于滑动面积
this.setValue(-(domWidth-this.data.phoneWidth));
}
})
})
.exec();
},
setSelect(e) {
const {dataset} = e.currentTarget
this.triggerEvent('input', dataset)
this.triggerEvent('cb', dataset.value)
},
/**
* 事件开始
* @param e
*/
touchstart(e) {
const { pageX } = e.touches[0];
// 移动的距离
this.data.width = pageX - this.data.left;
},
touchmove(e) {
const { pageX } = e.touches[0];
this.setValue(pageX - this.data.width);
},
/**
* 设置移动距离
* @param value
*/
setValue(value) {
// 超出tab长度禁止滚动
if(this.data.dom.width - this.data.phoneWidth < -value)return
// 设置滚动距离
this.setData({
left:Math.max(-this.data.dom.width, Math.min(parseInt(value), 0))
})
}
}
});
wxss
.b_tabs {
width: 100%;
overflow: hidden;
background: #fff;
margin-bottom: 0.02rem;
}
.b_content {
height: 94rpx;
display: flex;
}
.b_tabs_item {
font-size: 30rpx;
}
.text {
line-height: 94rpx;
white-space: nowrap;
color: #999;
margin: 0 25rpx;
}
.b_tabs_item_active {
color: #7468F2;
font-size: 1.134em;
font-weight: 600;
}
网友评论