<script setup> import { ref, computed } from 'vue' import MessageContent from './message/index.vue' const visible = ref(false) const messageType = ref('success') const messageText = ref('') const showIcon = ref(true) const customStyle = ref({}) const title = ref({}) const subTitle = ref({}) const containerStyle = computed(() => { const { top, bottom, left, right, transform, ...otherStyles } = customStyle.value || {} const baseStyle = { position: 'fixed', zIndex: 9999 } const horizontalPosition = left || right ? { left, right } : { left: '50%', transform: 'translateX(-50%)' } const verticalPosition = {} if (bottom !== undefined) { verticalPosition.bottom = bottom } else { verticalPosition.top = top || '50px' } return { ...baseStyle, ...horizontalPosition, ...verticalPosition, ...otherStyles } }) const emit = defineEmits(['after-leave']) const showMessage = (options) => { if (typeof options === 'string') { messageText.value = options title.value = {} subTitle.value = {} } else { messageText.value = options.message || '' title.value = options.title || {} subTitle.value = options.subTitle || {} } messageType.value = options.type || 'success' showIcon.value = options.icon !== false customStyle.value = options.style || {} visible.value = true setTimeout(() => { visible.value = false }, options.duration || 2000) } defineExpose({ showMessage }) </script> <template> <transition name="fade" @after-leave="$emit('after-leave')" > <MessageContent v-if="visible" :message="messageText" :type="messageType" :title="title" :sub-title="subTitle" :show-icon="showIcon" :style="containerStyle" /> </transition> </template> <style lang="scss" scoped> .fade-enter-active, .fade-leave-active { transition: opacity 0.2s ease; } .fade-enter-from, .fade-leave-to { opacity: 0; } </style>