el-cascader 支持多层级,多选(可自定义限制数量),保留最后一级

news2025/2/24 16:15:09

多功能的 el-cascader

序言:最近遇到一个需求关于级联的,有点东西,这里是要获取某个产品类型下的产品,会存在产品类型和产品在同一级的情况,但是产品类型不能勾选;

  • 情况1(二级菜单是产品)
    在这里插入图片描述
  • 情况2(二级菜单也有可能是产品类型,三级是产品)
    在这里插入图片描述

需求如下:

  1. 支持多选且保留最后勾选项(不包含父级)
  2. 自定义限制勾选数量(这里最多3个)
  3. 层级不固定,有子级的才可以点击
  4. 父级不能勾选
  5. 返回给后端的参数需要将最后勾选的子级的lable和value值转为字符串以逗号分隔

实现方式

  1. 支持多选可用:props="{ checkStrictly: true, label: 'name', emitPath: false, multiple: true }" multiple: true 实现;
    不包含父级: :show-all-levels="false"

  2. 限制数量这个就比较有趣了,因为官网上的limit在这里没有用,所以得自己去写,需要在数量超过3个的时候 再点下一个的时候替换掉上次勾选那个,3个以下就直接拿数据就行,因为勾选层级不固定,可以选不同层级的,所以需要用递归去获取勾选的值,下面是数据结构:
    在这里插入图片描述

  3. 递归获取label值(最多3个,可修改):
    mainProductName:lable值 (字符串)
    mainProductOptions:级联的数据源
    findObjectsByKey:扁平化数组
    mainProductArr:value (数组字符串) 用来编辑时回显 很重要

    mainProductChange(val) {
      const textArr = [];
      if (val.length > 3) {
        val.splice(-2, 1);
        for (let i = 0; i < val.length; i++) {
          let itemValue = findObjectsByKey(this.mainProductOptions, 'id', val[i]);
          textArr.push(itemValue.name);
        }
        this.formData.mainProductName = textArr.join(',');
        this.$message.warning('最多只能选择三种产品');
        return val;
      } else {
        for (let i = 0; i < val.length; i++) {
          let itemValue = findObjectsByKey(this.mainProductOptions, 'id', val[i]);
          textArr.push(itemValue.name);
        }
        this.formData.mainProductName = textArr.join(',');
      }
      this.formData.mainProductArr = val;
    },
    
    //查找多层数组中的符合条件的item
    //arr 被查找的数组  key 查找的key  keyValue 查找的值
    export function findObjectsByKey(arr, key, keyValue) {
      //先把数组扁平化
      function flatten(arr, newarr) {
        //遍历arr数组
        for (var i = 0; i < arr.length; i++) {
          if (arr[i].children instanceof Array) {
            flatten(arr[i].children, newarr);
          } else {
            newarr.push(arr[i]);
          }
        }
        //返回新数组
        return newarr;
      }
      let newArr = flatten(arr, []);
      let itemValue = {};
      for (let item of newArr) {
        if (item[key] == keyValue) {
          itemValue = item;
          return itemValue;
        }
      }
      return itemValue;
    }
    
  4. 不能勾选是产品类型的父级(这里就需要对数据源做个处理),给是产品类型的数据加上 disabled,这时候就需要一个字段来判断了,后端配合一下,我这里用的是(isVariety)方法如下:

     traverseArray(arr) {
          arr.forEach(item => {
            item.disabled = item.isVariety == 0 ? true : false;
            item.value = item.id;
            if (item.children && item.children.length > 0) {
              this.traverseArray(item.children);
            }
          });
        },
    

    为了不修改源数据,所以用一个变量暂存一下

    getIndustryVarietyList({ isVariety: '' }).then(res => {
    	        if (res.data.data.length > 0) {
    	          let temp = res.data.data;
    	          this.traverseArray(temp);
    	          this.mainProductOptions = temp;
    	        }
    	      });
    
  5. 级联代码如下:

 <el-form-item label="主营产品:" prop="mainProductArr">
      <el-cascader
         ref="cascaderArr"
            style="width: 100%"
             v-model="formData.mainProductArr"
             :options="mainProductOptions"
              show-all-levels="false"
              placeholder="最多选择三种产品"
              clearable
              @change="mainProductChange"
              :props="{ checkStrictly: true, label: 'name', emitPath: false, multiple: true }"
                ></el-cascader>
              </el-form-item>
  1. 最后源码
	<template>
	  <div>
	    <el-form :model="formData" label-width="120px" :rules="formRules" ref="formData">
	      <el-col :span="10">
	        <el-form-item label="主营产品:" prop="mainProductArr">
	          <el-cascader
	            ref="cascaderArr"
	            style="width: 100%"
	            v-model="formData.mainProductArr"
	            :options="mainProductOptions"
	            :show-all-levels="false"
	            placeholder="最多选择三种产品"
	            clearable
	            @change="mainProductChange"
	            :props="{ checkStrictly: true, label: 'name', emitPath: false, multiple: true }"
	          ></el-cascader>
	        </el-form-item>
	      </el-col>
	    </el-form>
	  </div>
	</template>
	<script>
	export default {
	  data() {
	    return {
	      mainProductOptions: [],
	      // 表单数据
	      formData: {
	        mainProduct: '',
	        mainProductArr: [],
	        mainProductName: '',
	      },
	    };
	  },
	  created() {},
	  watch: {},
	  mounted() {
	    getIndustryVarietyList({ isVariety: '' }).then(res => {
	      if (res.data.data.length > 0) {
	        let temp = res.data.data;
	        this.traverseArray(temp);
	        this.mainProductOptions = temp;
	      }
	    });
	  },
	  methods: {
	    mainProductChange(val) {
	      const textArr = [];
	      if (val.length > 3) {
	        val.splice(-2, 1);
	        for (let i = 0; i < val.length; i++) {
	          let itemValue = findObjectsByKey(this.mainProductOptions, 'id', val[i]);
	          textArr.push(itemValue.name);
	        }
	        this.formData.mainProductName = textArr.join(',');
	        this.$message.warning('最多只能选择三种产品');
	        return val;
	      } else {
	        for (let i = 0; i < val.length; i++) {
	          let itemValue = findObjectsByKey(this.mainProductOptions, 'id', val[i]);
	          textArr.push(itemValue.name);
	        }
	        this.formData.mainProductName = textArr.join(',');
	      }
	      this.formData.mainProductArr = val;
	    },
	    traverseArray(arr) {
	      arr.forEach(item => {
	        item.disabled = item.isVariety == 0 ? true : false;
	        item.value = item.id;
	        if (item.children && item.children.length > 0) {
	          this.traverseArray(item.children);
	        }
	      });
	    },
	  },
	};

