记录实现级联选择器多选功能时主要用到的函数

news/2024/7/10 1:52:22 标签: 算法, 前端, 级联选择器多选, vue

级联选择器多选功能时主要用到的函数

1、校验所给层级是否有效并且是否为完整路径

// 功能:涉及到级联选择器回显时,需校验是否为完整的路径,是则回显,不是则无无效路径
// options为级联数据,selectedPaths为要校验的数据
validatePaths(selectedPaths, options) {
    let {originKeys} = this;
    let current = options;
    for (const value of selectedPaths) {
        if (!current) return false;
        const node = current.find(item => item[originKeys.value] === value);
        if (node) {
            current = node.children;
        } else {
            return false;
        }
    }
    // 校验是否为完整路径
    return this.isChange ? true : !current || current.length === 0;
},

2、查找元素父级

// 使用场景:如果所有子节点状态变成已选择,那么要找到父级将其状态也变成已选择,应用于回显以及操作节点时使用
// value为操作值,arr为级联数据
findParentByValue(value, arr) {
    let {originKeys} = this;
    let parent = null;

    const findParent = (items, parentObj) => {
        for (const item of items) {
            if (item[originKeys.value] === value) {
                parent = parentObj;
                break;
            }
            if (item.children) {
                findParent(item.children, item);
            }
        }
    };

    findParent(arr, null);
    return parent;
},

3、获取所有级别的路径

getAllLevelsPath() {
    let str = '';
    let {originKeys} = this;

    this.activeAry.forEach((item, index) => {
        str +=
            index < this.activeAry.length - 1
                ? item.active[originKeys.label] + this.separator
                : item.active[originKeys.label];
    });

    return str;
},

4、状态判断

// 判断各个项状态,需要根据子项的状态判断父级也需要根据父级状态判断子集
allCheckStatus() {
    if (this.options.every(item => !this.getIsNotDisabled(item))) {
        return 'disabled'
    } else if (this.allCheckTrue(this.options)) {
        return 'checked'
    } else if (this.hasCheckTrue(this.options)) {
        return 'indeterminate'
    } else {
        return 'unChecked'
    }
},
// 元素没有被禁用则返回true
getIsNotDisabled(item) {
    let {defaultDisabledItems, originKeys} = this;
    if (!this.isChange) {
        if (defaultDisabledItems.includes(item[originKeys.value])) {
            return false;
        }
        if (item.children && item.children.length > 0) {
            return item.children.some(child => this.getIsNotDisabled(child));
        }

        return true;
    } else {
        return !defaultDisabledItems.includes(item[originKeys.value])
    }
},
// 多选级联每一项元素的勾选状态
getCheckStatus(item) {
    if (!this.isChange) {
        if (!this.getIsNotDisabled(item)) {
            return 'disabled'
        } else if (!item.check &&
            (!item.children || !item.children.length || !this.hasCheckTrue(item.children))
        ) {
            return 'unChecked'
        } else if (!item.children || !item.children.length || this.allCheckTrue(item.children)) {
            return 'checked'
        } else {
            return 'indeterminate'
        }
    } else {
        return !this.getIsNotDisabled(item) ? 'disabled' : item.check ? 'checked' : 'unChecked'
    }
},
// 所有元素是否都被选择,包括孩子元素,剔除禁选元素
allCheckTrue(arr) {
    return arr.every(
        item => (item.check || !this.getIsNotDisabled(item)) &&
            (!item.children || !item.children.length || this.allCheckTrue(item.children)))
},
// 判断孩子元素中是否有被选择的,剔除禁选元素
hasCheckTrue(arr) {
    return arr.some(item => item.check &&
        this.getIsNotDisabled(item) ||
        (item.children && this.hasCheckTrue(item.children))
    );
},

5、给初始化的数组增加check属性

addCheckProperty(arr, ids, flag) {
    let {originKeys} = this;
    for (const item of arr) {
        if (ids.includes(item[originKeys.value])) {
            this.$set(item, 'check', flag);
            this.updataSelectedItems(item, flag)
        }
        if (item.children && item.children.length) {
            this.addCheckProperty(item.children, ids, flag);
        }
    }
},

6、元素没有被禁用则返回true

// 判断元素有没有被禁用,涉及父级全选以及回显功能
getIsNotDisabled(item) {
    let {defaultDisabledKeys, originKeys} = this;
    if (!this.isChange) {
        if (defaultDisabledKeys.includes(item[originKeys.value])) {
            return false;
        }
        if (item.children && item.children.length > 0) {
            return item.children.some(child => this.getIsNotDisabled(child));
        }

        return true;
    } else {
        return !defaultDisabledKeys.includes(item[originKeys.value])
    }
},

7、更新某一项

