Vue3中ElementPlus组件二次封装,实现原组件属性、插槽、事件监听、方法的透传

本文以el-input组件为例,其它组件类似用法。
请添加图片描述

一、解决数据绑定问题

封装组件的第一步,要解决的就是数据绑定的问题,由于prop数据流是单向传递的,数据只能从父流向子,子想改父只能通过提交emit事件通知父修改。
父:

import { ref } from 'vue'
import CInput from '@/components/CInput/index.vue'const name = ref<string>('')
<c-input v-model:value="name"/>

子组件:

import { ref, computed } from 'vue';
const props = withDefaults(defineProps<{value: string;
}>(), {value: ''
})
const inputValue = computed({get: () => props.value,set: (value: string) => emit('update:value', value)
})
<el-inputv-model="inputValue" 
></el-input>

以上即可实现父子之前数据的双向传递。
但在Vue3.4+版本中,新增了defineModel() ,这个宏可以用来声明一个双向绑定 prop,通过父组件的 v-model 来使用:const model = defineModel()。同样实现了父子组件数据的双向绑定。感兴趣的同学可以看下官网解释,其有更多用法。

二、属性、事件监听

在vue3版本中,“透传 attribute”指的是传递给一个组件,却没有被该组件声明为 props 或 emits 的 attribute 或者 v-on 事件监听器。
例如el-input组件上有许多属性,clearable、show-word-limit、show-password、@input、@focus等等,这些肯定不需要通过props传递给子组件,那就是通过$attrs来进行传递。
在子组件封装时,编写:

<el-input v-model="inputValue"v-bind="$attrs" 
>
</el-input>

当然对于你二次封装的组件,根据你的业务需要,直接固定一些属性。
这样,在父组件中,我们可以像使用el-input组件一样,使用我们自己的组件传递属性和监听事件。

<c-input ref="nameRef" class="name-input" v-model:value="addForm.name" @input="handleInput" clearable/>

三、插槽传递

对于ElementPlus中的组件,通常都会都一些插槽,那我们封装后想保留这些插槽的使用,该如何写?Vue3为我们提供了$slots,里面存着父组件所传入插槽的对象。所以我们可以这样写:

<el-input ref="input"class="c-input" v-model="inputValue" :placeholder="props.label" v-bind="$attrs" 
><template v-for="(_, name) in $slots" v-slot:[name]><slot :name="name"></slot></template>
</el-input>

这样,在父组件中我们可以正常使用el-input中所带有的插槽:

<c-input v-model:value="loginForm.account" :label="$t('input.username')" clearable><template #prefix><el-icon><User /></el-icon></template>
</c-input>

四、原组件方法获取并暴露

最后一步,在父组件中想通过绑定ref调用el-input的方法,该如何写?首先父组件直接调用肯定是不行的,因为封装的组件中并没有这些方法,这些方法是挂在封装的el-input的实例对象上的。所以,解决办法就是我们通过在子组件中获取到这些方法,然后通过defineExpose向父组件暴露就行了。
子组件:

import { ref, onMounted, defineExpose } from 'vue';
import type { InputInstance } from 'element-plus';const input = ref<InputInstance>()
const inputMethods = ref({})onMounted(() => {const refMethods = Object.entries(input.value).filter(([_, value]) => value instanceof Function)refMethods.forEach(([key, value]) => {inputMethods.value[key] = value})
})
defineExpose(inputMethods.value)<el-input ref="input"class="c-input" v-model="inputValue" :placeholder="props.label" v-bind="$attrs" 
><template v-for="(_, name) in $slots" v-slot:[name]><slot :name="name"></slot></template>
</el-input>

这样,父组件中获取该组件的实例对象上就会存在这些方法了。完美解决!

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

scrapy的概念作用和工作流程

1. scrapy的概念 Scrapy是一个Python编写的开源网络爬虫框架。它是一个被设计用于爬取网络数据、提取结构性数据的框架。 Scrapy 使用了Twisted[twɪstɪd]异步网络框架&#xff0c;可以加快我们的下载速度。 Scrapy文档地址&#xff1a;http://scrapy-chs.readthedocs.io/zh_…

