music / src /components /common /Loading.vue
ahutchen's picture
fix
40f23a9
<template>
<div class="loading-container" :class="{ overlay: overlay }">
<div class="loading-content">
<!-- 加载动画 -->
<div class="loading-spinner" :class="size">
<div v-for="i in 12" :key="i" class="spinner-bar" :style="{ '--delay': `${i * 0.1}s` }"></div>
</div>
<!-- 加载文本 -->
<div v-if="text" class="loading-text">{{ text }}</div>
</div>
</div>
</template>
<script setup>
defineProps({
// 是否显示遮罩层
overlay: {
type: Boolean,
default: false
},
// 加载提示文字
text: {
type: String,
default: ''
},
// 大小:small, medium, large
size: {
type: String,
default: 'medium',
validator: (value) => ['small', 'medium', 'large'].includes(value)
}
})
</script>
<style scoped>
.loading-container {
display: flex;
align-items: center;
justify-content: center;
padding: 20px;
}
.loading-container.overlay {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgba(0, 0, 0, 0.6);
backdrop-filter: blur(4px);
z-index: 9999;
}
.loading-content {
display: flex;
flex-direction: column;
align-items: center;
gap: 16px;
}
.loading-spinner {
position: relative;
display: inline-block;
}
.loading-spinner.small {
width: 20px;
height: 20px;
}
.loading-spinner.medium {
width: 32px;
height: 32px;
}
.loading-spinner.large {
width: 48px;
height: 48px;
}
.spinner-bar {
position: absolute;
width: 2px;
height: 25%;
background: var(--accent-red);
border-radius: 1px;
opacity: 0;
animation: spin 1.2s linear infinite;
animation-delay: var(--delay);
transform-origin: 50% 200%;
}
.spinner-bar:nth-child(1) { transform: rotate(0deg); }
.spinner-bar:nth-child(2) { transform: rotate(30deg); }
.spinner-bar:nth-child(3) { transform: rotate(60deg); }
.spinner-bar:nth-child(4) { transform: rotate(90deg); }
.spinner-bar:nth-child(5) { transform: rotate(120deg); }
.spinner-bar:nth-child(6) { transform: rotate(150deg); }
.spinner-bar:nth-child(7) { transform: rotate(180deg); }
.spinner-bar:nth-child(8) { transform: rotate(210deg); }
.spinner-bar:nth-child(9) { transform: rotate(240deg); }
.spinner-bar:nth-child(10) { transform: rotate(270deg); }
.spinner-bar:nth-child(11) { transform: rotate(300deg); }
.spinner-bar:nth-child(12) { transform: rotate(330deg); }
@keyframes spin {
0%, 40%, 100% {
opacity: 0.3;
}
20% {
opacity: 1;
}
}
.loading-text {
font-size: 14px;
color: var(--text-secondary);
text-align: center;
font-weight: 500;
}
/* 响应式 */
@media (max-width: 375px) {
.loading-container {
padding: 16px;
}
.loading-content {
gap: 12px;
}
.loading-text {
font-size: 13px;
}
}
</style>