elementPlus + table 树形懒加载,子节点的刷新

需求描述

一个树形表格的增删查改

技术细节

刚开始想的很好,新增/编辑/删除时不调用接口,而是直接更改数据,如删除时,直接删除对应下标的数据
遇到的问题

  1. 实际业务中是否有子级,是不确定的-这个好解决,判断一下就行
  2. 通过load接口获取到的子项,使用proxy.$refs.table.store.states.lazyTreeNodeMap.value获取不到节点
  3. 通过proxy.$refs.table.store.states.treeData.value可以获取到节点数据,但是不能触发更新
  4. 最后使用了最简单的方式,新增,删除,编辑完成后,直接使用proxy.$refs.table.store.loadOrToggle(row)重新触发load调接口
<template>
  <div>

    <el-table :data="tableData1" style="width: 100%" row-key="id" border lazy :load="load"
      :tree-props="{ children: 'children', hasChildren: 'hasChildren' }" ref="table">
      <el-table-column prop="date" label="Date" />
      <el-table-column prop="name" label="Name" />
      <el-table-column prop="address" label="Address" />
      <el-table-column prop="address" label="Address" width="270">
        <template #default="scope">
           <el-button type="primary" size="small" @click="handleAdd(scope.row)">
            add
          </el-button>
           <el-button type="primary" size="small" @click="handleAdd2(scope.row)">
            add2
          </el-button>
          <el-button size="small" @click="handleEdit(scope.row)">
            Edit
          </el-button>
          <el-button size="small" type="danger" @click="handleDelete(scope.row)">
            Delete
          </el-button>
        </template>
      </el-table-column>
    </el-table>
  </div>
</template>
<script setup>
import {onMounted,ref,getCurrentInstance} from 'vue';
const {proxy} = getCurrentInstance();

const handleEdit = ((row) => {
  console.log(row)
})
const handleDelete = ((row) => {
  console.log(row)
})
const handleAdd = ((row) => {
console.log(proxy.$refs.table.store.states.treeData.value)
console.log(proxy.$refs.table.store.states.lazyTreeNodeMap.value)
 // proxy.$refs.table.store.states.treeData.value[row.id].loaded = false;
  proxy.$refs.table.store.states.treeData.value[row.id].loaded = false
  proxy.$refs.table.store.loadOrToggle(row)
})
const handleAdd2 = ((row) => {
  
})
const load = (
  row,
  treeNode,
  resolve
) => {
  console.log(row)
  setTimeout(() => {
    resolve([
      {
        id: `${row.id}_31`,
        date: '2016-05-01',
        name: 'wangxiaohu',
        address: 'No. 189, Grove St, Los Angeles',
        hasChildren: true,
      },
      {
        id: `${row.id}_32`,
        date: '2016-05-01',
        name: 'wangxiaohu',
        address: 'No. 189, Grove St, Los Angeles',
        hasChildren: true,
      },
    ])
  }, 1000)
}


const tableData1 = [
  {
    id: 11,
    date: '2016-05-02',
    name: 'wangxiaohu',
    address: 'No. 189, Grove St, Los Angeles',
    hasChildren: true,
  },
  {
    id: 2,
    date: '2016-05-04',
    name: 'wangxiaohu',
    hasChildren: true,
    address: 'No. 189, Grove St, Los Angeles',
  },
  {
    id: 3,
    date: '2016-05-01',
    name: 'wangxiaohu',
    hasChildren: true,
    address: 'No. 189, Grove St, Los Angeles',
  },
  {
    id: 4,
    date: '2016-05-03',
    name: 'wangxiaohu',
    hasChildren: true,
    address: 'No. 189, Grove St, Los Angeles',
  },
]
</script>

小结

关键点在于:proxy.$refs.table.store.loadOrToggle(row)

### Element Plus 表格组件触底加载更多数据 为了实现在 `Element Plus` 的 `table` 组件中当滚动到底部时自动加载更多的数据,可以采用监听表格容器的滚动事件来检测是否到达底部,并在此基础上触发新的数据请求。 通过自定义指令的方式绑定到 `el-table` 上是一个有效的方法[^2]。具体来说,在 Vue 组件内创建一个名为 `loadmore` 的自定义指令用于处理这一逻辑: ```javascript // 定义 loadmore 自定义指令 app.directive('loadmore', { mounted(el, binding) { let timer; function handleScroll() { clearTimeout(timer); const wrapper = el.querySelector('.el-table__body-wrapper'); if (wrapper.scrollTop + wrapper.clientHeight >= wrapper.scrollHeight - 10 && !binding.value.loading) { binding.value.loadMore(); } timer = setTimeout(() => { window.removeEventListener('scroll', handleScroll); }, 100); } window.addEventListener('scroll', handleScroll); // 清除事件监听器防止内存泄漏 el componentWillUnmount() { window.removeEventListener('scroll', handleScroll); }; }, }); ``` 接着是在模板部分应用此指令并设置相应的属性给它传递方法以及状态变量: ```html <template> <div> <!-- 使用 v-loadmore 指令 --> <el-table :data="tableData" @row-click="handleRowClick" v-loadmore="{ loading, loadData }"> ... </el-table> <!-- 加载指示符 --> <p v-if="loading">正在加载...</p> </div> </template> ``` 其中 `loading` 是布尔类型的响应式属性用来控制加载过程中的显示;而 `loadData()` 则是用来发起新一批次的数据请求函数。每当用户滚动接近页面末端时就会调用该函数去获取额外的信息填充至现有列表之中。 另外需要注意的是,如果希望在每次更新视图之后能够立即获得最新的 DOM 结构变化情况(比如新增加了一些行),那么可以在适当的位置利用 `nextTick` 来确保操作发生在下次DOM 更新循环结束之后[^1]。 例如,在完成一次异步加载后想要重新测量某些元素尺寸的情况下就可以这样做: ```javascript this.$nextTick(() => { // 此处可执行依赖于最新渲染结果的操作 }) ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值