Vue实现全局消息组件
使用了Vue 3中的setup语法和TypeScript来创建一个全局的消息组件,该组件挂载在app下无需全局注册即可使用,下面是详细步骤和代码。
效果展示

创建消息组件
首先需要创建一个名为Message.vue的Vue组件,该组件将负责显示用户的消息。
<!-- Message.vue -->
<script setup lang="ts">
import {computed, onMounted, ref} from 'vue';
const props = defineProps<{
type: 'success' | 'error' | 'warning' | 'info';
message: string;
}>();
const isShow = ref(false);
const messageType = computed(() => props.type);
onMounted(() => {
isShow.value = true;
});
</script>
<template>
<Transition name="down">
<div class="message" v-show="isShow" :class="messageType">
<span class="text">{{ props.message }}</span>
</div>
</Transition>
</template>
<style scoped lang="scss">
.message {
margin-top: 10px;
width: 300px;
height: 50px;
line-height: 50px;
padding: 0 25px;
border: 1px solid #e4e4e4;
color: #fff;
border-radius: 4px;
i {
margin-right: 4px;
vertical-align: middle;
}
.text {
vertical-align: middle;
}
&.success {
color: #67C23A;
background-color: #F0F9EB;
border-color: #E1F3D8;
}
&.error {
color: #F56C6C;
background-color: #FDF6F6;
border-color: #FDE2E2;
}
&.warning {
color: #E6A23C;
background-color: #FDF6EC;
border-color: #FBE6C2;
}
&.info {
color: #909399;
background-color: #F4F4F5;
border-color: #DCDFE6;
}
}
.down-enter {
&-from {
transform: translate3d(0, -75px, 0);
opacity: 0;
}
&-active {
transition: all 0.5s;
}
&-to {
transform: none;
opacity: 1;
}
}
</style>
<style lang="scss">
#gl-message {
position: fixed;
z-index: 9999;
left: 50%;
margin-left: -150px;
top: 25px;
}
</style>
全局消息工具函数
为了更便捷地使用消息组件,我们提供了一个Message 函数,用于动态渲染消息组件,并在一定时间后移除。此外,我们还定义了四个静态方法 success, error, warning, info ,分别用于显示不同类型的消息。
<!-- index.ts -->
import {h, render} from 'vue'
import GlMessage from './Message.vue'
type Props = {
type: 'success' | 'error' | 'warning' | 'info'
message: string
duration?: number
}
export default function Message({type, message, duration = 3000}: Props) {
// 获取或创建根元素
const appRootElement = document.getElementById('gl-message') || createRootElement();
// 在根元素下创建一个动态的 div 元素
const div = document.createElement('div');
div.setAttribute('class', 'my-message');
appRootElement.appendChild(div);
// 渲染消息组件
const vNode = h(GlMessage, {type, message});
render(vNode, div);
// 设置定时器,在一定时间后移除消息元素
setTimeout(() => {
render(null, div);
// 在定时器回调中,移除动态创建的 div 元素
div.parentNode && div.parentNode.removeChild(div);
// 获取所有的消息元素
const messageElements = document.getElementsByClassName('my-message');
// 如果没有消息元素存在,移除根元素
if (messageElements.length === 0) {
appRootElement.parentNode && appRootElement.parentNode.removeChild(appRootElement);
}
}, duration);
// 创建或获取根元素的函数
function createRootElement() {
const messageElement = document.createElement('div');
messageElement.setAttribute('id', 'gl-message');
document.body.appendChild(messageElement);
return messageElement;
}
}
Message.success = (message: string, duration?: number) => {
Message({type: 'success', message, duration})
}
Message.error = (message: string, duration?: number) => {
Message({type: 'error', message, duration})
}
Message.warning = (message: string, duration?: number) => {
Message({type: 'warning', message, duration})
}
Message.info = (message: string, duration?: number) => {
Message({type: 'info', message, duration})
}
使用消息组件
无需全局注册,直接在所需的文件中引入Message函数即可使用。
<!-- App.vue -->
<script setup lang="ts">
import Message from './components/Message/index.ts';
Message.success('成功消息');
Message.error('错误消息');
Message.warning('警告消息');
Message.info('信息消息');
</script>
评论 (0)
发表评论