element Table表格组件渲染不分页数据滚动加载不分页数据

该文介绍了两种在Vue.js应用中实现表格数据懒加载的方法。方法一是通过监听滚动事件,动态加载更多数据;方法二是使用ElementUI的自定义指令实现,当表格滚动到底部时加载更多数据。这两种方式都涉及到数据的分页和滚动事件处理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

方法一:

一、定义需要用到的变量 

data() {
  return {
    count: 19, // 默认展示条数
    tableData: [], // 表格数据
    allData: [] // 所有数据
  }
}

二、在进页面或打开弹窗时获取列表数据的地方处理成需要展示的数据

// 所有数据
this.allData = response.rows
// 初始值为19
this.needle = 19
this.tableData = []
//判断数据长度有没有20个,有就先添加20个,没有直接获取所有数据
if(this.allData.length > 19){
  for(let i = 0; i < 20; i++){
    this.tableData[i] = this.allData[i]
  }
} else {
    this.tableData = this.allData
}

 三、定义滚动加载函数 

lazyLoading(){
  // 获取table的body元素
  let dom = document.getElementById('table').querySelector('.el-table__body-wrapper')
  // console.log('dom', dom)
  // 添加对滚动条的监听
  dom.addEventListener('scroll', () => {
    const scrollDistance = dom.scrollHeight - dom.scrollTop - dom.clientHeight
    // console.log('鼠标滑动-scrollDistance', scrollDistance)
    if (scrollDistance <= 0 || scrollDistance <= 1) {
      let index = 0
      // 避免添加undefined数据导致表渲染报错
      if (this.needle === this.allData.length) {
        this.needle = 0
      }
      for (let i = this.needle; i < this.needle + 5; i++) {
        if (this.tableData[i]) {
          this.tableData[i] = this.allData[i]   
          this.$set(this.tableData, i, this.allData[i])
          this.$forceUpdate()
          index = i
        }
      }
      this.needle = index + 1
    }
  })
}

四、在mounted中设置监听鼠标滚动事件  

mounted() {
  this.lazyLoading()
},

方法二: 

element Table组件实现懒加载

(1)在项目 utils 文件夹下新建自定义指令文件 directives.js

import Vue from 'vue';
import { Message } from 'element-ui';

let oList = [], nList = [], dom, noMore = false, loading = false, isFirstUpdate = true // 原数组,表格渲染数组,dom节点

function LoadMore() {
  loading = true // 触底加载中
    if (oList.length <= 0 && !noMore) {
      noMore = true
      Message({
        type: 'warning',
        message: '数据已全部加载完毕',
        duration: 3000
      })
      loading = false
      return
    }  // 如果默认数据为0,return
    let list = []
    if (oList.length > 10) {
      list = oList.splice(0, 10)
    } else {
      list = oList.splice(0, oList.length)
    }
    for (let i = 0;i < list.length;i++) {
      nList.push(list[i])
    }
    loading = false
}
// 滚动事件
function handleScroll() {
  // 表格滚动条滚动的距离
  let scrollTop = dom.scrollTop
  // 变量windowHeight是可视区的⾼度
  let windowHeight = dom.clientHeight
  // 变量scrollHeight是滚动条的总⾼度
  let scrollHeight = dom.scrollHeight
  console.log('scrollTop---start')
  console.log(loading)
  console.log(scrollTop + windowHeight + 1)
  console.log(scrollHeight)
  if (scrollTop + windowHeight + 1 >= scrollHeight && !loading) {   // 这里就是滚动条滚动到底部的时候触发
    LoadMore()
  }
}

// 表格懒加载
Vue.directive('lazyLoad', {
  inserted: function(el, binding, vnode) {
    dom = vnode.componentInstance.bodyWrapper
    console.log(666)
  },
  update: function(el, binding, vnode){
    if(binding.value.oList && binding.value.nList) {
      oList = binding.value.oList
      nList = binding.value.nList
      console.log(777)
      console.log(oList)
      console.log(nList)
      if(nList.length <= 0) {
        LoadMore()
      }
      if(isFirstUpdate) {
        isFirstUpdate = false
        window.addEventListener('scroll', handleScroll, true)
      }
    }
  },
  unbind: function(el, binding, vnode) {
    console.log(999)
    oList = []
    nList = []
    noMore = false
    loading = false
    isFirstUpdate = true
    window.removeEventListener('scroll', handleScroll, true)
  }
});