updataSelectedItems(item, flag) {
    let {originKeys} = this;
    this.$set(item, 'check', flag);

    if (item.children && item.children.length && !this.isChange){
        this.changeCheckProperty(item.children, flag);
    } else {
        if (flag) {
            // 未被禁选&&没有被选择的元素push到selectedItems
            this.getIsNotDisabled(item) &&
            !this.selectedItems.find(selectedItem => selectedItem[originKeys.value] === item.value) &&
            this.selectedItems.push(item)
        } else {
            // 过滤掉取消勾选的元素
            this.selectedItems = this.selectedItems.filter(
                val => val[originKeys.value] !== item[originKeys.value]
            )
        }
        // 拿到全路径
        if (this.isShowLevels) {
            let hierarchyArr = [];
            let selectedOptionsArr = []
            this.selectedItems.forEach(item => {
                hierarchyArr.push(
                    this.getSelectedOptionsWithPath(item[originKeys.value], this.options).hierarchy
                )
                selectedOptionsArr.push(
                    this.getSelectedOptionsWithPath(item[originKeys.value], this.options).selectedOptions
                )
            })
            this.selectedItemsAllPath = hierarchyArr
            this.activeItems = selectedOptionsArr
        }
    }
},

8、返回点击事件回传参数 以及全路径

//事件回传参数处理
getSelectedOptionsWithPath(val, options) {
    let {originKeys, separator} = this;
    let hierarchy = null;
    let selectedOptions = [];

    const findOption = (items, parentHierarchy) => {
        for (const item of items) {
            if (item[originKeys.value] === val) {
                let obj = {}
                obj[originKeys.value] = item[originKeys.value]
                obj[originKeys.label] = item[originKeys.label]
                selectedOptions.push(obj);
                hierarchy = parentHierarchy ?
                    `${parentHierarchy}${separator}${item[originKeys.label]}` :
                    item[originKeys.label];
                return true;
            }
            if (item.children && item.children.length) {
                const currentHierarchy = parentHierarchy ?
                    `${parentHierarchy}${separator}${item[originKeys.label]}` :
                    item[originKeys.label];
                const found = findOption(item.children, currentHierarchy);
                if (found) {
                    let obj = {}
                    obj[originKeys.value] = item[originKeys.value]
                    obj[originKeys.label] = item[originKeys.label]
                    selectedOptions.unshift(obj);
                    return true;
                }
            }
        }
        return false;
    };

    findOption(options, null);

    return {hierarchy, selectedOptions};
},

http://www.niftyadmin.cn/n/5313858.html

相关文章

Python基础知识:整理7 字典的定义及其相关操作

1 字典的定义 # 1. 字典的定义 # 定义字典的字面量 # {key: value, key: value, ......, key: value}# 定义字典变量 # my_dict {key: value, key: value, ......, key: value}# 定义空字典 # my_dict {} # my_dict dict()定义重复Key的字典 my_dict1 {"张三": …

性能优化--实战利用arthas排查java服务cpu占用过高的问题

使用jps -l查看目前的java应用进程 启动arthas&#xff0c;选择需要监控的进程 dashboar查看该应用整体情况 使用thread命令&#xff0c;查看占用cpu过高的几个线程ID 然后使用thread 线程ID查看具体线程在执行哪些内容&#xff0c;可以看到对应的类和方法 正在上传… 重…

【Python】对比嵌套JSON的不同

前言 此对比默认json arry中的顺序相同&#xff0c;在Python中即list中出现的顺序相同。将结果保存在对应的xx_ret中。 import json import os import string# 保存不同的字段 different_ret [] # 保存缺失的字段 lack_ret [] # 保存额外的字段 extra_ret []# 保存do_check…

生成式人工智能市场规模、趋势和统计数据(2024-2026)

生成式人工智能市场规模、趋势和统计数据&#xff08;2024-2026&#xff09; 目录 生成式人工智能市场规模、趋势和统计数据&#xff08;2024-2026&#xff09;一、生成式人工智能行业亮点二、生成式人工智能市场规模三、生成式人工智能市场增长预测四、生成式人工智能采用统计…

Python从入门到网络爬虫(OS模块详解)

前言 本章介绍python自带模块os&#xff0c;os为操作系统 operating system 的简写&#xff0c;意为python与电脑的交互。os 模块提供了非常丰富的方法用来处理文件和目录。通过使用 os 模块&#xff0c;一方面可以方便地与操作系统进行交互&#xff0c;另一方面页可以极大增强…

【实用工具指南 三】CHAT-GPT4接入指南

好消息&#xff0c;CHAT-GPT4终于开放订阅了&#xff0c;聪明的人已经先用上了&#xff0c;先上个图。 但是去订阅的时候发现银行卡验证不通过&#xff0c;后来一查必须是老美的州才行&#xff0c;于是买了个美元虚拟卡 接下来就比较简单&#xff0c;直接找客服把GPT的充值界…

arch modelsim 解决无法运行

13.0的quartus modelsim版本10.1d 是32位的 修改/etc/pacman.conf [multilib] Include /etc/pacman.d/mirrorlistpacman -Sy安装 lib32-l…

CVE-2023-36025 Windows SmartScreen 安全功能绕过漏洞

CVE-2023-36025是微软于11月补丁日发布的安全更新中修复Windows SmartScreen安全功能绕过漏洞。攻击者可以通过诱导用户单击特制的URL来利用该漏洞&#xff0c;对目标系统进行攻击。成功利用该漏洞的攻击者能够绕过Windows Defender SmartScreen检查及其相关提示。该漏洞的攻击…