zoukankan      html  css  js  c++  java
  • vue2.0 移动端,下拉刷新,上拉加载更多 封装组件

    前言

    在做移动端的避免不了 下拉刷新,上拉加载

    直接上代码吧,哈哈

    组件里:

      1 <template lang="html">
      2   <div class="yo-scroll"
      3   :class="{'down':(state===0),'up':(state==1),refresh:(state===2),touch:touching}"
      4   @touchstart="touchStart($event)"
      5   @touchmove="touchMove($event)"
      6   @touchend="touchEnd($event)"
      7   @scroll="(onInfinite || infiniteLoading) ? onScroll($event) : undefined">
      8     <section class="inner" :style="{ transform: 'translate3d(0, ' + top + 'px, 0)' }">
      9       <header class="pull-refresh">
     10         <slot name="pull-refresh">
     11            <span class="down-tip">下拉更新</span>
     12            <span class="up-tip">松开更新</span>
     13            <span class="refresh-tip">更新中……</span>
     14         </slot>
     15       </header>
     16       <slot></slot>
     17       <footer class="load-more">
     18         <slot name="load-more">
     19           <span>{{loadingText}}</span>
     20         </slot>
     21       </footer>
     22     </section>
     23   </div>
     24 </template>
     25  
     26 <script>
     27 export default {
     28   name: 'kl-scroll',
     29   props: {
     30     offset: {
     31       type: Number,
     32       default: 40
     33     },
     34     loadingText: {
     35       type: String,
     36       default: '加载中...'
     37     },
     38     enableInfinite: {
     39       type: Boolean,
     40       default: true
     41     },
     42     enableRefresh: {
     43       type: Boolean,
     44       default: true
     45     },
     46     onRefresh: {
     47       type: Function,
     48       default: undefined,
     49       required: false
     50     },
     51     onInfinite: {
     52       type: Function,
     53       default: undefined,
     54       require: false
     55     }
     56   },
     57   data() {
     58     return {
     59       top: 0,
     60       state: 0,
     61       startY: 0,
     62       touching: false,
     63       infiniteLoading: false
     64     }
     65   },
     66   methods: {
     67     touchStart(e) {
     68       this.startY = e.targetTouches[0].pageY
     69       this.startScroll = this.$el.scrollTop || 0
     70       this.touching = true
     71     },
     72     touchMove(e) {
     73       if (!this.enableRefresh || this.$el.scrollTop > 0 || !this.touching) {
     74         return
     75       }
     76       let diff = e.targetTouches[0].pageY - this.startY - this.startScroll
     77       if (diff > 0) e.preventDefault()
     78       this.top = Math.pow(diff, 0.8) + (this.state === 2 ? this.offset : 0)
     79  
     80       if (this.state === 2) { // in refreshing
     81         return
     82       }
     83       if (this.top >= this.offset) {
     84         this.state = 1
     85       } else {
     86         this.state = 0
     87       }
     88     },
     89     touchEnd(e) {
     90       if (!this.enableRefresh) return
     91       this.touching = false
     92       if (this.state === 2) { // in refreshing
     93         this.state = 2
     94         this.top = this.offset
     95         return
     96       }
     97       if (this.top >= this.offset) { // do refresh
     98         this.refresh()
     99       } else { // cancel refresh
    100         this.state = 0
    101         this.top = 0
    102       }
    103     },
    104     refresh() {
    105       this.state = 2
    106       this.top = this.offset
    107       this.onRefresh(this.refreshDone)
    108     },
    109     refreshDone() {
    110       this.state = 0
    111       this.top = 0
    112       this.infiniteLoading = false
    113     },
    114  
    115     infinite() {
    116       this.infiniteLoading = true
    117       this.onInfinite(this.infiniteDone)
    118     },
    119  
    120     infiniteDone() {
    121       this.infiniteLoading = false
    122     },
    123  
    124     onScroll(e) {
    125       if (!this.enableInfinite || this.infiniteLoading) {
    126         return
    127       }
    128       let outerHeight = this.$el.clientHeight
    129       let innerHeight = this.$el.querySelector('.inner').clientHeight
    130       let scrollTop = this.$el.scrollTop
    131       let ptrHeight = this.onRefresh ? this.$el.querySelector('.pull-refresh').clientHeight : 0
    132       let infiniteHeight = this.$el.querySelector('.load-more').clientHeight
    133       let bottom = innerHeight - outerHeight - scrollTop - ptrHeight
    134       if (bottom < infiniteHeight) this.infinite()
    135     }
    136   }
    137 }
    138 </script>
    139 <style >
    140 .yo-scroll {
    141   position: absolute;
    142   /* top: 2.5rem;  */
    143    top: 0;
    144   right: 0;
    145   bottom: 0;
    146   left: 0;
    147   overflow: auto;
    148   -webkit-overflow-scrolling: touch;
    149   background-color: #f5f8fa;
    150 }
    151 .yo-scroll .inner {
    152   position: absolute;
    153   top: -2rem;
    154    100%;
    155   transition-duration: 300ms;
    156 }
    157 .yo-scroll .pull-refresh {
    158   position: relative;
    159   left: 0;
    160   top: 0;
    161    100%;
    162   height: 2rem;
    163   display: flex;
    164   align-items: center;
    165   justify-content: center;
    166 }
    167 .yo-scroll.touch .inner {
    168   transition-duration: 0ms;
    169 }
    170 .yo-scroll.down .down-tip {
    171   display: block;
    172 }
    173 .yo-scroll.up .up-tip {
    174   display: block;
    175 }
    176 .yo-scroll.refresh .refresh-tip {
    177   display: block;
    178 }
    179 .yo-scroll .down-tip,
    180 .yo-scroll .refresh-tip,
    181 .yo-scroll .up-tip {
    182   display: none;
    183 }
    184 .yo-scroll .load-more {
    185   height: 1rem;
    186   display: flex;
    187   align-items: center;
    188   justify-content: center;
    189 }
    190 </style>
    View Code

    然后

    把上面组件拷贝一下,保存vue文件refresh.vue放到你的component/common文件夹下,  然后引入到页面 ,

    下面是引用我的demo

    <template>
      <kl-scroll :on-refresh="onRefresh" :on-infinite="onInfinite" :loading-text="loadingText">
        <section class="app-body container">
          <div class="container top30r record-table">
            <div class="record-header">
              <span class="label-time">提款时间</span>
              <span class="label-withdraw-amount">提现金额</span>
              <span class="label-arrival-amount">到帐金额</span>
              <span class="label-status">到账状态</span>
            </div>
            <div class="record-body">
              <div class="record-body-row" v-for="(item,index) in records" :key="index">
                <span class="time">{{item._created_at}}</span>
                <span class="withdraw-amount">{{item.withdraw_amount}}</span>
                <span class="arrival-amount">{{item.arrival_amount}}</span>
                <span
                  class="status"
                  :class="item.status == withdrawStatus.arrival ? 'label-green' : ''"
                >{{item._status}}</span>
              </div>
            </div>
          </div>
        </section>
      </kl-scroll>
    </template>
    
    <script>
    import api from "@/api";
    import qs from "qs";
    export default {
      name: "withdrawRecord",
      data() {
        return {
          withdrawStatus: {
            arrival: 1
          },
          records: [
            // {
            //   _created_at: "2019-03-07 15:20",
            //   withdraw_amount: "137854",
            //   arrival_amount: "13552.55",
            //   status: 1
            // }
          ],
          loadingText: "加载中...",
          page: 0, //当前页面
          num: 20, // 一次显示多少条
          listdata: [], // 下拉更新数据存放数组
          downdata: [] // 上拉更多的数据存放数组
        };
      },
      beforeCreate() {
        this.$loading.open();
      },
      mounted() {
        let vm = this;
        this.$nextTick(() => {
          vm.getList();
        });
      },
      methods: {
        onRefresh(done) {
          let _this = this;
          _this.counter = 1;
          _this.$el.querySelector(".load-more").style.display = "flex";
          _this.loadingText = "加载中……";
          _this.getList();
          done(); // call done
        },
        onInfinite(done) {
          let _this = this;
          let arr = [];
          for (var i = 0; i < 10; i++) {
            arr.push({
              _created_at: "2019-03-07 15:20",
              withdraw_amount: 155 + i,
              arrival_amount: "13552.55",
              status: 1,
              _status: "到賬"
            });
          }
          setTimeout(() => {
            _this.records = _this.records.concat(arr);
          }, 300);
    
          if (arr.length < _this.num) {
            _this.loadingText = "加载完毕……";
            //vm.$el.querySelector('.load-more').style.display = 'none';
            return;
          } else {
            _this.counter++;
          }
          done(); // call done
        },
        getList() {
          let _this = this;
          // let arr = [];
          // for (var i = 0; i < 40; i++) {
          //   arr.push({
          //     _created_at: "2019-03-07 15:20",
          //     withdraw_amount: 155 + i,
          //     arrival_amount: "13552.55",
          //     status: 1,
          //     _status: "到賬"
          //   });
          // }
    
          // _this.records = arr;
          // if (arr.length >= _this.num) {
          //   _this.counter++;
          // }
          let urlParams = {
            urlParams: {
              page: _this.page
            }
          };
          api.withdrawRecords(urlParams).then(res => {
            if (res.data) {
              let data = res.data.data;
              _this.records = data.records;
              if (_this.records.length == 0 || _this.records.length < _this.num) {
                _this.loadingText = "加载完毕……";
                _this.$el.querySelector(".load-more").style.display = "none";
              }
              _this.$loading.close();
            }
          });
        }
      }
    };
    </script>
    
    <style lang="scss" scoped>

    好啦 看下效果图

     

  • 相关阅读:
    Redis 主从复制
    LESSON THREE
    SSIS OLEDB COMMAND RULES
    Hadoop step by step _ install and configuration environment
    repcached的安装练习
    Check list
    简单对象定位——xpath定位
    简单对象定位
    Python webdriver API- 浏览器的操作
    第一个自动化脚本示例
  • 原文地址:https://www.cnblogs.com/yf-html/p/10553877.html
Copyright © 2011-2022 走看看