还有个不足就是不能把含有children的勾选框给去掉,有知道的大佬告诉教教我

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1824216.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Oracle生产运维】数据库服务器高负载排查处理

说明 在Oracle数据库运维工作中&#xff0c;经常会遇到Oracle数据库服务器平均负载&#xff08;load average&#xff09;突然异常升高&#xff0c;如果放任不管&#xff0c;严重的情况下会出现数据库宕机、服务器重启等重大故障。因此&#xff0c;当发现数据库服务器平均负载…

热门开源项目推荐:智谱GLM-4-9B和ChatGLM3-6B

目录 热门开源项目推荐&#xff1a;智谱GLM-4-9B和ChatGLM3-6B 1.引言 1.1 开源文化简介 1.2 开源项目的重要性 1.3 博客目的和读者价值 2.什么是开源项目&#xff1f; 2.1 开源定义 2.2 开源许可证类型 2.3 开源社区的作用 3.为什么程序员应该关注开源项目&#xff…

高精度减法的实现

这是C算法基础-基础算法专栏的第八篇文章&#xff0c;专栏详情请见此处。 引入 上次我们学习了高精度加法的实现&#xff0c;这次我们要学习高精度减法的实现。 高精度减法与高精度加法的定义、前置过程都是大致相同的&#xff0c;如果想了解具体内容&#xff0c;可以移步至我的…

WPF中的隧道路由和冒泡路由事件

文章目录 简介&#xff1a;一、事件最基本的用法二、理解路由事件 简介&#xff1a; WPF中使用路由事件升级了传统应用开发中的事件&#xff0c;在WPF中使用路由事件能更好的处理事件相关的逻辑&#xff0c;我们从这篇开始整理事件的用法和什么是直接路由&#xff0c;什么是冒…

【建设方案】文档管理系统实现方案(Word原件)

文档管理系统建设的主要意义在于提升组织内部文档管理的效率、安全性和便利性。首先&#xff0c;通过集中存储和分类管理&#xff0c;文档管理系统能够迅速检索和共享文件&#xff0c;大幅提高工作效率。其次&#xff0c;系统内置的权限控制功能确保文档的安全&#xff0c;防止…

OpenStack入门体验及一键部署

OpenStack入门体验 技能目标&#xff1a; 了解云计算概念 了解OpenStack 了解OpenStack的构成 会OpenStack单机环境一键部署 从控制台认识OpenStack各项功能会 通过OpenStack控制台创建云主机 什么是云计算 云计算(cloudcomputing)是一种基于网络的超级计算模式&a…

Nginx负载均衡之长连接负载均衡

当客户端通过浏览器访问 HTTP 服务器时&#xff0c;HTTP 请求会通过 TCP 协议与 HTTP 服务器建立一条访问通道&#xff0c;当本次访问数据传输完毕后&#xff0c;该 TCP 连接会立即被断开&#xff0c;由于这个连接存在的时间很短&#xff0c;所以 HTTP 连接也被称为短连接。 …

Python学习打卡:day06

day6 笔记来源于&#xff1a;黑马程序员python教程&#xff0c;8天python从入门到精通&#xff0c;学python看这套就够了 目录 day648、函数综合案例49、数据容器入门50、列表的定义语法51、列表的下标索引1、列表的下标&#xff08;索引&#xff09;2、列表的下标&#xff08…

