vant van-pull-refresh + van-list实现list列表支持搜索和下拉刷新

news2024/9/27 7:25:11

1 介绍

在使用 van-pull-refresh + van-list实现list列表下拉刷新时遇到几个问题在这里进行一个总结。

2 出现的问题

问题一:当van-pull-refresh + van-list组合使用时,下拉刷新会调用两个加载图标。
解答:去除van-pull-refresh加载图标,防止下拉刷新时出现两个加载图标

      <!--  去除加载图标,防止下拉刷新时出现两个加载图标 -->
            <template #loading>
              <div></div>
            </template>

问题二: 通过筛选条件查询数据时,van-list会请求多次接口
解答:因为当this.finished = false时, 会触发 onLoad 事件,onLoad方法会调用一次fetchData方法,onRefresh方法也会调用fetchData方法这就使得你会调用两次接口。所以我们只好把查询单独写一个方法onSearch,然后在onLoad中判断是不是刷新操作,如果说是刷新就设置为false,只调用onload方法。

    onSearch() {
      this.medicalList = []
      this.pageIndex = 1
      this.finished = false
      this.loading = true
      this.refreshing = false
      this.fetchData()
    },
    onLoad() {
      if (this.refreshing) {
        this.medicalList = []
        this.refreshing = false
      }
      // 触底加载下一页数据
      // 网页刚打开也会触发一次
      this.fetchData()
    },
        // 下拉刷新
    onRefresh() {
      this.medicalList = []
      this.pageIndex = 1
      // finished 设置为 false 则会触发 onLoad 事件
      this.finished = false
      this.loading = true
      this.fetchData()
    },

3 结果展示

这个页面叫做TreatmentStation分为两部分:顶部的搜索和中间的内容。中间的内容是一个单独的组件(MedicalList),是TreatmentStation的子组件,父组件通过传值的方式将查询条件传给子组件,子组件调用接口获取数据,渲染至页面。
在这里插入图片描述

4 代码实现

TreatmentStation 组件

<template>
  <div id="treatment">
    <!-- 筛选条件 -->
    <div class="filter-criteria">
      <van-search
          v-model="model.keyword"
          placeholder="请输入患者姓名/就诊号"
          show-action
          @search="onSearch"
      >
        <template #action>
          <div style="display: flex; align-items: center;justify-content: center">
            <van-button size="small" type="info" @click="onSearch">搜索</van-button>
          </div>
        </template>
      </van-search>
      <van-dropdown-menu active-color="#1989fa">
        <van-dropdown-item ref="dateItem" v-model="model.appointTime" :title="model.appointTime.toString()">
          <van-datetime-picker
              v-model="currentDate"
              title="选择日期"
              type="date"
              @cancel="onCancelDate"
              @confirm="onConfirmDate"
          />
        </van-dropdown-item>
        <van-dropdown-item v-model="model.departmentName" :options="model.deptOption" @change="changeDropdown"/>
        <van-dropdown-item v-model="model.my" :options="model.myOption" @change="changeDropdown"/>
      </van-dropdown-menu>
    </div>
    <back-top/>
    <!-- list-->
    <medical-list ref="medicalList" :model="model"/>
  </div>
</template>

<script>
import moment from 'moment'
import MedicalList from './components/medical-list.vue'
import api from '../../api'
import BackTop from '../../components/back-top.vue'

export default {
  name: 'TreatmentStation',
  components: {BackTop, MedicalList},
  data() {
    return {
      model: {
        keyword: '',
        my: true,
        myOption: [
          {text: '我的', value: true},
          {text: '全部医师', value: false}
        ],
        departmentName: '',
        deptOption: [{text: '全部科室', value: ''}],
        appointTime: ''
      },
      medicalList: [],
      pageIndex: 1,
      currentDate: new Date()
    }
  },
  mounted() {
    //
    this.model.appointTime = moment().format('YYYY-MM-DD')
    const sessionModel = JSON.parse(sessionStorage.getItem('sessionModel'))
    if (sessionModel !== null) {
      this.model = sessionModel
    }
    this.getDepartList()
  },
  methods: {
    // 搜索确定
    onSearch(val) {
      this.$refs.medicalList.onSearch()
    },
    // 搜索框取消按钮
    onCancel() {
      // Toast('取消')
      this.$refs.medicalList.onSearch()
    },
    onConfirmDate(value) {
      this.model.appointTime = moment(value).format('YYYY-MM-DD')
      this.$refs.dateItem.toggle()
      this.$refs.medicalList.onSearch()
    },
    onCancelDate() {
      // 收起
      this.$refs.dateItem.toggle()
    },
    changeDropdown(value) {
      this.$refs.medicalList.onSearch()
    },
    // 获取所有科室
    getDepartList() {
      api.getDepartment().then(res => {
        this.model.deptOption = res.data.map(item => ({
          text: item.name,
          value: item.name
        }))
        this.model.deptOption.unshift({text: '全部科室', value: ''})
      }).catch(error => {
        console.log(error)
      })
    }
  },
  beforeRouteLeave(to, from, next) {
    // 当路由跳转到治疗页面时存储sessionModel
    if (to.name === 'treatmentContent') {
      sessionStorage.setItem('sessionModel', JSON.stringify(this.model))
    } else {
      sessionStorage.removeItem('sessionModel')
    }
    next()
  }
}
</script>

