diff --git a/dashboard/src/assets/mdi-subset/materialdesignicons-subset.css b/dashboard/src/assets/mdi-subset/materialdesignicons-subset.css index 54785df237..d0a4a57686 100644 --- a/dashboard/src/assets/mdi-subset/materialdesignicons-subset.css +++ b/dashboard/src/assets/mdi-subset/materialdesignicons-subset.css @@ -1,4 +1,4 @@ -/* Auto-generated MDI subset – 247 icons */ +/* Auto-generated MDI subset – 252 icons */ /* Do not edit manually. Run: pnpm run subset-icons */ @font-face { @@ -316,6 +316,10 @@ content: "\F164B"; } +.mdi-database-import::before { + content: "\F095D"; +} + .mdi-database-off::before { content: "\F1640"; } @@ -352,6 +356,10 @@ content: "\F01DA"; } +.mdi-earth::before { + content: "\F01E7"; +} + .mdi-emoticon::before { content: "\F0C68"; } @@ -652,6 +660,10 @@ content: "\F0375"; } +.mdi-moon-waning-crescent::before { + content: "\F0F65"; +} + .mdi-music-note-outline::before { content: "\F0F74"; } @@ -696,6 +708,10 @@ content: "\F0601"; } +.mdi-palette::before { + content: "\F03D8"; +} + .mdi-paperclip::before { content: "\F03E2"; } @@ -900,6 +916,10 @@ content: "\F060D"; } +.mdi-sync::before { + content: "\F04E6"; +} + .mdi-text::before { content: "\F09A8"; } diff --git a/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff b/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff index b5c8cefd74..354f467b9e 100644 Binary files a/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff and b/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff differ diff --git a/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff2 b/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff2 index 74e05e5454..a0a8293e45 100644 Binary files a/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff2 and b/dashboard/src/assets/mdi-subset/materialdesignicons-webfont-subset.woff2 differ diff --git a/dashboard/src/components/chat/Chat.vue b/dashboard/src/components/chat/Chat.vue index b24aeed044..15f93a1da0 100644 --- a/dashboard/src/components/chat/Chat.vue +++ b/dashboard/src/components/chat/Chat.vue @@ -267,7 +267,7 @@ }} {{ - isDark ? tm("modes.lightMode") : tm("modes.darkMode") + isDark ? tm("modes.light") : tm("modes.dark") }} @@ -848,7 +848,7 @@ watch(transportMode, (mode) => { localStorage.setItem("chat.transportMode", mode); }); -const isDark = computed(() => customizer.uiTheme === "PurpleThemeDark"); +const isDark = computed(() => customizer.isDarkTheme); const canSend = computed( () => Boolean(draft.value.trim() || stagedFiles.value.length) && !sending.value, @@ -1394,7 +1394,7 @@ async function stopCurrentSession() { } function toggleTheme() { - customizer.SET_UI_THEME(isDark.value ? "PurpleTheme" : "PurpleThemeDark"); + customizer.TOGGLE_DARK_MODE(); } function formatTime(value: string) { diff --git a/dashboard/src/components/chat/ChatInput.vue b/dashboard/src/components/chat/ChatInput.vue index 7f2117377e..37ed1d23ef 100644 --- a/dashboard/src/components/chat/ChatInput.vue +++ b/dashboard/src/components/chat/ChatInput.vue @@ -365,9 +365,8 @@ const emit = defineEmits<{ }>(); const { tm } = useModuleI18n("features/chat"); -const isDark = computed( - () => useCustomizerStore().uiTheme === "PurpleThemeDark", -); +const customizer = useCustomizerStore(); +const isDark = computed(() => customizer.isDarkTheme); const inputField = ref(null); const imageInputRef = ref(null); diff --git a/dashboard/src/components/chat/LiveMode.vue b/dashboard/src/components/chat/LiveMode.vue index 2740459d96..01d0d23f6f 100644 --- a/dashboard/src/components/chat/LiveMode.vue +++ b/dashboard/src/components/chat/LiveMode.vue @@ -54,7 +54,7 @@ diff --git a/dashboard/src/i18n/locales/en-US/features/auth.json b/dashboard/src/i18n/locales/en-US/features/auth.json index 5c44558a03..f51384229c 100644 --- a/dashboard/src/i18n/locales/en-US/features/auth.json +++ b/dashboard/src/i18n/locales/en-US/features/auth.json @@ -8,7 +8,7 @@ "subtitle": "Welcome" }, "theme": { - "switchToDark": "Switch to Dark Theme", - "switchToLight": "Switch to Light Theme" + "light": "Light Mode", + "dark": "Dark Mode" } } \ No newline at end of file diff --git a/dashboard/src/i18n/locales/en-US/features/chat.json b/dashboard/src/i18n/locales/en-US/features/chat.json index 4b87cc8abc..19a27a3497 100644 --- a/dashboard/src/i18n/locales/en-US/features/chat.json +++ b/dashboard/src/i18n/locales/en-US/features/chat.json @@ -73,8 +73,8 @@ "confirmDelete": "Are you sure you want to delete \"{name}\"? This action cannot be undone." }, "modes": { - "darkMode": "Switch to Dark Mode", - "lightMode": "Switch to Light Mode" + "light": "Light Mode", + "dark": "Dark Mode" }, "shortcuts": { "help": "Get Help", diff --git a/dashboard/src/i18n/locales/en-US/features/settings.json b/dashboard/src/i18n/locales/en-US/features/settings.json index b497659ee4..0e24547168 100644 --- a/dashboard/src/i18n/locales/en-US/features/settings.json +++ b/dashboard/src/i18n/locales/en-US/features/settings.json @@ -1,6 +1,24 @@ { "network": { "title": "Network", + "proxy": { + "title": "Proxy", + "subtitle": "Configure proxy for network requests" + }, + "server": { + "title": "Server Address", + "subtitle": "Configure backend API URL", + "label": "API Base URL", + "placeholder": "e.g. http://localhost:6185", + "hint": "Empty for default (relative path)", + "save": "Save & Reload", + "presets": "Presets", + "preset": { + "add": "Add Preset", + "name": "Name", + "url": "URL" + } + }, "githubProxy": { "title": "GitHub Proxy Address", "subtitle": "Set the GitHub proxy address used when downloading plugins or updating AstrBot. This is effective in mainland China's network environment. Can be customized, input takes effect in real time. All addresses do not guarantee stability. If errors occur when updating plugins/projects, please first check if the proxy address is working properly.", @@ -21,11 +39,23 @@ "subtitle": "Customize theme primary and secondary colors. Changes apply immediately and are stored locally in your browser.", "customize": { "title": "Theme Colors", + "colors": "Custom Colors", + "preset": "Color Scheme", "primary": "Primary Color", "secondary": "Secondary Color", - "reset": "Reset to Default" + "reset": "Reset to Default", + "presetApplied": "Theme applied", + "light": "Light Mode", + "dark": "Dark Mode", + "auto": "System Mode", + "autoSwitchDesc": "Theme will automatically switch based on your browser's appearance setting when enable system mode" } }, + "reset": { + "title": "Reset to Default", + "subtitle": "Reset theme colors to default settings", + "button": "Reset" + }, "system": { "title": "System", "restart": { @@ -33,6 +63,11 @@ "subtitle": "Restart AstrBot", "button": "Restart" }, + "logout": { + "title": "Log Out", + "subtitle": "Log out of the current account", + "button": "Log Out" + }, "migration": { "title": "Data Migration to v4.0.0", "subtitle": "If you encounter data compatibility issues, you can manually start the database migration assistant", @@ -89,6 +124,10 @@ } }, "backup": { + "title": "Backup", + "subtitle": "Manage data backups", + "operate": "Backup Operations", + "open": "Open Backup Manager", "dialog": { "title": "Backup Manager" }, @@ -169,6 +208,14 @@ "subtitle": "Create API keys for external developers to call open HTTP APIs.", "name": "Key Name", "expiresInDays": "Expiration", + "expiry": { + "7days": "7 days", + "30days": "30 days", + "90days": "90 days", + "180days": "180 days", + "365days": "365 days", + "permanent": "Permanent" + }, "expiryOptions": { "day1": "1 day", "day7": "7 days", diff --git a/dashboard/src/i18n/locales/ru-RU/features/auth.json b/dashboard/src/i18n/locales/ru-RU/features/auth.json index d6ba05dc3b..2363943b3d 100644 --- a/dashboard/src/i18n/locales/ru-RU/features/auth.json +++ b/dashboard/src/i18n/locales/ru-RU/features/auth.json @@ -8,7 +8,7 @@ "subtitle": "Добро пожаловать" }, "theme": { - "switchToDark": "Перейти на темную тему", - "switchToLight": "Перейти на светлую тему" + "light": "Светла тема", + "dark": "Темная тема" } } \ No newline at end of file diff --git a/dashboard/src/i18n/locales/ru-RU/features/chat.json b/dashboard/src/i18n/locales/ru-RU/features/chat.json index cf574a1a0e..638b7e79c6 100644 --- a/dashboard/src/i18n/locales/ru-RU/features/chat.json +++ b/dashboard/src/i18n/locales/ru-RU/features/chat.json @@ -73,8 +73,8 @@ "confirmDelete": "Вы уверены, что хотите удалить «{name}»? Это действие необратимо." }, "modes": { - "darkMode": "Темная тема", - "lightMode": "Светлая тема" + "light": "Светлая тема", + "dark": "Темная тема" }, "shortcuts": { "help": "Справка", diff --git a/dashboard/src/i18n/locales/ru-RU/features/settings.json b/dashboard/src/i18n/locales/ru-RU/features/settings.json index d1100435f4..5aa686fad0 100644 --- a/dashboard/src/i18n/locales/ru-RU/features/settings.json +++ b/dashboard/src/i18n/locales/ru-RU/features/settings.json @@ -1,4 +1,4 @@ -{ +{ "network": { "title": "Сеть", "githubProxy": { @@ -21,9 +21,14 @@ "subtitle": "Настройка основных и дополнительных цветов. Изменения вступают в силу немедленно и сохраняются в браузере.", "customize": { "title": "Цвета темы", + "preset": "Цветовая схема", "primary": "Основной", "secondary": "Дополнительный", - "reset": "Сбросить" + "reset": "Сбросить", + "presetApplied": "Тема применена", + "light": "Светла тема", + "dark": "Темная тема", + "auto": "Автоматическая тема" } }, "system": { diff --git a/dashboard/src/i18n/locales/zh-CN/features/auth.json b/dashboard/src/i18n/locales/zh-CN/features/auth.json index d6da999430..e5390d35ff 100644 --- a/dashboard/src/i18n/locales/zh-CN/features/auth.json +++ b/dashboard/src/i18n/locales/zh-CN/features/auth.json @@ -8,7 +8,7 @@ "subtitle": "欢迎使用" }, "theme": { - "switchToDark": "切换到深色主题", - "switchToLight": "切换到浅色主题" + "light": "浅色主题", + "dark": "深色主题" } } \ No newline at end of file diff --git a/dashboard/src/i18n/locales/zh-CN/features/chat.json b/dashboard/src/i18n/locales/zh-CN/features/chat.json index 0bb669382a..683735f031 100644 --- a/dashboard/src/i18n/locales/zh-CN/features/chat.json +++ b/dashboard/src/i18n/locales/zh-CN/features/chat.json @@ -73,8 +73,8 @@ "confirmDelete": "确定要删除“{name}”吗?此操作无法撤销。" }, "modes": { - "darkMode": "切换到夜间模式", - "lightMode": "切换到日间模式" + "light": "浅色模式", + "dark": "深色模式" }, "shortcuts": { "help": "获取帮助", diff --git a/dashboard/src/i18n/locales/zh-CN/features/settings.json b/dashboard/src/i18n/locales/zh-CN/features/settings.json index 092b4a5d9b..59f10f7ac2 100644 --- a/dashboard/src/i18n/locales/zh-CN/features/settings.json +++ b/dashboard/src/i18n/locales/zh-CN/features/settings.json @@ -1,6 +1,24 @@ { "network": { "title": "网络", + "proxy": { + "title": "代理设置", + "subtitle": "配置网络请求代理" + }, + "server": { + "title": "服务器地址", + "subtitle": "配置后端 API 地址", + "label": "API 基础地址", + "placeholder": "例如:http://localhost:6185", + "hint": "留空以使用默认设置(相对路径)", + "save": "保存并刷新", + "presets": "预设列表", + "preset": { + "add": "添加预设", + "name": "名称", + "url": "URL" + } + }, "githubProxy": { "title": "GitHub 加速地址", "subtitle": "设置下载插件或者更新 AstrBot 时所用的 GitHub 加速地址。这在中国大陆的网络环境有效。可以自定义,输入结果实时生效。所有地址均不保证稳定性,如果在更新插件/项目时出现报错,请首先检查加速地址是否能正常使用。", @@ -21,11 +39,23 @@ "subtitle": "自定义主题主色与辅助色。修改后立即生效,并保存在浏览器本地。", "customize": { "title": "主题颜色", + "colors": "自定义颜色", + "preset": "配色方案", "primary": "主色", "secondary": "辅助色", - "reset": "恢复默认" + "reset": "恢复默认", + "presetApplied": "主题已应用", + "light": "浅色", + "dark": "深色", + "auto": "系统", + "autoSwitchDesc": "应用系统主题后,主题将根据您的浏览器外观设置自动切换" } }, + "reset": { + "title": "恢复默认", + "subtitle": "恢复主题颜色为默认设置", + "button": "恢复默认" + }, "system": { "title": "系统", "restart": { @@ -33,6 +63,11 @@ "subtitle": "重启 AstrBot", "button": "重启" }, + "logout": { + "title": "退出登录", + "subtitle": "退出当前账号,回到登录界面", + "button": "退出登录" + }, "migration": { "title": "数据迁移到 v4.0.0 格式", "subtitle": "如果您遇到数据兼容性问题,可以手动启动数据库迁移助手", @@ -89,6 +124,10 @@ } }, "backup": { + "title": "备份", + "subtitle": "管理数据备份", + "operate": "备份操作", + "open": "打开备份管理", "dialog": { "title": "备份管理" }, @@ -169,6 +208,14 @@ "subtitle": "为外部开发者创建 API Key,用于调用开放 HTTP API。", "name": "Key 名称", "expiresInDays": "有效期", + "expiry": { + "7days": "7 天", + "30days": "30 天", + "90days": "90 天", + "180days": "180 天", + "365days": "365 天", + "permanent": "永久" + }, "expiryOptions": { "day1": "1 天", "day7": "7 天", diff --git a/dashboard/src/layouts/full/vertical-header/VerticalHeader.vue b/dashboard/src/layouts/full/vertical-header/VerticalHeader.vue index bfd501ccc3..438b15e3fe 100644 --- a/dashboard/src/layouts/full/vertical-header/VerticalHeader.vue +++ b/dashboard/src/layouts/full/vertical-header/VerticalHeader.vue @@ -12,7 +12,6 @@ import 'katex/dist/katex.min.css'; import { useI18n } from '@/i18n/composables'; import { router } from '@/router'; import { useRoute } from 'vue-router'; -import { useTheme } from 'vuetify'; import StyledMenu from '@/components/shared/StyledMenu.vue'; import { useLanguageSwitcher } from '@/i18n/composables'; import type { Locale } from '@/i18n/types'; @@ -23,7 +22,6 @@ enableKatex(); enableMermaid(); const customizer = useCustomizerStore(); -const theme = useTheme(); const { t } = useI18n(); const route = useRoute(); const LAST_BOT_ROUTE_KEY = 'astrbot:last_bot_route'; @@ -369,12 +367,35 @@ function updateDashboard() { }); } -function toggleDarkMode() { - const newTheme = customizer.uiTheme === 'PurpleThemeDark' ? 'PurpleTheme' : 'PurpleThemeDark'; - customizer.SET_UI_THEME(newTheme); - theme.global.name.value = newTheme; +function toggleTheme() { + customizer.TOGGLE_DARK_MODE(); } +function autoSwitchTheme() { + // 根据浏览器主题同步页面主题 + customizer.APPLY_SYSTEM_THEME(); +} + +function autoSwitchThemeListener(e: MediaQueryListEvent) { + if (customizer.autoSwitchTheme) { + autoSwitchTheme(); + } +} + +// 通过 watch 变量来添加和移除监听器 +watch(() => customizer.autoSwitchTheme, (isAuto) => { + if (typeof window === 'undefined') return; + + const mediaQuery = window.matchMedia('(prefers-color-scheme: dark)'); + + if (isAuto) { + autoSwitchTheme(); + mediaQuery.addEventListener('change', autoSwitchThemeListener); + } else { + mediaQuery.removeEventListener('change', autoSwitchThemeListener); + } +}, { immediate: true }); + function openReleaseNotesDialog(body: string, tag: string) { selectedReleaseNotes.value = body; selectedReleaseTag.value = tag; @@ -680,17 +701,17 @@ onMounted(async () => { - {{ useCustomizerStore().uiTheme === 'PurpleThemeDark' ? t('core.header.buttons.theme.light') : t('core.header.buttons.theme.dark') }} + {{ customizer.isDarkTheme ? t('core.header.buttons.theme.light') : t('core.header.buttons.theme.dark') }} diff --git a/dashboard/src/layouts/full/vertical-sidebar/VerticalSidebar.vue b/dashboard/src/layouts/full/vertical-sidebar/VerticalSidebar.vue index e2636d211a..2266a690d0 100644 --- a/dashboard/src/layouts/full/vertical-sidebar/VerticalSidebar.vue +++ b/dashboard/src/layouts/full/vertical-sidebar/VerticalSidebar.vue @@ -1,7 +1,6 @@ diff --git a/dashboard/src/views/SubAgentPage.vue b/dashboard/src/views/SubAgentPage.vue index 4f71ddf78a..562b750bdf 100644 --- a/dashboard/src/views/SubAgentPage.vue +++ b/dashboard/src/views/SubAgentPage.vue @@ -214,7 +214,7 @@ import axios from 'axios' import { computed, onBeforeUnmount, onMounted, ref } from 'vue' import { onBeforeRouteLeave } from 'vue-router' -import { useTheme } from 'vuetify' +import { useCustomizerStore } from '@/stores/customizer' import PersonaQuickPreview from '@/components/shared/PersonaQuickPreview.vue' import PersonaSelector from '@/components/shared/PersonaSelector.vue' import ProviderSelector from '@/components/shared/ProviderSelector.vue' @@ -237,12 +237,12 @@ type SubAgentConfig = { } const { tm } = useModuleI18n('features/subagent') -const theme = useTheme() +const customizerStore = useCustomizerStore() const confirmDialog = useConfirmDialog() const loading = ref(false) const saving = ref(false) -const isDark = computed(() => theme.global.current.value.dark) +const isDark = computed(() => customizerStore.isDarkTheme) const snackbar = ref({ show: false, diff --git a/dashboard/src/views/authentication/auth/LoginPage.vue b/dashboard/src/views/authentication/auth/LoginPage.vue index acd1e798a2..a3fbba84de 100644 --- a/dashboard/src/views/authentication/auth/LoginPage.vue +++ b/dashboard/src/views/authentication/auth/LoginPage.vue @@ -6,20 +6,16 @@ import { useAuthStore } from '@/stores/auth'; import { useRouter } from 'vue-router'; import { useCustomizerStore } from "@/stores/customizer"; import { useModuleI18n } from '@/i18n/composables'; -import { useTheme } from 'vuetify'; const cardVisible = ref(false); const router = useRouter(); const authStore = useAuthStore(); const customizer = useCustomizerStore(); const { tm: t } = useModuleI18n('features/auth'); -const theme = useTheme(); // 主题切换函数 function toggleTheme() { - const newTheme = customizer.uiTheme === 'PurpleThemeDark' ? 'PurpleTheme' : 'PurpleThemeDark'; - customizer.SET_UI_THEME(newTheme); - theme.global.name.value = newTheme; + customizer.TOGGLE_DARK_MODE(); } onMounted(async () => { @@ -53,10 +49,10 @@ onMounted(async () => { style="height: 24px !important; opacity: 0.9 !important; align-self: center !important; border-color: rgba(var(--v-theme-primary), 0.45) !important;"> - {{ customizer.uiTheme === 'PurpleThemeDark' ? 'mdi-white-balance-sunny' : 'mdi-weather-night' }} + {{ customizer.isDarkTheme ? 'mdi-white-balance-sunny' : 'mdi-weather-night' }} - {{ customizer.uiTheme === 'PurpleThemeDark' ? t('theme.switchToLight') : t('theme.switchToDark') }} + {{ customizer.isDarkTheme ? t('theme.light') : t('theme.dark') }} diff --git a/dashboard/src/views/stats/StatsPage.vue b/dashboard/src/views/stats/StatsPage.vue index cb0a358c69..a3662c2e8b 100644 --- a/dashboard/src/views/stats/StatsPage.vue +++ b/dashboard/src/views/stats/StatsPage.vue @@ -207,8 +207,10 @@ import type { ApexOptions } from 'apexcharts' import axios from 'axios' import { computed, onBeforeUnmount, onMounted, ref, watch } from 'vue' -import { useTheme } from 'vuetify' import { useI18n, useModuleI18n } from '@/i18n/composables' +import { useTheme } from 'vuetify'; +import { useCustomizerStore } from '@/stores/customizer'; +import type { ThemeTypes } from '@/types/theme'; type TokenRange = 1 | 3 | 7 type ChartSeries = Array<{ @@ -278,29 +280,16 @@ interface ProviderTokenStatsResponse { const { locale } = useI18n() const { tm: t } = useModuleI18n('features/stats') -const theme = useTheme() +const theme = useTheme(); +const customizer = useCustomizerStore() const loading = ref(true) const errorMessage = ref('') const baseStats = ref(null) const providerStats = ref(null) const selectedRange = ref(1) const lastUpdatedAt = ref(null) -const isDark = computed(() => theme.global.current.value.dark) -const themePalette = computed(() => { - const colors = theme.global.current.value.colors as Record - return { - primary: colors.primary, - secondary: colors.secondary, - info: colors.info, - success: colors.success, - warning: colors.warning, - accent: colors.accent, - border: colors.border ?? colors.borderLight ?? colors.primary, - mutedText: colors.secondaryText ?? colors.primaryText ?? colors.primary, - lightPrimary: colors.lightprimary ?? colors.surface ?? colors.background, - lightSecondary: colors.lightsecondary ?? colors.surface ?? colors.background - } -}) +const isDark = computed(() => customizer.isDarkTheme) +const themeColors = computed(() => theme.current.value.colors as ThemeTypes['colors']) let refreshTimer: number | null = null @@ -537,29 +526,20 @@ const startTimeLabel = computed(() => formatDateTime(baseStats.value?.start_time ?? 0) ) -const providerChartColors = computed(() => - isDark.value - ? [ - '#6F8FAF', - '#7E9A73', - '#A78468', - '#8A78A8', - '#6B9995', - '#B07A87', - '#8C8F62', - '#7C8798' - ] - : [ - '#5F7E9B', - '#708865', - '#9A7557', - '#786696', - '#5D8985', - '#9C6674', - '#80844F', - '#69788D' - ] -) +const providerChartColors = computed(() => { + const colors = theme.current.value.colors; + // A harmonious palette derived from theme colors + return [ + colors.primary, + colors.secondary, + colors.info, + colors.success, + colors.warning, + colors.accent ?? '#FFAB91', + (colors as any).darkprimary ?? colors.primary, + (colors as any).darksecondary ?? colors.secondary, + ]; +}) const messageChartOptions = computed(() => ({ chart: { @@ -571,7 +551,7 @@ const messageChartOptions = computed(() => ({ theme: { mode: isDark.value ? 'dark' : 'light' }, - colors: [themePalette.value.primary], + colors: [themeColors.value.primary], stroke: { curve: 'smooth', width: 2.4 @@ -581,7 +561,7 @@ const messageChartOptions = computed(() => ({ opacity: 0.12 }, grid: { - borderColor: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26), + borderColor: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26), strokeDashArray: 0 }, dataLabels: { enabled: false }, @@ -589,15 +569,15 @@ const messageChartOptions = computed(() => ({ type: 'datetime', labels: { datetimeUTC: false, - style: { colors: themePalette.value.mutedText } + style: { colors: themeColors.value.secondaryText ?? themeColors.value.primaryText ?? themeColors.value.primary } }, - axisBorder: { color: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26) }, - axisTicks: { color: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26) } + axisBorder: { color: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26) }, + axisTicks: { color: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26) } }, yaxis: { labels: { formatter: (value) => formatCompactNumber(Number(value)), - style: { colors: themePalette.value.mutedText } + style: { colors: themeColors.value.secondaryText ?? themeColors.value.primaryText ?? themeColors.value.primary } } }, tooltip: { @@ -630,21 +610,21 @@ const providerChartOptions = computed(() => ({ colors: providerChartColors.value, dataLabels: { enabled: false }, grid: { - borderColor: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26) + borderColor: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26) }, xaxis: { type: 'datetime', labels: { datetimeUTC: false, - style: { colors: themePalette.value.mutedText } + style: { colors: themeColors.value.secondaryText ?? themeColors.value.primaryText ?? themeColors.value.primary } }, - axisBorder: { color: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26) }, - axisTicks: { color: hexToRgba(themePalette.value.border, isDark.value ? 0.4 : 0.26) } + axisBorder: { color: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26) }, + axisTicks: { color: hexToRgba(themeColors.value.border ?? themeColors.value.borderLight ?? themeColors.value.primary, isDark.value ? 0.4 : 0.26) } }, yaxis: { labels: { formatter: (value) => formatCompactNumber(Number(value)), - style: { colors: themePalette.value.mutedText } + style: { colors: themeColors.value.secondaryText ?? themeColors.value.primaryText ?? themeColors.value.primary } } }, tooltip: { @@ -657,7 +637,7 @@ const providerChartOptions = computed(() => ({ position: 'top', horizontalAlign: 'left', labels: { - colors: themePalette.value.mutedText + colors: themeColors.value.secondaryText ?? themeColors.value.primaryText ?? themeColors.value.primary } } }))