优化
This commit is contained in:
@@ -1,16 +1,151 @@
|
||||
<script setup>
|
||||
import { RouterView } from 'vue-router'
|
||||
import { ref, onMounted } from 'vue'
|
||||
import { theme } from 'ant-design-vue'
|
||||
import { ref, computed, watchEffect } from 'vue'
|
||||
import SvgSprite from '@/components/icons/SvgSprite.vue'
|
||||
import { useUserStore } from '@/stores/user'
|
||||
import tokenManager from '@gold/utils/token-manager'
|
||||
import zhCN from 'ant-design-vue/es/locale/zh_CN';
|
||||
const themeToken = ref({
|
||||
import zhCN from 'ant-design-vue/es/locale/zh_CN'
|
||||
|
||||
// ========================================
|
||||
// Ant Design Vue 主题配置
|
||||
// ========================================
|
||||
const isDark = ref(false)
|
||||
|
||||
// 初始化主题
|
||||
const initTheme = () => {
|
||||
const stored = localStorage.getItem('theme')
|
||||
if (stored) {
|
||||
isDark.value = stored === 'dark'
|
||||
} else {
|
||||
isDark.value = window.matchMedia('(prefers-color-scheme: dark)').matches
|
||||
}
|
||||
document.documentElement.setAttribute('data-theme', isDark.value ? 'dark' : 'light')
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const toggleTheme = () => {
|
||||
isDark.value = !isDark.value
|
||||
document.documentElement.setAttribute('data-theme', isDark.value ? 'dark' : 'light')
|
||||
localStorage.setItem('theme', isDark.value ? 'dark' : 'light')
|
||||
}
|
||||
|
||||
// Ant Design 主题 Token
|
||||
const themeToken = computed(() => {
|
||||
const lightToken = {
|
||||
// 品牌色
|
||||
colorPrimary: '#3B82F6',
|
||||
colorSuccess: '#22C55E',
|
||||
colorWarning: '#F59E0B',
|
||||
colorError: '#EF4444',
|
||||
colorInfo: '#3B82F6',
|
||||
// 背景色
|
||||
colorBgContainer: '#FFFFFF',
|
||||
colorBgElevated: '#FFFFFF',
|
||||
colorBgLayout: '#F9FAFB',
|
||||
// 边框
|
||||
colorBorder: '#E5E7EB',
|
||||
colorBorderSecondary: '#F3F4F6',
|
||||
// 文字
|
||||
colorText: '#111827',
|
||||
colorTextSecondary: '#4B5563',
|
||||
colorTextTertiary: '#6B7280',
|
||||
colorTextQuaternary: '#9CA3AF',
|
||||
// 填充
|
||||
colorFill: '#F3F4F6',
|
||||
colorFillSecondary: '#F9FAFB',
|
||||
// 字体
|
||||
fontFamily: '-apple-system, BlinkMacSystemFont, "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", sans-serif',
|
||||
fontSize: 14,
|
||||
// 圆角
|
||||
borderRadius: 6,
|
||||
borderRadiusSM: 4,
|
||||
borderRadiusLG: 8,
|
||||
// 控件尺寸
|
||||
controlHeight: 32,
|
||||
controlHeightSM: 28,
|
||||
controlHeightLG: 40,
|
||||
// 动画
|
||||
motionDurationFast: '0.15s',
|
||||
motionDurationMid: '0.2s',
|
||||
motionDurationSlow: '0.3s',
|
||||
// 阴影
|
||||
boxShadow: '0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 1px 2px -1px rgba(0, 0, 0, 0.1)',
|
||||
boxShadowSecondary: '0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -2px rgba(0, 0, 0, 0.1)',
|
||||
}
|
||||
|
||||
const darkToken = {
|
||||
colorPrimary: '#60A5FA',
|
||||
colorBgContainer: '#1E293B',
|
||||
colorBgElevated: '#334155',
|
||||
colorBgLayout: '#0F172A',
|
||||
colorBorder: '#334155',
|
||||
colorBorderSecondary: '#1E293B',
|
||||
colorText: '#F1F5F9',
|
||||
colorTextSecondary: '#94A3B8',
|
||||
colorTextTertiary: '#64748B',
|
||||
colorTextQuaternary: '#475569',
|
||||
colorFill: '#334155',
|
||||
colorFillSecondary: '#1E293B',
|
||||
boxShadow: '0 1px 3px 0 rgba(0, 0, 0, 0.4), 0 1px 2px -1px rgba(0, 0, 0, 0.4)',
|
||||
boxShadowSecondary: '0 4px 6px -1px rgba(0, 0, 0, 0.4), 0 2px 4px -2px rgba(0, 0, 0, 0.4)',
|
||||
}
|
||||
|
||||
return {
|
||||
token: isDark.value ? { ...lightToken, ...darkToken } : lightToken,
|
||||
components: {
|
||||
Button: {
|
||||
primaryShadow: 'none',
|
||||
defaultShadow: 'none',
|
||||
fontWeight: 500,
|
||||
},
|
||||
Input: {
|
||||
paddingBlock: 6,
|
||||
paddingInline: 12,
|
||||
activeShadow: '0 0 0 3px rgba(59, 130, 246, 0.15)',
|
||||
},
|
||||
Select: {
|
||||
optionSelectedBg: isDark.value ? 'rgba(96, 165, 250, 0.15)' : '#EFF6FF',
|
||||
optionActiveBg: isDark.value ? '#334155' : '#F3F4F6',
|
||||
},
|
||||
Table: {
|
||||
headerBg: isDark.value ? '#1E293B' : '#F9FAFB',
|
||||
rowHoverBg: isDark.value ? '#334155' : '#F9FAFB',
|
||||
borderColor: isDark.value ? '#334155' : '#E5E7EB',
|
||||
headerColor: '#4B5563',
|
||||
},
|
||||
Card: {
|
||||
paddingLG: 20,
|
||||
borderRadiusLG: 12,
|
||||
},
|
||||
Modal: {
|
||||
borderRadiusLG: 12,
|
||||
},
|
||||
Menu: {
|
||||
itemHoverBg: isDark.value ? '#334155' : '#F3F4F6',
|
||||
itemSelectedBg: isDark.value ? 'rgba(96, 165, 250, 0.15)' : '#EFF6FF',
|
||||
itemSelectedColor: isDark.value ? '#60A5FA' : '#3B82F6',
|
||||
},
|
||||
},
|
||||
}
|
||||
})
|
||||
|
||||
onMounted(async () => {})
|
||||
// 初始化
|
||||
initTheme()
|
||||
|
||||
// 监听系统主题变化
|
||||
watchEffect(() => {
|
||||
const media = window.matchMedia('(prefers-color-scheme: dark)')
|
||||
const handler = (e) => {
|
||||
if (!localStorage.getItem('theme')) {
|
||||
isDark.value = e.matches
|
||||
document.documentElement.setAttribute('data-theme', e.matches ? 'dark' : 'light')
|
||||
}
|
||||
}
|
||||
media.addEventListener('change', handler)
|
||||
})
|
||||
|
||||
// 暴露给模板使用
|
||||
defineExpose({ toggleTheme, isDark })
|
||||
</script>
|
||||
|
||||
<template>
|
||||
|
||||
Reference in New Issue
Block a user