(2)在main.js文件引入

import './utils/directives';

(3)在Table组件<el-table>标签加上这个 v-lazyLoad 属性 

v-lazyLoad="{'oList': defaultData.firstItemList, 'nList': modalForm.firstItemList}"

以下仅供参考 

data() {
  return {
    modalForm: new Form(),
    defaultData: {},
  }
},
methods: {
  /** 查询demo数据 */
  openModal() {
    this.loading = true
    getQmsIpqcTFirstStandardInfo(this.command.data.id).then(res => {
    if (res.data.firstItemList && res.data.firstItemList.length > 0 &&  res.data.firstItemList.length > 10) {
      this.defaultData = JSON.parse(JSON.stringify(res.data))
      let tableList = this.defaultData.firstItemList.splice(0, 10)
      res.data.firstItemList = tableList
     }
      this.loading = false
      this.modalForm = Object.assign(new Form(), res.data)
    })
  }
}
### 实现 `el-table` 组件滚动分页加载更多数据的方法 为了实现 `el-table` 的滚动分页加载功能,可以通过监听表格容器的滚动事件来动态触发数据加载逻辑。以下是具体实现方法: #### 1. 使用自定义指令绑定滚动事件 通过 Vue 自定义指令 `v-load-table-more` 来监听滚动行为,并判断是否到达底部以触发展开新数据的操作。 ```javascript Vue.directive('load-table-more', { bind(el, binding) { let throttleTimer; const handleScroll = () => { clearTimeout(throttleTimer); throttleTimer = setTimeout(() => { const scrollTop = el.scrollTop; const clientHeight = el.clientHeight; const scrollHeight = el.scrollHeight; if (scrollTop + clientHeight >= scrollHeight - 50 && !binding.value.loading) { binding.value(); } }, 200); // 防抖处理 }; el.addEventListener('scroll', handleScroll); // 解绑事件以防内存泄漏 el.__handleScroll__ = handleScroll; }, unbind(el) { el.removeEventListener('scroll', el.__handleScroll__); } }); ``` 此部分代码实现了防抖机制以及滚动到底部时调用回调函数的功能[^1]。 #### 2. 动态更新表格数据 在父组件设置一个异步方法用于模拟请求接口获取新的数据片段并追加到现有列表中。 ```javascript export default { data() { return { tableData: [], // 表格显示的数据集合 pageParams: { // 当前面参数对象 currentPage: 1, pageSize: 10, totalSize: 0 }, loading: false // 控制加载状态标志位 }; }, methods: { infiniteScrollLoad() { this.loading = true; this.pageParams.currentPage += 1; // 模拟网络延迟效果 setTimeout(async () => { try { const res = await fetch(`https://example.com/api/data?page=${this.pageParams.currentPage}&size=10`); const newData = await res.json(); if (!newData || newData.length === 0) { console.log("No more data"); return; } this.tableData.push(...newData); this.pageParams.totalSize += newData.length; } catch (error) { console.error(error.message); } finally { this.loading = false; } }, 800); } } }; ``` 上述代码展示了如何利用定时器模拟 API 请求过程,并将返回的新记录加入当前展示数组中的操作流程。 #### 3. 设置固定高度与开启虚拟滚动优化(可选) 如果预计总条目数较多,则建议启用 Element Plus 提供的 **虚拟滚动** 特性 (`max-height`) 或者手动控制 DOM 渲染范围减少性能消耗。 ```html <template> <div style="height: calc(100vh - 200px);"> <el-table ref="dataTable" :data="tableData" border height="calc(100%)" v-load-table-more="infiniteScrollLoad"> <!-- 列字段 --> <el-table-column prop="name" label="姓名"></el-table-column> <el-table-column prop="age" label="年龄"></el-table-column> </el-table> </div> </template> ``` 这里设置表格外层包裹 div 的高度为视窗减去一定偏移量,同时赋予表格本身百分比形式的高度值以便适应同分辨率下的布局需求。 --- ### 总结注意事项 - 如果项目中有多个类似的场景需要用到该功能,推荐封装成独立插件或者通用工具类库。 - 对于大数据集而言,除了采用无限滚定外还可以考虑其他策略比如懒加载、分批渲染等方式提升用户体验和系统效率[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

想散在风中

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值