总结放后面:

Tipes: 封装弹框组件应用了Teleport,防止了组件嵌套可能导致的定位层级的隐患,还应用了defineProps,defineEmits,插槽减少了组件的拓展性。

前言:

之前始终没有本人去封装过一个弹框组件,然而感觉一个小小的弹窗组件那不是洒洒水小意思了。而后明天新我的项目中须要一个弹窗组件,所以我就做了一个。不做不要紧一做发现还是有很多不同的小问题,而后就把遇到的问题和大佬们分享一下。开始先回顾一下需要,一个全局应用的公共弹框组件。那么就有几个要点:公共、全局、弹框,上面咱们就针对这几个要点去一点点实现弹框组件。

公共

公共这个简略,置信在座的各位大佬必定都是手拿把掐,轻轻松松就实现了。先实现一个主体内容,我的办法就是应用插槽和参数传递。例子只是简略的传递两个参数,一个题目内容一个管制关上和敞开的布尔值。次要波及到Vue3两个Api的应用defineProps,defineEmits还有插槽的应用。

<template>

<Mask @click="close" /> // 蒙板层<div class="modal_all" v-if="visible">    <slot name="header"> // 不便页面减少定制头部        <div class="modal_header">            <p class="modal_header_title">{{ title }}</p>            <p class="modal_header_img" @click="close"></p>        </div>    </slot>    <div class="modal_content">        <slot></slot> // 凋谢弹框内容应用    </div></div>

</template>
<script lang="ts" setup>
defineProps({

visible: {    type: Boolean,    default: false,},title: {    type: String,},

});
const emit = defineEmits(['update:visible']);
const close = () => {

emit('update:visible', false);

};
</script>
// 款式省略
复制代码
全局

根本布局差不多了,上面就是全局注册,目标是为了不必每次应用每次都要引入。vue2在注册全局组件的时候,间接Vue.component('名称', 组件)就能够了,那么在vue3中怎么批量注册全局组件呐?提供一个install办法,应用app.use()主动调用。

import Modal from './Modal/Modal.vue';
import Mask from './Modal/Mask.vue';

// 在script setup不能写name,所以在这里加一个
const coms = [
{

name: 'Modal', // 应用组件的名称compent: Modal,

},
{

name: 'Mask',compent: Mask,

},
];

export default {
install: (app) => {

coms.forEach((item) => {  app.component(item.name, item.compent);});

},
};

// main.ts
import Common from './common/index';
const app = createApp(App);
app.use(Common);
复制代码
弹框

其实弹框组件写到这里曾经差不多了,那为什么要把弹框这个独自列出来说一下呐?置信各位大佬在日常工作中也遇到过定位和层级的问题,如果咱们把须要定位的组件嵌套在 Vue 的某个组件外部,因为css各种层的起因咱们在解决嵌套的定位、层级 和款式就会变得很艰难,一不小心就会呈现一些奇奇怪怪的问题,那么怎么去防止这个问题?上面就要应用到Vue3中另外一个传送门Api:Teleport。

Tipes: Teleport就是将咱们的组件挂载到属性 to 对应的DOM元素中,相似一个任意门。
先上代码:

<teleport to="#mask_modal" v-if="visible">

<div class="modal_cent">    <Mask @click="close" />        <div class="modal_all">            <slot name="header">                <div class="header">                    <p class="header_title">{{ title }}</p>                    <p class="header_img" @click="close"></p>                </div>            </slot>        <div>        <slot></slot>        </div>    </div></div>

</teleport>
复制代码
咱们来看一下这样写之后的层级:

通过 to 属性,指定弹框组件渲染的地位与layput组件同级,然而 teleport 的状态 visible 又是齐全由咱们调用的组件管制,就防止了咱们在嵌套组件的时候定位层级款式的问题。

 至此,一个简略的公共弹框组件曾经写的差不多了。而后在写这个组件的过程中我还是遇到了几个不算问题的问题。

❗️❗️❗️1.script setup中没法写name属性:

如果没有用ts的话,能够再写一个script标签,在外面导出而后写name。如果应用ts,那么这个办法就行不通就会报错。那么就利用我下面写的办法,本人从新定义一下写一个对象那样。

❗️❗️❗️2.间接给全局组件加一个class加款式不失效:

其实咱们失常写公共组件,在应用的中央想间接在外层管制外部容器的款式,咱们能够间接在里面加一个类名去减少款式,然而我在写这个弹框组件的时候却始终不失效,找了半天起初才发现原来是因为我应用了teleport,所以在解析的时候class不能被继承。同样要是组件内没有一个根组件同样会呈现这样的问题。这样其实也没关系,咱们在插槽内写内容主动撑开就能够了,置信各位大佬必定不会像我一样搞这么傻的操作,哈哈。

结语:

其实一个弹框组件的封装还是很简略的,不过也算是积攒了一点教训,把本人的我的项目施行落地。前面去封装更加简单的组件也会比拟有思路。不积硅步无以至千里,加油各位大佬!

最初
如果你感觉此文对你有一丁点帮忙,点个赞。或者能够退出我的开发交换群:1025263163互相学习,咱们会有业余的技术答疑解惑

如果你感觉这篇文章对你有点用的话,麻烦请给咱们的开源我的项目点点star: https://gitee.com/ZhongBangKe...不胜感激 !