Linux中断 -- 中断路由、优先级、数据和标识

目录 1.中断路由 2.中断优先级 3.中断平衡 4.Linux内核中重要的数据结构 5.中断标识 承前文&#xff0c;本文从中断路由、优先级、数据结构和标识意义等方面对Linux内核中断进行一步的解析。 1.中断路由 Aset affinity flow GIC文中有提到SPI类型中断的路由控制器寄存器为…

Prometheus 架构全面解析

在本指南中&#xff0c;我们将详细介绍 Prometheus 架构。 Prometheus 是一个用 Golang 编写的开源监控和告警系统&#xff0c;能够收集和处理来自各种目标的指标。您还可以查询、查看、分析指标&#xff0c;并根据阈值收到警报。 此外&#xff0c;在当今世界&#xff0c;可观…

风口抓猪-借助亚马逊云科技EC2服务器即刻构建PalWorld(幻兽帕鲁)私服~~~持续更新中

Pocketpair出品的生存类游戏《幻兽帕鲁》最近非常火&#xff0c;最高在线人数已逼近200万。官方服务器亚历山大&#xff0c;游戏开发商也提供了搭建私人专用服务器的方案&#xff0c;既可以保证稳定的游戏体验&#xff0c;也可以和朋友一起联机游戏&#xff0c;而且还能自定义经…

【PyTest】玩转HTML报告:修改、汉化和优化

前言 Pytest框架可以使用两种测试报告&#xff0c;其中一种就是使用pytest-html插件生成的测试报告&#xff0c;但是报告中有一些信息没有什么用途或者显示的不太好看&#xff0c;还有一些我们想要在报告中展示的信息却没有&#xff0c;最近又有人问我pytest-html生成的报告&a…

Ubuntu findfont: Font family ‘SimHei‘ not found.

matplotlib中文乱码显示 当我们遇到这样奇怪的问题时, 结果往往很搞笑 尝试1不行 Stopping Jupyter Installing font-manager: sudo apt install font-manager Cleaning the matplotlib cache directory: rm ~/.cache/matplotlib -fr Restarting Jupyter. 尝试2 This work fo…

vue实现甘特图

目录 实现效果 一、安装依赖 二、使用 二、绕过license 实现效果 一、安装依赖 npm i --save vue-gantt-schedule-timeline-calendar 实现甘特图需先安装上述依赖&#xff0c;安装依赖实际上是通过gantt-schedule-timeline-calendar来实现的。所以node_module中因包含以下…

openssl3.2 - 测试程序的学习 - test\sanitytest.c

文章目录 openssl3.2 - 测试程序的学习 - test\sanitytest.c概述笔记添加好实现的工程效果END openssl3.2 - 测试程序的学习 - test\sanitytest.c 概述 openssl3.2 - 测试程序的学习 重建工程参考 makefile, 将该加的实现加入vs2019工程, 不能无脑添加, 否则编译不过. 这个工…

掌握可视化大屏:提升数据分析和决策能力的关键(上)

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

Nginx,安装及基础配置

目录 下载 Nginx Nginx 目录 配置文件 主要配置 events server 启动与关闭 方法一 方法二 方法三 查看是否启动成功 下载 Nginx 官网中文网 Nginx 目录 conf&#xff1a; 存放 核心配置文件 contrib&#xff1a; 存放 语法支持脚本 docs&#xff1a; …

浪花 - 响应拦截器(强制登录)

1. 配置响应拦截器 import axios from axios;const myAxios axios.create({baseURL: http://localhost:8080/api/, });myAxios.defaults.withCredentials true;// 请求拦截器 myAxios.interceptors.request.use(function (config) {// Do something before request is sentc…

Web3 游戏开发者的数据分析指南

作者&#xff1a;lesleyfootprint.network 在竞争激烈的 Web3 游戏行业中&#xff0c;成功不仅仅取决于游戏的发布&#xff0c;还需要在游戏运营过程中有高度的敏锐性&#xff0c;以应对下一次牛市的来临。 人们对 2024 年的游戏行业充满信心。A16Z GAMES 和 GAMES FUND ONE …