<style scoped>
#treatment {
  height: 100%;
}
</style>

MedicalList组件

<template>
  <div id="medical-list">
    <van-pull-refresh
        v-model="refreshing"
        :class="{'content': activeClass}"
        :offset="100"
        success-text="刷新成功"
        @refresh="onRefresh"
    >
      <!--  去除加载图标,防止下拉刷新时出现两个加载图标 -->
            <template #loading>
              <div></div>
            </template>
      <van-list
          v-model="loading"
          :finished="finished"
          finished-text="没有更多了"
          @load="onLoad"
      >
        <van-cell v-for="item in medicalList" :key="item.id"
                  :to="{
                    name:'treatmentContent',
                    params:{
                      medicalInfo_Id: item.id,
                      appointTime: model.appointTime,
                      patientName: item.patientName,
                      patient_Id: item.patient_Id
                    }
                  }"
                  is-link
                  style="text-align: left; align-items: center"
        >
          <template #title>
            <span style="margin-left: 10px">{{ item.patientName }}</span>
          </template>
          <template #label>
            <span style="margin-left: 10px">{{ '就诊号: ' + item.medicalNo }}</span>
          </template>
          <template #default>
            <span>{{ item.bedNumber ? '床号: ' + item.bedNumber : '' }}</span>
          </template>
          <template #icon>
            <van-icon name="contact-o" size="25px"/>
          </template>
        </van-cell>
      </van-list>
    </van-pull-refresh>
  </div>
</template>
<script>
import api from '../../../api'

export default {
  name: 'MedicalList',
  props: ['model'],
  data() {
    return {
      medicalList: [],
      loading: false,
      finished: false,
      refreshing: false,
      pageIndex: 1,
      pageSize: 50,
      pullRefreshDisabled: false
    }
  },
  methods: {
    // list列表方法
    onLoad() {
      if (this.refreshing) {
        this.medicalList = []
        this.refreshing = false
      }
      // 触底加载下一页数据
      // 网页刚打开也会触发一次
      this.fetchData()
    },
    // 下拉刷新
    onRefresh() {
      this.medicalList = []
      this.pageIndex = 1
      // finished 设置为 false 则会触发 onLoad 事件
      this.finished = false
      this.loading = true
      this.fetchData()
    },
    onSearch() {
      this.medicalList = []
      this.pageIndex = 1
      this.finished = false
      this.loading = true
      this.refreshing = false
      this.fetchData()
    },
    // 获取就诊信息数据
    fetchData() {
      api.query({
        'page.index': this.pageIndex,
        'page.size': this.pageSize,
        My: this.model.my,
        keyword: this.model.keyword,
        appointTime: this.model.appointTime,
        departmentName: this.model.departmentName
      }).then(res => {
        if (!res.data) return
        this.medicalList = this.medicalList.concat(res.data.rows)
        // 所有数据加载完成
        if (this.medicalList.length >= res.data.total) {
          this.finished = true
        } else {
          this.pageIndex++
        }
      }).catch(error => {
        console.log(error)
        this.finished = true
      }).finally(() => {
        this.refreshing = false
        this.loading = false
      })
    },
    bedNumber(value) {
      return value ? '床号:' + value : ''
    }
  },
  computed: {
    activeClass() {
      return this.medicalList.length <= 5
    }
  }
}
</script>
<style scoped>
#medical-list {
}

#medical-list .content {
  height: 80vh;
}
</style>

back-top组件
悬浮回到顶部按钮

<template>
  <!--  回到顶部悬浮按钮-->
  <div id="back-top">
    <van-sticky>
      <van-icon v-if="showBackTop" class="back-to-top" name="back-top" size="20px" @click="scrollToTop"/>
    </van-sticky>
  </div>
