当前位置: 首页 > news >正文

【Vue3 Element UI - Plus + Tyscript 实现Tags标签输入及回显】

Vue3 + Element Plus + TypeScript 实现 Tags 标签输入及回显

在开发后台管理系统或表单页面时,动态标签(Tags) 是一个常见的功能需求。用户可以通过输入框添加标签,并通过关闭按钮删除标签,同时还需要支持标签数据的提交和回显。本文将详细介绍如何使用 Vue 3Element PlusTypeScript 实现这一功能。我们的CSDN发布一栏也是相同的功能。
在这里插入图片描述
在这里插入图片描述


1. 功能需求

我们需要实现以下功能:

  1. 动态添加标签:用户可以通过输入框添加新的标签。
  2. 动态删除标签:用户可以点击标签的关闭按钮删除标签。
  3. 标签数据提交:将标签数据绑定到表单的 productsLabel 字段,随表单一起提交。
  4. 标签数据回显:在编辑表单时,从接口获取已保存的标签数据并展示。

2. 技术实现

官网上也有实现方式 https://element-plus.org/zh-CN/component/tag.html
在这里插入图片描述

2.1 动态标签的实现

动态标签的核心是通过 v-for 渲染标签列表,并使用 el-tag 组件展示标签。用户可以通过输入框添加新标签,并通过关闭按钮删除标签。

关键代码
<el-form-item label="产品标签" prop="productsLabel"><el-tagv-for="tag in dynamicTags":key="tag"class="mx-1"closable:disable-transitions="false"@close="handleClose(tag)">{{ tag }}</el-tag><el-inputv-if="inputVisible"ref="InputRef"v-model="inputValue"class="ml-1 w-20"@keyup.enter="handleInputConfirm"@blur="handleInputConfirm"/><el-button v-else class="button-new-tag ml-1" @click="showInput">+ 添加产品标签</el-button>
</el-form-item>
代码解析
  1. el-tag 组件

    • 使用 v-for 遍历 dynamicTags 数组,渲染已添加的标签。
    • closable 属性为标签添加关闭按钮,点击关闭按钮时触发 handleClose 方法。
  2. el-input 组件

    • inputVisibletrue 时,显示输入框,用户可以在输入框中输入新标签。
    • 输入框支持按下回车键(@keyup.enter)或失去焦点(@blur)时触发 handleInputConfirm 方法,将输入的内容添加到标签列表。
  3. el-button 组件

    • inputVisiblefalse 时,显示“添加产品标签”按钮,点击按钮后显示输入框。

2.2 标签的添加与删除

标签的添加和删除通过以下方法实现:

关键代码
const inputValue = ref('') // 输入框的值
const dynamicTags = ref<string[]>([]) // 动态标签数组
const inputVisible = ref(false) // 控制输入框的显示
const InputRef = ref<InstanceType<typeof ElInput>>() // 输入框的引用// 删除标签
const handleClose = (tag: string) => {dynamicTags.value.splice(dynamicTags.value.indexOf(tag), 1)formData.value.productsLabel = dynamicTags.value // 同步到表单数据
}// 显示输入框
const showInput = () => {inputVisible.value = truenextTick(() => {InputRef.value!.input!.focus() // 自动聚焦输入框})
}// 确认输入
const handleInputConfirm = () => {if (inputValue.value) {dynamicTags.value.push(inputValue.value) // 添加新标签formData.value.productsLabel = dynamicTags.value // 同步到表单数据}inputVisible.value = false // 隐藏输入框inputValue.value = '' // 清空输入框
}
代码解析
  1. handleClose 方法

    • dynamicTags 数组中删除指定的标签。
    • 将更新后的标签数组同步到表单的 productsLabel 字段。
  2. showInput 方法

    • 显示输入框,并通过 nextTick 确保输入框渲染完成后自动聚焦。
  3. handleInputConfirm 方法

    • 将输入框的值添加到 dynamicTags 数组中。
    • 将更新后的标签数组同步到表单的 productsLabel 字段。
    • 隐藏输入框并清空输入框的值。

2.3 标签数据的回显

在编辑表单时,需要从接口获取已保存的标签数据并回显到页面上。

关键代码
const open = async (type: string, id?: number) => {dialogVisible.value = truedialogTitle.value = t('action.' + type)formType.value = typeresetForm()if (id) {formLoading.value = truetry {formData.value = await ProductsApi.getProducts(id) // 获取表单数据dynamicTags.value = formData.value.productsLabel || [] // 回显标签数据} finally {formLoading.value = false}}
}
代码解析
  1. open 方法
    • 打开表单弹窗时,如果是编辑模式(id 存在),则调用接口获取表单数据。
    • 将接口返回的 productsLabel 字段赋值给 dynamicTags,实现标签数据的回显。

2.4 标签数据的提交

标签数据通过 formData.productsLabel 字段随表单一起提交。

关键代码
const submitForm = async () => {try {await formRef.value.validate() // 表单验证formLoading.value = trueconst data = formData.value as unknown as ProductsVOif (formType.value === 'create') {await ProductsApi.createProducts(data) // 创建产品} else {await ProductsApi.updateProducts(data) // 更新产品}dialogVisible.value = falseemit('success') // 提交成功后触发事件} catch (error) {console.error('表单提交失败:', error)message.error(t('common.submitFailed'))} finally {formLoading.value = false}
}
代码解析
  1. submitForm 方法
    • 在表单提交时,formData.productsLabel 字段会包含用户添加的所有标签数据。
    • 根据 formType 的值,调用创建或更新接口,将标签数据提交到后端。

3. 注意事项

  1. 标签去重

    • handleInputConfirm 方法中,建议添加去重逻辑,避免用户输入重复的标签。例如:
      if (inputValue.value && !dynamicTags.value.includes(inputValue.value)) {dynamicTags.value.push(inputValue.value)
      }
      
  2. 输入框验证

    • 可以为输入框添加验证规则,限制标签的长度或内容格式。例如:
      • 限制标签长度:if (inputValue.value.length > 10) { message.error('标签长度不能超过10个字符') }
      • 限制特殊字符:使用正则表达式检查输入内容是否合法。
  3. 性能优化

    • 如果标签数量较多,建议使用虚拟滚动(Virtual Scroll)技术优化渲染性能,避免页面卡顿。
    • 可以使用 el-tageffect 属性(如 darklight)优化标签的视觉效果。
  4. 用户体验优化

    • 在用户输入标签时,提供实时提示(如“按回车键添加标签”),提升交互体验。
    • 在标签数量较多时,可以添加滚动条或分页功能,避免页面布局混乱。
  5. 国际化支持

    • 使用 useI18n 实现标签相关文本的国际化,确保多语言环境下功能正常。例如:
      const { t } = useI18n()
      const addTagText = t('form.addTag') // 添加标签
      const tagLimitText = t('form.tagLimit') // 标签长度不能超过10个字符
      
  6. 数据同步

    • 确保 dynamicTagsformData.productsLabel 的数据同步,避免表单提交时遗漏标签数据。
    • 在编辑模式下,从接口获取数据后,及时将 productsLabel 赋值给 dynamicTags,确保标签正确回显。
  7. 错误处理

    • 在标签添加或删除时,增加错误处理逻辑。例如,如果标签添加失败,可以显示错误提示并恢复原有状态。
  8. 浏览器兼容性

    • 测试不同浏览器下的表现,确保功能在主流浏览器(如 Chrome、Firefox、Safari)中正常运行。

4. 总结

通过以上实现,我们完成了动态标签的添加、删除、提交和回显功能。这个功能的核心在于:

  • 使用 v-for 动态渲染标签列表。
  • 通过 el-inputel-tag 实现标签的输入和展示。
  • 将标签数据绑定到表单的 productsLabel 字段,实现数据的提交和回显。

希望这篇文章对你有帮助!如果有任何问题,欢迎在评论区留言讨论~

相关文章:

【Vue3 Element UI - Plus + Tyscript 实现Tags标签输入及回显】

Vue3 Element Plus TypeScript 实现 Tags 标签输入及回显 在开发后台管理系统或表单页面时&#xff0c;动态标签&#xff08;Tags&#xff09; 是一个常见的功能需求。用户可以通过输入框添加标签&#xff0c;并通过关闭按钮删除标签&#xff0c;同时还需要支持标签数据的提…...

STM32 子设备通过CAN发送数据到主设备

采集ADC、GPS经纬坐标、温湿度数据、大气压数据通过CAN方式发送给主设备端&#xff0c;帧ID按照如下定义&#xff1a; 我尼玛一个标准帧ID位数据是11位&#xff0c;扩展帧才是111829位&#xff0c;它说最开头的是四位是真类型&#xff0c;并给我如下解释&#xff1a; 它把帧的定…...

Python可视化——地理空间型图表(自用)

地图信息可视化的实现就是将不可展开的曲面上的地理坐标信息转化为二维平面进行显示&#xff0c;这个过程也叫地图投影&#xff08;空间三维投影到平面二维&#xff09; 地图投影的要求&#xff1a;等面积、等角度、等距离。总的来说就是映射到二维平面中的任何点通过比例尺放大…...

WordPress报502错误问题解决-php-fpm-84.service loaded failed failed LSB: starts php-fpm

文章目录 问题描述问题排查问题解决 问题描述 服务器环境&#xff1a; php&#xff1a;8.4MySQL&#xff1a;8.0Nginx&#xff1a;1.26.2 在访问站点时&#xff0c;一直报502&#xff0c;而两天前还能正常访问。 问题排查 导致502的问题很多&#xff0c;比如站点访问量太大…...

Python在SEO中的自动化应用爬虫开发与日志分析实例

引言 搜索引擎优化&#xff08;SEO&#xff09;是数字营销中至关重要的一环&#xff0c;旨在提高网站在搜索引擎结果页面&#xff08;SERP&#xff09;中的排名。随着互联网数据的爆炸式增长&#xff0c;手动进行SEO分析和管理变得愈发困难。Python作为一种强大的编程语言&…...

thingsboard edge 在windows 环境下的配置

按照官方文档&#xff1a;Installing ThingsBoard Edge on Windows | ThingsBoard Edge&#xff0c;配置好java环境和PostgreSQL。 下载对应的windows 环境下的tb-edge安装包。下载附件 接下来操作具体如下 步骤1&#xff0c;需要先在thingsboard 服务上开启edge 权限 步骤2…...

nnMamba:基于状态空间模型的3D生物医学图像分割、分类和地标检测

摘要 本文提出了一种基于状态空间模型&#xff08;SSMs&#xff09;的创新架构——nnMamba&#xff0c;用于解决3D生物医学图像分割、分类及地标检测任务中的长距离依赖建模难题。nnMamba结合了卷积神经网络&#xff08;CNN&#xff09;的局部特征提取能力与SSMs的全局上下文建…...

nginx 配置403页面(已亲测)

问题&#xff1a;GET请求访问漏洞url即可看到泄露的内网ip 解决方式&#xff1a; 1.配置nginx 不显示真实Ip 2.限制接口只能是POST请求 具体配置&#xff1a; 编写一个403.html 在nginx的配置文件中&#xff0c;配置location参数&#xff1a; location /api/validationCode…...

SyntaxError: Invalid or unexpected token in JSON at position x

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》、《前端求职突破计划》 &#x1f35a; 蓝桥云课签约作者、…...

Uncaught TypeError: Cannot read properties of undefined (reading ‘xxx‘)

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》、《前端求职突破计划》 &#x1f35a; 蓝桥云课签约作者、…...

Nginx 跨域配置详细讲解

一、跨域请求概述 跨域资源共享&#xff08;CORS&#xff0c;Cross-Origin Resource Sharing&#xff09;是一种机制&#xff0c;它使用额外的HTTP头部来告诉浏览器让运行在一个origin&#xff08;域&#xff09;上的Web应用被准许访问来自不同源服务器上的指定的资源。当一个资…...

前端开发基石:HTML语义化深度解析与实践指南

一、语义化设计的本质价值 1.1 从文档结构到信息表达 在Web诞生初期&#xff08;1991年&#xff09;&#xff0c;HTML仅包含18个标签用于学术文档展示。经过30年发展&#xff0c;HTML5已拥有超过110个标签&#xff0c;其中语义化标签占比提升至60%。这种演进背后是互联网从简…...

mongodb安装教程以及mongodb的使用

MongoDB是由C语言编写的一种面向文档的NoSQL数据库&#xff0c;旨在为WEB应用提供可扩展的高性能数据存储解决方案。与传统的关系型数据库&#xff08;如 MySQL 或 PostgreSQL&#xff09;不同&#xff0c;MongoDB 存储数据的方式是以 BSON&#xff08;类似于 JSON 的二进制格式…...

C# 中的多线程同步机制:lock、Monitor 和 Mutex 用法详解

在多线程编程中&#xff0c;线程同步是确保多个线程安全地访问共享资源的关键技术。C# 提供了几种常用的同步机制&#xff0c;其中 lock、Monitor 和 Mutex 是最常用的同步工具。本文将全面介绍这三种同步机制的用法、优缺点以及适用场景&#xff0c;帮助开发者在多线程开发中做…...

【通义万相】蓝耘智算 | 开源视频生成新纪元:通义万相2.1模型部署与测评

【作者主页】Francek Chen 【专栏介绍】 ⌈ ⌈ ⌈人工智能与大模型应用 ⌋ ⌋ ⌋ 人工智能&#xff08;AI&#xff09;通过算法模拟人类智能&#xff0c;利用机器学习、深度学习等技术驱动医疗、金融等领域的智能化。大模型是千亿参数的深度神经网络&#xff08;如ChatGPT&…...

期权帮|中证1000股指期权交割结算价怎么算?

期权帮锦鲤三三每日分享期权知识&#xff0c;帮助期权新手及时有效地掌握即市趋势与新资讯&#xff01; 中证1000股指期权交割结算价怎么算&#xff1f; 一、按照最后交易日结算价&#xff1a; &#xff08;1&#xff09;计算方法&#xff1a;最后交易日标的指数&#xff08…...

Python 面向对象高级编程-定制类

目录 __str__ __iter__ __getitem__ __getattr__ __call__ 小结 看到类似__slots__这种形如__xxx__的变量或者函数名就要注意&#xff0c;这些在Python中是有特殊用途的。 __slots__我们已经知道怎么用了&#xff0c;__len__()方法我们也知道是为了能让class作用于len()…...

qt creator示例空白

通常情况下&#xff0c;进入qt后&#xff0c;就会弹出以下窗口&#xff1a; 但如果出现示例空白&#xff0c;那可能是因为 Qt Creator 无法正确识别 Qt 的安装路径或配置。 解决&#xff1a; 点击“添加”&#xff1a; 然后跳转到你的qmake.exe的目录&#xff0c;例如我的qmak…...

MyBatis-Plus 与 Spring Boot 的最佳实践

在现代 Java 开发中,MyBatis-Plus 和 Spring Boot 的结合已经成为了一种非常流行的技术栈。MyBatis-Plus 是 MyBatis 的增强工具,提供了许多便捷的功能,而 Spring Boot 则简化了 Spring 应用的开发流程。本文将探讨如何将 MyBatis-Plus 与 Spring Boot 进行整合,并分享一些…...

TDengine 中的标签索引

简介 本节说明 TDengine 的索引机制。在 TDengine 3.0.3.0 版本之前&#xff08;不含&#xff09;&#xff0c;默认在第一列 TAG 上建立索引&#xff0c;但不支持给其它列动态添加索引。从 3.0.3.0 版本开始&#xff0c;可以动态地为其它 TAG 列添加索引。对于第一个 TAG 列上…...

[2025CVPR]DeepVideo-R1:基于难度感知回归GRPO的视频强化微调框架详解

突破视频大语言模型推理瓶颈,在多个视频基准上实现SOTA性能 一、核心问题与创新亮点 1.1 GRPO在视频任务中的两大挑战 ​安全措施依赖问题​ GRPO使用min和clip函数限制策略更新幅度,导致: 梯度抑制:当新旧策略差异过大时梯度消失收敛困难:策略无法充分优化# 传统GRPO的梯…...

python打卡day49

知识点回顾&#xff1a; 通道注意力模块复习空间注意力模块CBAM的定义 作业&#xff1a;尝试对今天的模型检查参数数目&#xff0c;并用tensorboard查看训练过程 import torch import torch.nn as nn# 定义通道注意力 class ChannelAttention(nn.Module):def __init__(self,…...

Spark 之 入门讲解详细版(1)

1、简介 1.1 Spark简介 Spark是加州大学伯克利分校AMP实验室&#xff08;Algorithms, Machines, and People Lab&#xff09;开发通用内存并行计算框架。Spark在2013年6月进入Apache成为孵化项目&#xff0c;8个月后成为Apache顶级项目&#xff0c;速度之快足见过人之处&…...

React第五十七节 Router中RouterProvider使用详解及注意事项

前言 在 React Router v6.4 中&#xff0c;RouterProvider 是一个核心组件&#xff0c;用于提供基于数据路由&#xff08;data routers&#xff09;的新型路由方案。 它替代了传统的 <BrowserRouter>&#xff0c;支持更强大的数据加载和操作功能&#xff08;如 loader 和…...

day52 ResNet18 CBAM

在深度学习的旅程中&#xff0c;我们不断探索如何提升模型的性能。今天&#xff0c;我将分享我在 ResNet18 模型中插入 CBAM&#xff08;Convolutional Block Attention Module&#xff09;模块&#xff0c;并采用分阶段微调策略的实践过程。通过这个过程&#xff0c;我不仅提升…...

中南大学无人机智能体的全面评估!BEDI:用于评估无人机上具身智能体的综合性基准测试

作者&#xff1a;Mingning Guo, Mengwei Wu, Jiarun He, Shaoxian Li, Haifeng Li, Chao Tao单位&#xff1a;中南大学地球科学与信息物理学院论文标题&#xff1a;BEDI: A Comprehensive Benchmark for Evaluating Embodied Agents on UAVs论文链接&#xff1a;https://arxiv.…...

uni-app学习笔记二十二---使用vite.config.js全局导入常用依赖

在前面的练习中&#xff0c;每个页面需要使用ref&#xff0c;onShow等生命周期钩子函数时都需要像下面这样导入 import {onMounted, ref} from "vue" 如果不想每个页面都导入&#xff0c;需要使用node.js命令npm安装unplugin-auto-import npm install unplugin-au…...

Qt Widget类解析与代码注释

#include "widget.h" #include "ui_widget.h"Widget::Widget(QWidget *parent): QWidget(parent), ui(new Ui::Widget) {ui->setupUi(this); }Widget::~Widget() {delete ui; }//解释这串代码&#xff0c;写上注释 当然可以&#xff01;这段代码是 Qt …...

java调用dll出现unsatisfiedLinkError以及JNA和JNI的区别

UnsatisfiedLinkError 在对接硬件设备中&#xff0c;我们会遇到使用 java 调用 dll文件 的情况&#xff0c;此时大概率出现UnsatisfiedLinkError链接错误&#xff0c;原因可能有如下几种 类名错误包名错误方法名参数错误使用 JNI 协议调用&#xff0c;结果 dll 未实现 JNI 协…...

Module Federation 和 Native Federation 的比较

前言 Module Federation 是 Webpack 5 引入的微前端架构方案&#xff0c;允许不同独立构建的应用在运行时动态共享模块。 Native Federation 是 Angular 官方基于 Module Federation 理念实现的专为 Angular 优化的微前端方案。 概念解析 Module Federation (模块联邦) Modul…...