Element树实现懒加载

懒加载数据从后台传入

Posted by Ayi on September 23, 2018

前言

Element官网中有关于树的懒加载的写法,但是数据是写死在代码中的,在真正项目中,如果要从后台返回数据,然后懒加载到树上,官网就没有写了,因此只好自己探索了一下。

顺便提一下懒加载的好处就是,每次点击父节点的时候,才从后台get父节点下的子树的数据,再渲染到网页上,这样如果树的数据量很大的时候,不用一次get所有数据回来,能减轻前后端的负担

代码实现

<template>
  <div class="packet">
    <el-tree :data="treeData" :props="defaultProps" :load="loadNode" ref="tree" lazy node-key="value" highlight-current >
    </el-tree>
  </div>
</template>
<script>
import Api from '@/api/Index.js'
export default {
  name: 'PacKet',
  data () {
    return {
      treeData: [],
      defaultProps: {
        children: 'children',
        label: 'label',
        isLeaf: 'isLeaf'
      },
      serviceId: ''
    }
  },
  mounted () {
    this.getfindGroupTree()
  },
  methods: {
    getfindGroupTree () {
      this.serviceId = 1
      Api.getfindGroupTree(this.serviceId)
        .then(data => {
          let datas = data.data
          console.log(datas)
          if (data.status === 0) {
            this.treeData = data.data
            console.log(this.treeData)
          } else {
            this.$message({
              type: 'warning',
              message: '获取数据失败'
            })
          }
        })
        .catch(res => {
          this.$message({
            type: 'error',
            message: '获取数据失败'
          })
        })
    },
    loadNode (node, resolve) {
      if (node.level === 0) {
        return false
      }
      let arr = []
      Api.getfindGroupTree(node.data.value)
        .then(data => {
          console.log(node.data.value)
          if (data.status === 0) {
            let body = data.data
            if (body instanceof Array) {
              if (body.length !== 0) {
                // console.log(body)
                body.forEach((item) => {
                  arr.push({
                    id: item.value,
                    label: item.label,
                    isLeaf: leaf
                  })
                })
              } else {
                arr = []
                resolve([])
                return
              }
            } else {
              arr = []
            }
            let childData = arr
            setTimeout(() => {
              resolve(childData)
            }, 300)
          } else {
            this.$message({
              type: 'warning',
              message: '获取数据失败'
            })
          }
        })
        .catch(res => {
          this.$message({
            type: 'error',
            message: '获取数据失败'
          })
        })
    }
  }
}

</script>

主要思路就是第一次先传serviceId给后台,后台收到这个值的时候,一次性返回所有父树的数据回来,当点击某一个父树的时候,将node.data.value传入后台,后台收到这个值以后,再将这个组下的数据返回,然后前端使用resolve把数据渲染到子树上。

但是这里需要注意的是传给后台的值是node.data.后台返回的字段名,这里后台传给我的节点的唯一标识是value,如果后台传给的是id,那就应该写成node.data.id。 这里父树和子树后台传回的数据格式应该是一样的。

当然这里后台给我传的接口是localhost:8081/terminalGroup/findGroupTree2?serviceId=1,因此在第一次get父树的时候要定义serviceId,并传给后台。