</template>
<script>
export default {
  name: 'BackTop',
  data() {
    return {
      showBackTop: false

    }
  },
  beforeDestroy() {
    window.removeEventListener('scroll', this.handleScroll)
  },
  mounted() {
    window.addEventListener('scroll', this.handleScroll)
  },
  methods: {
    handleScroll() {
      this.showBackTop = window.pageYOffset >= 300
    },
    scrollToTop() {
      window.scrollTo({top: 0, behavior: 'smooth'})
    }
  }
}
</script>

<style scoped>
#back-top .back-to-top {
  position: fixed;
  bottom: 50px;
  right: 30px;
  padding: 15px 15px;
  background-color: whitesmoke;
  color: black;
  border-radius: 25px;
  cursor: pointer;
  z-index: 1000;
}

</style>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2165821.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

leetcode-189:轮转数组

给定一个整数数组 nums&#xff0c;将数组中的元素向右轮转 k 个位置&#xff0c;其中 k 是非负数。 示例 1: 输入: nums [1,2,3,4,5,6,7], k 3 输出: [5,6,7,1,2,3,4] 解释: 向右轮转 1 步: [7,1,2,3,4,5,6] 向右轮转 2 步: [6,7,1,2,3,4,5] 向右轮转 3 步: [5,6,7,1,2,3,4…

快讯:腾讯轻量服务器四周年,最低一折续费,还有免费升配

最近腾讯云轻量服务器四周年庆开始了&#xff0c;免费升级配置&#xff0c;续费服务器最低一折。 最低一折续费&#xff1a; 持有多久的轻量服务器决定续费几折&#xff0c;已经持有四年就是一折&#xff0c;三年1.5折以此类推。 免费升级配置&#xff1a; 2-4-5免费升级到…

String类常用的方法

源代码&#xff1a; 输出结果&#xff1a;

Linux 之 logrotate 【日志分割】

简介 logrotate 是一个用于管理日志文件的工具。它可以自动对日志文件进行轮转、压缩、删除等操作&#xff0c;以防止日志文件无限增长占用过多磁盘空间。logrotate 通常作为一个守护进程定期运行&#xff0c;也可以通过 cron 任务来调度执行 工作原理 按照配置文件中的规则…

【Mysql多数据源实现读写分离的几种方案】

文章目录 一.什么是MySQL 读写分离二.读写分离的几种实现方式(手动控制)1.基于Spring下的AbstractRoutingDataSource1.yml2.Controller3.Service实现4.Mapper层5.定义多数据源6.继承Spring的抽象路由数据源抽象类&#xff0c;重写相关逻辑7. 自定义注解WR&#xff0c;用于指定当…

客户端数JSON据库SQL操作功能实现代码-———未来之窗行业应用跨平台架构

一、前端json结构化查询优点 以下是前端本地化查询的一些优点&#xff1a; 1. 快速响应&#xff1a;无需通过网络请求从服务器获取数据&#xff0c;查询结果能够立即返回&#xff0c;提供了几乎零延迟的用户体验&#xff0c;使应用更加流畅和响应迅速。 2. 离线可用性&#x…

9.4 Linux_I/O_访问目录、文件属性

访问目录 1、打开关闭目录 打开目录函数声明如下&#xff1a; //1.直接打开指定路径的目录文件 DIR *opendir(const char *name); //2.先用open打开目录文件&#xff0c;再用该函数访问目录文件 DIR *fdopendir(int fd); 返回值&#xff1a;成功返回指向打开的目录文件的结…

ELK-05-skywalking监控SpringCloud服务日志

文章目录 前言一、引入依赖二、增加日志配置文件三、打印日志四、skywalking网页查询链路五、日志收集5.1 修改logback-spring.xml5.2 重启SpringCloud服务并请求test接口5.3 查看skywalking网页的Log 总结 前言 基于上一章节&#xff0c;现在使用skywalkin监控SpringCloud服务…

JWT令牌技术介绍及使用

一、JWT介绍 JWT是JSON Web Token的缩写&#xff0c;即JSON Web令牌&#xff0c;是一种自包含令牌。 是为了在网络应用环境间传递声明而执行的一种基于JSON的开放标准。 JWT的声明一般被用来在身份提供者和服务提供者间传递被认证的用户身份信息&#xff0c;以便于从资源服务…

D. Determine Winning Islands in Race (cf div2,dp、图论最短路)

