实现下拉刷新功能

下拉刷新主要用于移动端网页,PC端网页并没有 touch 事件所以需要自行模拟。实现该功能主要依赖如下几个事件:

  • touchstart
  • touchmove
  • touchend

从事件名我们很容易就能看出这几个事件分别代表什么含义。在事件回调函数里面,可以获取 touchList,该 list 中的每一个元素表示一个触摸点的信息。可以看出,触摸事件可以监听到多个触摸点,例如多个手指滑动屏幕就会有多个触摸点。实现下来刷新功能,我们只考虑一个触摸点即可。

思路

下拉刷新的思路很简单:

  1. 触摸开始时保存初始触摸点在屏幕上的坐标
  2. 触摸移动时计算移动的触摸点和初始坐标点的距离,如果距离大于阈值,则触发刷新回调
  3. 触摸结束后重置触摸状态

值得注意的是,在 touchmove 的时候,计算下拉距离的同时也要显示下拉加载提示元素,具体思路就是设置提示元素的 min-height,设置 min-height 使动画生效。

<html>

<head>
    <title>Pulldown refreshtitle>
    <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0">
    <style>
        body {
            margin: 0;
            background-color: #eee;
        }

        #tip-wrap {
            height: 0;
            overflow: hidden;
            text-align: center;
            background-color: #ccc;
            font-size: 0.9rem;
            color: white;
            display: flex;
            align-items: center;
            justify-content: center;
            width: 100%;
            pointer-events: none;
            transition: min-height 0.2s ease;
        }
    style>
head>

<body>
    <div id="tip-wrap">
        <div id="tip">松开刷新div>
    div>

    <div id="wrap">
        Lorem ipsum dolor sit amet consectetur adipisicing elit. Similique delectus dolores dolore commodi minus,
        corrupti, veritatis totam repudiandae facilis dolorum beatae labore nesciunt vel fugit illum quo distinctio
        praesentium accusamus.
    div>

    <script>
        let state = undefined // start | moving | end
        let touchStartY = undefined;
        let touchTrigger = 100;
        let dist = 0
        const tip = document.querySelector('#tip-wrap')
        const tipmsg = document.querySelector('#tip')
        const wrap = document.querySelector('#wrap')

        window.addEventListener('touchstart', (e) => {
            console.log('touchstart', e.touches)
            if (!window.scrollY)
                touchStartY = e.touches[0].screenY;
            state = 'start'
        }, false)

        window.addEventListener('touchmove', (e) => {
            // console.log('touchmove', e.touches)
            const screenY = e.touches[0].screenY

            if (state === 'start') {
                touchStartY = screenY
                state = 'moving'
            }

            dist = screenY - touchStartY

            if (dist > 0) {
                e.preventDefault();
                tip.style.minHeight = Math.min(dist, 50) + 'px'
            }
        }, { passive: false })

        window.addEventListener('touchend', (e) => {
            console.log('touchend', e.touches)
            if(dist >= 50 && !window.scrollY) {
                alert('refresh')
            }
            touchStartY = 0
            tip.style.minHeight = 0
        }, false)
    script>
body>

html>

注意addEventListener('touchmove', cb, { passive: false }) { passive: false } 能达到下拉页面时页面不会整体向下移动的效果。

你可能感兴趣的:(前端,javascript)