Vue中的数据更新了但UI没有刷新2

2020-03-12  本文已影响0人  光明程辉

这次是我们封装的一个scroll.vue组件

<!--
 * @Author: liangcs
 * @Date: 2020-03-03 13:36:09
 * @LastEditors: liangcs
 * @LastEditTime: 2020-03-05 17:17:02
 * @FilePath: /h5-dev-mobile-sales-components/src/components/scroller/index.vue
 -->
<template>
    <div ref="scroll" class="wrapper">
        <div class="scroll-content" ref="content">
            <slot></slot>
        </div>
        <div name="pull-down" v-if="pullDown">
          <slot name="pullDown" 
            :pullDownStyle="pullDownStyle"
            :beforePullDown="beforePullDown"
            :isPullingDown="isPullingDown"
            :readyPullDown="readyPullDown"
            >
            <div :style="pullDownStyle" class="pull-down" >{{pullDownLabel}}</div>
          </slot>
        </div>
    </div>
</template>
<script>
let clickVal = (function(){
                    if (/iPhone|iPad|iPod|Macintosh/i.test(navigator.userAgent)) return false;
                    if (/Chrome/i.test(navigator.userAgent)) return (/Android/i.test(navigator.userAgent));
                    if (/Silk/i.test(navigator.userAgent)) return false;
                    if (/Android/i.test(navigator.userAgent)) {
                        var s=navigator.userAgent.substr(navigator.userAgent.indexOf('Android')+8,3);
                        return parseFloat(s[0]+s[3]) < 44 ? false : true}
                }())
