antd design TreeSelect 改造

本文分享了如何改造antd design的TreeSelect组件,以支持单击、双击、三击复选框对应不同选择状态的功能。改造思路包括设置treeCheckStrictly属性以实现父子节点不联动,并通过onChange事件手动控制选中状态,利用递归算法处理节点选择逻辑。

antd design TreeSelect 改造

1.背景

对于部门树组件,需要支持三种操作: 点击一次复选框,表示选中当前节点及该节点下的所有子节点;点击二次,表示选中当前节点;点击三次,表示不选中当前节点

2.现状

​ 目前常见的操作:

​ 1.点击复选框时,选中当前节点及该节点下的所有子节点;

​ 2.取消复选框,取消当前节点及该节点下的所有子节点;

3.改造思路

首先把复选框改为不受控,即父节点和子节点不联动。通过treeCheckStrictly属性。 通过onChange事件,去手动控制选中的节点。

  1. 下面的代码片段,使用了递归算法,找出当前点击的父节点下,没有被选中的子节点及所有子节点
 // 获取没有被选中的子节点
  getChildNodeType = (children, value, noSelectedChildNode=[], allChildNode=[]) => {
    children.forEach((item)=> {
      const index = value.findIndex(obj => obj.value === item.props.id)
      // 没有选中则添加到没有选中的数组中
      index === -1 && (noSelectedChildNode.push({label: item.props.name, value: item.props.id})) 
      allChildNode.push(item.props.id)
      if (item.props.children && item.props.children.length > 0) { // 有孩子节点
        this.getChildNodeType(item.props.children, value, noSelectedChildNode, allChildNode)
      }
    })
    return {noSelectedChildNode, allChildNode}
  }
  1. 下面的代码片段讲解: 只拦截点击的是父节点。对叶子节点不予操作

​ 点击父节点时,如果子节点没有全部选中,则把没有选中的节点加入到所有选中的节点 ​ 再次点击父节点时,需要把所有的子节点从选中的节点中移除掉,并且需要把父节点加入到选中的节点中(父节点就会处于勾选状态)

​ 再次点击父节点时,不操作处理,父节点会主动取消勾选状态

 handleChange = (value, label, extra) => {
    // console.log('handleChangevalue========', value, label, extra)
    if (this.props.treeCheckStrictly && extra.triggerNode?.props?.children && extra.triggerNode?.props?.children.length > 0) { // 不是叶子节点
      const {noSelectedChildNode: noSelectedNode, allChildNode: allNode} = this.getChildNodeType(extra.triggerNode.props.children, value)
      // console.log('noSelectedChildNode=', noSelectedNode, 'allChildNode=', allNode)
      if (extra.checked) { // 父节点被选中
        if (noSelectedNode.length > 0 ) { // 子节点没有被全部选中,则选中全部子节点
          value = [...value, ...noSelectedNode]
        }
      } else { // 父节点不被选中
        if (noSelectedNode.length === 0 ) { // 子节点全部选中 ,则取消所有子节点
          value = value.filter(item => !allNode.includes(item.value))
          value.push({label: extra.triggerNode.props.name, value: extra.triggerNode.props.id}) // 选中当前父节点
        }
      }
    }
    this.setState({ value });

  };

作者: 咸鱼翻身

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值