D. Determine Winning Islands in Race 思路: bfs找到E到达每个点的最短时间t[i]。 如果E要超过B&#xff0c;那么一定要借助辅助桥&#xff0c;从而获胜。 假设有u->v的辅助桥&#xff0c;E能通过这个桥超过B的条件是: s>u 且 t[v] < v-s 即 s的取值要为[u1,v-t[v]-…

C++核心编程和桌面应用开发 第七天(运算符重载 智能指针)

目录 1.数组类 2.运算符重载 2.1加号运算符 2.1.1成员函数实现 2.1.2全局函数实现 2.1.3加号重载 2.2左移运算符 2.3递增运算符 2.4指针运算符 2.5赋值运算符 1.数组类 //默认构造函数 MyArray::MyArray() {m_Size 0;m_Capacity 100;pAddress new int[m_Capacity]…

【有啥问啥】深度解析迁移学习(Transfer Learning)

深度解析迁移学习&#xff08;Transfer Learning&#xff09; 在机器学习领域&#xff0c;迁移学习&#xff08;Transfer Learning&#xff09;作为一种强大的技术&#xff0c;正广泛应用于各种实际场景中。本文将详细解析迁移学习的基本概念、原理、分类、应用场景以及具体实…

vue3中storeToRefs让store中的结构出来的数据也能变成响应式

1、首先需要安装pinia 具体安装和使用教程参考 2、创建 src/stores/counter.js 文件&#xff0c;其内容如下&#xff1a; import {defineStore} from "pinia"; import {ref} from "vue";export const useCounterStore defineStore(counter,()>{const…

C语言程序设计题目十九:编写一万年历系统

文章目录 题目十九&#xff1a;编写一万年历系统calendar.hcalendar.ctest.c 题目十九&#xff1a;编写一万年历系统 要求&#xff1a; 模仿现实中的挂历&#xff0c;显示当前月的每一天及星期几&#xff0c;当系统日期变为下一个月时&#xff0c;自动翻页到下一个月。 calend…

【第3期】INFINI Easysearch 免费认证培训开放报名

探索 Easysearch 的无限可能&#xff0c;与 INFINI Labs 共赴搜索技术前沿&#xff01; 随着数字化转型的加速&#xff0c;搜索技术已成为企业数据洞察的核心。INFINI Labs 作为搜索创新技术的引领者&#xff0c;诚邀所有对 Easysearch 搜索引擎感兴趣的开发者、技术爱好者及合…

安卓13禁止待机 永不休眠 android13永不休眠

总纲 android13 rom 开发总纲说明 文章目录 1.前言2.问题分析3.代码分析4.代码修改5.彩蛋1.前言 设置 =》显示 =》屏幕超时 =》 永不。 我们通过修改系统待机时间配置,来达到设置屏幕超时的配置。像网上好多文章都只写了在哪里改,改什么东西,但是实际上并未写明为什么要改那…

[智能控制】【第2 章 模糊控制的理论基础】

目录 第2章 模糊控制的理论基础 2.1 概述——模糊控制的提出 2.1 概述——模糊控制的特点 2.2 模糊集合 2.2.1 模糊集合 1 特征函数和隶属函数 2 模糊集合的表示 例2.1 例2.2 2.2.2 模糊集合的运算 1 模糊集合的基本运算 &#xff08;1&#xff09;空集…

docker搭建clickhouse并初始化用户名密码

1、新建挂载目录 mkdir -p /home/clickhouse-server/ mkdir -p /home/clickhouse-server/etc/2、拉取镜像 docker pull clickhouse/clickhouse-server3、创建临时容器 docker run -d --rm --name clickhouse-server --ulimit nofile262144:262144 clickhouse/clickhouse-ser…

目标检测流程

流程概述 背景&#xff1a;梳理目标检测标注&#xff0c;训练&#xff0c;部署全流程。供后续初学者快速上手 方案&#xff1a;Ubuntu&#xff08;PC端&#xff09;进行标注&#xff0c;基于OpenMMLab进行训练得到pt模型&#xff0c;pt模型通过转换rknn并部署。 1. 数据集 公…

成都睿明智科技有限公司可靠吗?

在这个短视频风靡的时代&#xff0c;抖音已不仅仅是一个娱乐平台&#xff0c;它更是无数商家眼中的蓝海市场&#xff0c;是电商领域的新宠儿。在这场流量与转化的盛宴中&#xff0c;成都睿明智科技有限公司以其敏锐的市场洞察力和专业的服务能力&#xff0c;正逐步成为抖音电商…