const DEFAULT_OPTIONS = {
    probeType: 3,//probeType:1对性能没有影响。在滚动事件被触发时,滚动轴是不是忙着做它的东西。probeType:2总执行滚动,除了势头,反弹过程中的事件。这类似于原生的onscroll事件。probeType:3发出的滚动事件与到的像素精度。注意,滚动被迫requestAnimationFrame(即:useTransition:假)。
    scrollbars: false,//有滚动条
    mouseWheel: false,//允许滑轮滚动
    fadeScrollbars: false,//滚动时显示滚动条,默认影藏,并且是淡出淡入效果
    bounce: true,//边界反弹
    click: clickVal,
    disablePointer: true,
    disableTouch : false,
    disableMouse : true,
    eventPassthrough: 'horizontal',
    pullDownRefresh: false
}
const DEFAULT_PULLDOWN_OPTIONS = {
    threshold: 50,
    stop: 40
}
const SCROLL_EVENTS = ['scrollStart', 'scroll', 'scrollEnd']
import BScroll from 'better-scroll'
export default {
    data() {
        return {
            beforePullDown: true,
            readyPullDown: false,//到达下拉阀值
            isPullingDown: false,//触发下拉回调
            isPullingUp: false,
            pullDownStyle: ""
        }
    },
    props: {
        data: {
            type: Array,
            default () {
                return []
            }
        },
        options: {
            type: Object,
            default () {
                return {}
            }
        },
        // 是否仅需要滚动
        onlyScroll: {
            type: Boolean,
            default: false
        },
        // 是否启动无限加载
        pullUp: {
            type: Boolean,
            default: true
        },
        // 是否启动下拉
        pullDown: {
            type: Boolean,
            default: true
        },
        // 是否监听滚动事件
        listenScroll: {
            type: Boolean,
            default: false
        },
        hasLoading: {
            type: Boolean,
            default: true
        }
    },
    computed: {
      pullDownLabel() {
        if(this.isPullingDown) {
          return '正在加载';
        } else if(this.readyPullDown) {
          return '松开刷新'
        } else {
          return '下拉刷新'
        }
      }
    },
    mounted() {
        this._initScroll();
        // console.log(this.scroller.wrapperHeight);
        // 
    },
    watch: {
        data() { // 监听数据改变时直接刷新,不知道会不会有坑
            setTimeout(this.refresh,20)
        },
        pullDown(newVal, oldVal) {
            if(newVal) {
                this.scroller.openPullDown(DEFAULT_PULLDOWN_OPTIONS)
                if(!oldVal) {
                    this._onPullDownRefresh();
                    this._onPullDownScrollHandle();
                }
            }
            if(!newVal && oldVal) {
                this.scroller.closePullDown();
                this._offPullDownScroll();
                this._offPullDownRefresh();
            }
        },
        pullUp(newVal, oldVal) {
            if(newVal && !oldVal) {
                this._onPullUpRefresh();
            }
            if(!newVal && oldVal) {
                this._offPullUpRefresh();
            }
        }
    },
    methods: {
        _initScroll() {
            this._calMinHeight();
            var options = Object.assign({}, DEFAULT_OPTIONS, {
                pullDownRefresh : this.pullDown ? DEFAULT_PULLDOWN_OPTIONS : false
            }, this.options)
            this.scroller = new BScroll(this.$refs.scroll, options)
            if(this.listenScroll) {
              this._listenScroll();
            }
            //下拉刷新
            if(this.pullDown){
                this._onPullDownRefresh();
                this._onPullDownScroll();
            }
            if(this.pullUp) {
                this._onPullUpRefresh();
            }
            
        },
        //解决内部元素小于scroll高度无法滑动的bug
        _calMinHeight() {
            this.$refs.content.style.minHeight = (this.$refs.scroll.offsetHeight+ 1)+'px';
        },
        refresh() {
            this.$nextTick(()=>{
                if(this.isPullingDown) {
                    this.beforePullDown = true;
                    this.isPullingDown = false;
                    this.scroller.finishPullDown();
                }
                
                this.isPullingUp = false;
                this.scroller.refresh();
            })
        },
        _onPullDownRefresh() {
            this.scroller.on('pullingDown', this._pullDownHandle);
        },
        _onPullDownScroll() {
            this.scroller.on('scroll', this._pullDownScrollHandle);
        },
        _offPullDownRefresh() {
            this.scroller.off('pullingDown', this._pullDownHandle);
        },
        _offPullDownScroll() {
            this.scroller.off('scroll', this._pullDownScrollHandle);
        },
        _pullDownScrollHandle(pos) {
            if(this.beforePullDown) {
                this.pullDownStyle = `top:${Math.min(pos.y - 40, 0)}px`
            } else {
                this.pullDownStyle = `top:${Math.min(pos.y - 40, 0)}px`
            }
            if(pos.y>=50) {
              this.readyPullDown = true;
            } else {
              this.readyPullDown = false;
            }
        },
        _pullDownHandle() {
            this.beforePullDown = false;
            this.readyPullDown = false;
            this.isPullingDown = true;
            this.$emit('pullDown');
        },
        _onPullUpRefresh() {
            this.scroller.on('scroll', this.pullUpRefreshHandle)
        },
        _offPullUpRefresh() {
            this.scroller.off('scroll', this.pullUpRefreshHandle)
        },
        pullUpRefreshHandle(pos) {
            if(this.scroller.y < 0 && this.scroller.maxScrollY - this.scroller.y > -100 && !this.isPullingUp && !this.isPullingDown) {
                this.isPullingUp = true;
                this.$emit('pullup')
            }
        },
        _listenScroll() {
          SCROLL_EVENTS.forEach(v => {
            this.scroller.on(v, (...arg) => {
              this.$emit(v, ...arg)
            })
          })
        },
        enable() {
          this.scroller && this.scroller.enable();
        },
        disable() {
          this.scroller && this.scroller.disable();
        },
        scrollTo() {
          this.scroller && this.scroller.scrollTo.apply(this.scroll, arguments)
        },
        scrollToElement() {
          this.scroller && this.scroller.scrollToElement.apply(this.scroll, arguments)
        }

    }
}
</script>
<style lang="less" scoped>
    .wrapper {
      position: relative;
      height: 100%;
      .pull-down {
        position: absolute;
        width: 100%;
        line-height: 40px;
        text-align: center;
      }
    }
    
</style>

使用:

 <scroller ref="scroller" class="my-scroller" style="position:absolute;top:306px;bottom:10px;left:0;right:0" :pullDown="true" @pullDown="downLoading()" :pullUp="page.isMore" @pullUp='upLoading()'>
</scroller>

但是发现下拉刷新的时候,没反应,“下拉刷新” 不显示!

因为么有,刷新!

使用到一个方法

// 刷新一下表
  this.$nextTick(()=>{
      this.$refs.scroller.refresh();
  });

补充:
上篇是

这里是

this.$nextTick

在Vue生命周期的created()钩子函数进行的DOM操作一定要放在Vue.nextTick()的回调函数中。

官网有说到这2者的区别:

https://cn.vuejs.org/v2/api/index.html#Vue-nextTick

上一篇 下一篇

猜你喜欢

热点阅读