likes
comments
collection
share

vue封装第三方组件

作者站长头像
站长
· 阅读数 28

需求场景

我们可能在工作中经常会遇到这样的场景,需要基于某个UI组件库(本文以Vuetify为例,其他的也同理)封装一个可复用的组件,不仅要实现自定义功能,还希望能沿用第三方组件本身提供的属性,事件等。举几个具体的栗子:

  • 统一给text-field添加一个clearable的动作
  • 想更改text-field默认label样式,由点击悬浮变为固定位置
  • 给image组件添加loading的效果
  • 给table组件统一添加一些诸如移动列,刷新,csv下载的动作

技术关键点

一、继承属性

v-bind="$attrs" 和 inheritAttrs: false

$attrs包含了父组件里除了props属性的 attribute 绑定,所以在子组件中使用$attrs就可以获取到父组件传递的属性。但是默认情况下这些属性会被认作是普通的HTML attribute应用到子组件的根元素上,现在我们像创建一个wrapper来做封装时很可能会出现不符合预期的情况,此时我们就需要设置inheritAttrs: false来消除这种默认行为。

vue2.x和vue3.x中的区别

$attrs在vue2和vue3中的表现有所不同,在vue2里,$attrs不包含style和class,而在vue3中包含

二、继承事件

v-on="$listeners"

$listeners里包含了父组件作用域中v-on 事件监听器。我们在子组件中可以通过v-on="$listeners"来获取父组件传入的事件

vue2.x和vue3.x中的区别

$listeners在vue3中被移除了,可以直接通过$attrs来替代

三、继承插槽

$scopedSlots 和 $slots

vuetify中提供了非常灵活的自定义插槽,所以对于插槽的继承也是非常重要滴

<template v-for="(_, scopedSlotName) in $scopedSlots" #[scopedSlotName]="slotData">
  <slot :name="scopedSlotName" v-bind="slotData" />
</template>
<template v-for="(_, slotName) in $slots" #[slotName]>
  <slot :name="slotName" />
</template>

参考文章

转载自:https://segmentfault.com/a/1190000042538522
评论
请登录