Vue+Element实现给数据打标签操作(el-cascader结合el-tag)

默认效果:(只有一个按钮)

操作效果:(element级联选择框)

选中效果:(可添加多个标签)

在添加一个标签效果:(添加多个标签时,确保一级分类只能对应一种规格)

全部选中后效果:(全部一级选择后,按钮置灰,变更需删除标签后继续操作)

上代码仅测试使用,具体样式及业务逻辑,,需自行调整

HTML:

<template>
                <div style="display:flex;align-items: center;height:36px">
                  <!-- 已选择的标签 -->
                  <div v-if="selectedTags.length">
                    <el-tag
                      v-for="(tag, index) in selectedTags"
                      :key="index"
                      closable
                      @close="removeTag(index)"
                      v-show="tag.label"
                      style="margin-right:10px"
                    >{{ tag.label }}</el-tag>
                  </div>

                  <!-- 只有在没有选择标签时,显示 ➕ 按钮 -->
                  <el-button
                    v-if="selectedTags.length === 0 || !selectedTags[selectedTags.length - 1].showCascader "
                    size="mini"
                    icon="el-icon-plus"
                    @click="showNewCascader"
                    style="margin-left: 10px;"
                    type="primary"
                    :disabled="categories.length === selectedTags.length"
                  ></el-button>
                  <!-- 第一个 el-cascader -->
                  <!-- <div v-if="showFirstCascader">
                      <el-cascader
                        v-model="currentValue"
                        :options="categories"
                        :props="cascaderProps"
                        clearable
                        placeholder="请选择"
                        @change="handleChange"
                        style="display: inline-block; width: 200px"
                      />
                  </div>-->

                  <!-- 每次选择后新增的 el-cascader,点击每个标签的 ➕ 按钮后显示 -->
                  <div v-for="(tag, index) in selectedTags" :key="index">
                    <div v-if="tag.showCascader">
                      <el-cascader
                        v-model="tag.currentValue"
                        :options="categories"
                        :props="cascaderProps"
                        clearable
                        placeholder="请选择"
                        @change="handleSubChange(tag, index)"
                        style="display: inline-block; width: 200px;"
                      />
                    </div>
                  </div>
                </div>
              </template>

测试数据:

data() {
    return {
      selectedTags: [], // 存储选择的标签
      currentValue: [], // 当前的选择值
      categories: [
        {
          value: "standard", // 一级分类 code
          label: "标准", // 一级分类名称
          children: [
            { value: "gasoline", label: "汽油" }, // 二级分类
            { value: "diesel", label: "柴油" }
          ]
        },
        {
          value: "category", // 另一个一级分类
          label: "分类",
          children: [
            { value: "lubricant_oil", label: "润滑油" }, // 二级分类
            { value: "brake_oil", label: "刹车油" }
          ]
        }
      ],
      cascaderProps: {
        value: "value",
        label: "label",
        children: "children"
      },
  }
}

实现方法:

methods: {
    // 点击标签后的 ➕ 按钮,显示新的 cascader
    showNewCascader() {
      this.selectedTags.push({
        label: "",
        currentValue: [],
        showCascader: true
      });
    },

    // 选择后处理
    handleChange(value) {
      if (value && value.length > 0) {
        const selectedItem = this.getLabelByValue(value);
        this.selectedTags.push({
          label: selectedItem,
          value,
          showCascader: false
        });
        this.currentValue = []; // 清空当前的选择值
      }
    },

    // 根据选择的值获取显示的标签
    getLabelByValue(value) {
      for (let category of this.categories) {
        if (category.value === value[0]) {
          const child = category.children.find(c => c.value === value[1]);
          return child ? `${category.label}--${child.label}` : "";
        }
      }
      return "";
    },

    // 选择后更新标签
    handleSubChange(tag, index) {
      if (tag.currentValue && tag.currentValue.length > 0) {
        const selectedItem = this.getLabelByValue(tag.currentValue);
        this.selectedTags[index].label = selectedItem;
        //添加 置灰项
        this.categories.forEach(item => {
          if (item.value === tag.currentValue[0]) {
            item.disabled = true;
          }
        });
        this.selectedTags[index].showCascader = false;
      }
    },

    // 删除标签
    removeTag(index) {
      //删除后 置灰项可以再次被选择
      this.categories.forEach(item => {
        if (item.value === this.selectedTags[index].currentValue[0]) {
          item.disabled = false;
        }
      });
      this.selectedTags.splice(index, 1);
    },
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值