2024 年最新使用 Node 搭建QQ开放平台官方 QQ 频道机器人详细教程(更新中)

注册 QQ 开放平台账号 QQ 开放平台是腾讯应用综合开放类平台&#xff0c;包含 QQ 机器人、QQ 小程序、QQ 小游戏 等集成化管理&#xff0c;也就是说你注册了QQ 开放平台&#xff0c;你开发 QQ 机器人还是 QQ 小程序都是在这个平台进行部署上线和管理。 如何注册 QQ 开放平台账…

代码随想录:回溯20-21

51.N皇后 题目 按照国际象棋的规则&#xff0c;皇后可以攻击与之处在同一行或同一列或同一斜线上的棋子。 n 皇后问题 研究的是如何将 n 个皇后放置在 nn 的棋盘上&#xff0c;并且使皇后彼此之间不能相互攻击。 给你一个整数 n &#xff0c;返回所有不同的 n 皇后问题 的解…

WDF驱动开发-同步技术

使用自动同步 基于框架的驱动程序中几乎所有的代码都驻留在事件回调函数中。 框架会自动同步驱动程序的大部分回调函数&#xff0c;如下所示&#xff1a; 框架始终将 常规设备对象、 功能设备对象 (FDO) 和 物理设备对象 (PDO) 事件回调函数同步&#xff0c;以便每个设备一次…

内网安全【2】-域防火墙

1.判断什么时候用代理 2.判断什么时候用隧道 3.判断出网和不出网协议 4.如何使用代理建立节点并连接 5.如何使用隧道技术封装协议上线 6.判断哪些代理或隧道情况选择放弃 代理技术&#xff1a;解决网络通讯不通的问题(利用跳板机建立节点后续操作)&#xff08;网络设置导…

【SpringBoot】深入分析 SpringApplication 源码:彻底理解 SpringBoot 启动流程

在黄昏的余晖里&#xff0c;梦境渐浓&#xff0c;如烟如雾。心随星辰&#xff0c;徜徉远方&#xff0c;岁月静好&#xff0c;愿如此刻般绵长。 文章目录 前言一、SpringBoot 应用二、SpringApplication2.1 SpringApplication 中的属性2.2 SpringApplication 的构造器2.3 Sprin…

高压消防接力泵的工作原理_鼎跃安全

森林消防工作是一项艰巨的任务&#xff0c;森林火灾具有蔓延快、控制难和燃烧剧烈等特点&#xff1b;同时&#xff0c;森林具有复杂的峡谷、山坡和陡峭等复杂情况&#xff0c;传统的消防设备难以深入火场&#xff0c;高压消防接力泵通过便携灵活性&#xff0c;深入火场助力消防…

【TF-IDF算法】

&#x1f3a5;博主&#xff1a;程序员不想YY啊 &#x1f4ab;CSDN优质创作者&#xff0c;CSDN实力新星&#xff0c;CSDN博客专家 &#x1f917;点赞&#x1f388;收藏⭐再看&#x1f4ab;养成习惯 ✨希望本文对您有所裨益&#xff0c;如有不足之处&#xff0c;欢迎在评论区提出…

基于LangChain-Chatchat实现的RAG-本地知识库的问答应用[2]-简洁部署版

基于LangChain-Chatchat实现的RAG-本地知识库的问答应用[2]-简洁部署版 1.环境要求 1.1 软件要求 要顺利运行本代码,请按照以下系统要求进行配置 已经测试过的系统 Linux Ubuntu 22.04.5 kernel version 6.7其他系统可能出现系统兼容性问题。 最低要求 该要求仅针对标准模…

C++的map

作用&#xff1a; 映射&#xff0c;相当于python的字典&#xff0c;使用一个key来寻找value&#xff0c;m[key]value; 生成&#xff1a; map<int,string> m;//无参生成&#xff0c;key是int类型&#xff0c;value是string类型 map<int,string> m{{1,"hello…

手把手教你入门vue+springboot开发(三)--登录功能后端

文章目录 前言一、redis安装二、后端代码1.修改application.yml文件2.增加utils文件3.增加Result类4.修改UserController类5.修改UserMapper类6.修改UserService和UserServiceImpl类7.增加LoginInterceptor类8.增加WebConfig类9.修改pom.xml文件 前言 前两篇我们用vuespringbo…

内网不能访问网站怎么办?

内网不能访问网站是在网络使用过程中常见的问题之一。当我们使用局域网连接时&#xff0c;有时候会遇到无法访问特定网站的情况。这可能是因为网络环境复杂&#xff0c;或者受到了某些限制。本篇文章将介绍一种解决内网不能访问网站问题的产品——天联组网。 天联组网是一款由…

非计算机专业可以考“软考”吗?

全国计算机软件水平考试对报名条件没有学历、资历、年龄以及专业等限制&#xff0c;非计算机专业的人员也可以报考。证书长期有效&#xff0c;考生可根据个人需求选择合适的级别和资格进行报考。报名方式包括网上报名和考生本人到指定地点报名两种。 考试范围 (1) 高级资格包括…