Results show

Sweep code experience

Click to visit the demo address click to view the source code

background

Pull-down refresh is a function that is often used on mobile terminals. After looking at various UI libraries, I wanted to play with them and study the principle, so I got this example.

A page frame

<template>
  <div class="pullDown">
    <! --loading-->
    <div class="pullDown__loading"></div>
    <! --scroll content-->
    <div class="pullDown__scroll">
        <ul class="pullDown__list"></ul>
    </div>
  </div>
</template>

Copy the code

Basic page Style

.pullDown{
    background-color: #fff;
    position: absolute;
    z-index: 1;
    width: 100%;
    height: 100%;
    overflow-y: scroll;
    /* Add this property to increase elasticity */
    -webkit-overflow-scrolling: touch;
    transform: translate3d(0, 0, 0);
    -webkit-transform: translate3d(0, 0, 0);    
}
.pullDonw__loading{
    position: absolute;
    left: 0;
    top: 0;
    display: block;
    overflow: hidden;
    width: 100%;
    height: 50px;
    text-align: center;
    padding: 16px 24px; 
    z-index: 2;
    background-color: #fff;
}
.pullDown__scroll{
    position: relative;
    z-index: 10;
    background-color: #fff;
    border-bottom: 1px solid #e8e8e8;
    border-top: 1px solid #e8e8e8;
}
Copy the code

The core to realize

The pull-down refresh is judged by the three events of TouchStart, Touchmove and touchend.

  1. When touchStar is triggered, judge the refresh state and the situation when the container reaches the top, otherwise record the current position information and set the pull-able state;
  2. When touchemove is triggered, judge the refresh state and pulleable state, and the current moving position should be greater than the starting position, then set the container to scroll with the finger;
  3. When touchend is triggered, there are two situations to judge the refresh state and animation:
    • If the pull distance exceeds the refresh condition, the animation is executed and the refresh action is performed
    • If the pull distance does not exceed the refresh condition, return to the original state
touchstart($event) {
    var vm= this;
    // Determine whether pull-down is allowed
    if(! vm.isPull && ! vm.isLoading && vm._scrollWrap.scrollTop == vm.offsetTop) { vm.isPull=true;
      vm.startPos= $event.touches[0].pageY;
    };
},
touchmove($event) {
    var vm= this;
    vm.endPos= $event.touches[0].pageY;
    
    // Whether it can be pulled
    if(! vm.isLoading && vm.isPull && vm.startPos<vm.endPos) { vm.distance= (vm.endPos- vm.startPos)*vm.modulus;var offsetLoading= vm._loadingWrap.offsetHeight;
    
      if (vm.distance >= offsetLoading) {
        vm.pullStatus = 'up'
      }else{
        vm.pullStatus = 'down'
      }
      vm.moveTransition(vm.$refs.scroll, vm.distance, 0);
    }
},
touchend($event) {
    var vm= this;
    var offsetLoading= vm._loadingWrap.offsetHeight;
    // vm.isPull= false;
    
    // Cannot move while loading or when moving distance is less than 0
    if (vm.isLoading || vm.distance<=0 || vm.isBack) {return false; }// Pull distance is greater than the critical value
    if ( vm.distance>0 && vm.distance >= offsetLoading) {
    
      // Perform a refresh
      vm.pullTransition({
        dom: vm._scrollWrap,
        begin: offsetLoading,
        end: vm.distance,
        duration: 500
      });
    
      // Refresh data in the background
      vm.refresh();
    }else{
    
      vm.isBack= true;
      // Return to the initial state of back
      vm.pullTransition({
        dom: vm._scrollWrap,
        end: vm.distance,
        duration: 500.callback: vm.resetStatus }); }}Copy the code

Pull down the drawing to achieve

Using CSS animation, it is difficult to accurately grasp the end time of animation. So we use RequestAnimationFrame to implement the animation, which listens to the end state and handles the callback. Refer to the following information about requestAnimationFrame:

  • requestAnimationFrame
  • CSS3 animation is so strong, requestAnimationFrame is still used?
/** * [pullTransition animation pull] * @param {[type]} dom [element] * @param {[type]} begin [start value] * @param {[type]} end [end value] * @param {[type]} duration [time] * @param {[type]} callback [callback function] * @return {[type]} [description] */
pullTransition(opt) {
    var vm= this;
    if(! opt.dom || ! opt.end) {console.error('Insufficient parameters');
      return false;
    };
    
    var opt= {
      dom: opt.dom,
      currentTime: 0.begin: opt.begin? opt.begin: 0.end: opt.end,
      // Quite a few browsers have a display frequency of 16.7ms equal to about 17
      duration: opt.duration? Math.ceil(opt.duration / 17) : 0.callback: opt.callback || false
    };
    
    var step= function() {
    
      // Get the value according to the slow algorithm
      var value = opt.end-vm.easeInOut(opt.currentTime, opt.begin, opt.end-opt.begin, opt.duration)+opt.begin;
      opt.dom.style.transform= 'translate3d(0,'+value+'px,0)';
    
      opt.currentTime++;
    
      // Check whether the time is up
      if (opt.currentTime <= opt.duration) {
           // Keep moving
           requestAnimationFrame(step);
      } else {
          // End of animation
          if(opt.callback) opt.callback(); }}; step(); }/**
* [Linear ็ผ“ๅŠจ็ฎ—ๆณ•]
* @param {[type]} t [current time๏ผˆๅฝ“ๅ‰ๆ—ถ้—ด๏ผ‰]
* @param {[type]} b [beginning value๏ผˆๅˆๅง‹ๅ€ผ๏ผ‰]
* @param {[type]} c [change in value๏ผˆๅ˜ๅŒ–้‡๏ผ‰]
* @param {[type]} d [duration๏ผˆๆŒ็ปญๆ—ถ้—ด๏ผ‰]
*/
easeInOut(t, b, c, d) {
    if ((t /= d / 2) < 1) return c / 2 * t * t*t + b;
    return c / 2*((t -= 2) * t * t + 2) + b;      
}
Copy the code

Wechat drop down display url processing

When opening a page on wechat, the situation as shown in the picture below will appear when you pull down the page at the top. The experience is poor for the drop-down refresh. I searched on the Internet to find two ways to deal with, for your reference. This example adopts the first method. As for the basis of adoption, there is no in-depth comparison at present, and further investigation will be conducted in the future.

  • Wechat inside to prevent pulling down the “bottom” component
  • prevent-overscroll


At this point, the drop-down refresh function is complete, any comments and suggestions are welcome.