vue中使用better-scroll2.0的无法滚动的坑

vue中使用better-scroll2.0的坑

前提我自己封装的一个Scroll组件 比较简单

<template>
  <div class="scroll_wrapper" ref="scroll_wrapper">
    <div class="content">
      <slot></slot>
    </div>
  </div>
</template>

<script>
import BScroll from "better-scroll"
export default {
  name: "Scroll",
  props:{
    data: {
      type: Object,
      default: null
    },
  },
  mounted() {
    setTimeout(() => {
      this._initScroll()
    }, 20)
  },
  methods:{
  //初始化BS
    _initScroll(){
      if (!this.$refs.scroll_wrapper) {
        return
      }
      this.scroll = new BScroll(this.$refs.scroll_wrapper, {
        click:true
      })
    },
    refresh(){
    //重新计算BS
      this.scroll && this.scroll.refresh()
    },
    enable() {
      // 启用BS
      this.scroll && this.scroll.enable()
    },
    disable(){
    //禁用BS
      this.scroll&&this.scroll.disable();
    },
  },
  watch: {
    // 监听数据的变化,延时refreshDelay时间后调用refresh方法重新计算,保证滚动效果正常
    data() {
      setTimeout(() => {
        this.refresh()
      }, 200)
    }
  }
}
</script>

组件在父组件中的引用是下面这样

<Scroll :data="$data" ref="scroll">
     <div class="orders">
         <div v-for="(order,index) in allOrders" :key="index" @click="selectOrder(order)" >
          <!--内容-->
         </div>
     </div>
     <div class="none"></div>
 </Scroll>

进入主题
请求数据并将数据展示出来的列表内容高度是符合BS的,也就是说可以滚动,但是事实并没有滚动,原因在于并没有在请求完数据的时候重新计算BS
这里一定要加上this.$nextTick,不然不起作用

getOrderList(){
      let url = "/api/order/client/queryOrderByUserId?userId="+this.$store.state.user.id
      this.axios.get(url).then(res=>{
        this.allOrders = res.data.data
        this.$nextTick(()=>{
          this.$refs.scroll.refresh()
        })
      })
    }

注意:请求数据时如果是在created中请求,一定要加上this.$nextTick

created(){
	this.$nextTick(()=>{
	     this.getOrderList()
	 })
}

如果是在mounted中要这样写

mounted(){
	this.getOrderList()
}

不推荐在mounted中获取数据,会有滚动bug(亲测)

第二个就是当页面滚动内容是可变的,但是是没有数据请求的,要实现这样的效果:**当content内容大于外层的wrapper设置的可视内容高度时,就要滚动,当content内容小于外层的wrapper设置的可视内容高度时,就要不滚动。**例如我的项目中
在这里插入图片描述

这个页面中商品评价是可以展开的,上图中的content内容是没有大于蓝色部分wrapper的可视内容高度,所以不能滚动。
但是当我点开一个面板时,如下图
在这里插入图片描述
这时候content内容高度是大于蓝色部分的可视内容高度,可以滚动。
说明:这里的content高度一定是面板展开结束后的高度,而不是为展开时的高度。所以整个content的高度一定实在面板动画展开结束后计算,这时候就要用到vue中transitionend事件
代码如下

<van-collapse-item  :name="index" @transitionend="transitionend"  v-for="(product,index) in order.list"/>
methods:{

    //当面板展开动画结束后计算滚动内容高度,然后确定是否禁用还是重新计算滚动内容高度
    transitionend(){
    //内层高度小于外层wrapper的高度 禁用BS
      if(this.scrollHeight < this.clientHeight){
        this.$nextTick(()=>{
          this.$refs.scroll.disable()
        })
        //内层高度大于外层wrapper的高度 启用BS并重新计算BS高度
      }else {
        this.$nextTick(()=>{
          this.$refs.scroll.enable()
          this.$refs.scroll.refresh()
        })
      }
    }
  },
  computed:{
  //Scroll组件中外层wrapper的可视高度,即上面图片中的蓝色区域
    clientHeight(){
      return this.$refs.scroll.scroll.wrapper.clientHeight
    },
    //Scroll组件中内层content的可视高度
    scrollHeight(){
      return this.$refs.scroll.scroll.content.clientHeight
    }
  }

下面是this.$refs.scroll的打印内容,我把它里面的wrapper和content都打印出来

this.$refs.scroll的内容
在这里插入图片描述

this.$refs.scroll.scroll的内容
在这里插入图片描述

this.$refs.scroll.scroll.wrapper以及this.$refs.scroll.scroll.content的内容都在this.$refs.scroll.scroll中如下图

在这里插入图片描述

  • BS外层固定的clientHeight都可以通过
    this.$refs.scroll.scroll.wrapper.clientHeight获取
  • BS内层滚动内容clientHeight都可以通过
    this.$refs.scroll.scroll.content.clientHeight
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值