From 6153c7e87e8795e029885e0c9eda2d4abe069b2a Mon Sep 17 00:00:00 2001 From: gushen610140 Date: Wed, 18 Feb 2026 01:56:07 +0800 Subject: [PATCH] feat: dynamic language change --- components.d.ts | 2 ++ src/components/special/AnimText.vue | 27 +++++++++++++++++++++++++++ src/hooks/bus/index.ts | 4 ++++ src/hooks/bus/languageChangeBus.ts | 4 ++++ src/hooks/globalLanguageHook.ts | 10 ++++++++-- src/pages/index.vue | 20 ++++++++++++++------ src/style.css | 5 +++-- 7 files changed, 62 insertions(+), 10 deletions(-) create mode 100644 src/components/special/AnimText.vue create mode 100644 src/hooks/bus/index.ts create mode 100644 src/hooks/bus/languageChangeBus.ts diff --git a/components.d.ts b/components.d.ts index 75fc332..e3f9c38 100644 --- a/components.d.ts +++ b/components.d.ts @@ -13,6 +13,7 @@ export {} declare module 'vue' { export interface GlobalComponents { AnimatePresence: typeof import('motion-v')['AnimatePresence'] + AnimText: typeof import('./src/components/special/AnimText.vue')['default'] AuthDialog: typeof import('./src/components/dialog/AuthDialog.vue')['default'] Button: typeof import('./src/components/ui/button/Button.vue')['default'] Calendar: typeof import('./src/components/ui/calendar/Calendar.vue')['default'] @@ -52,6 +53,7 @@ declare module 'vue' { // For TSX support declare global { const AnimatePresence: typeof import('motion-v')['AnimatePresence'] + const AnimText: typeof import('./src/components/special/AnimText.vue')['default'] const AuthDialog: typeof import('./src/components/dialog/AuthDialog.vue')['default'] const Button: typeof import('./src/components/ui/button/Button.vue')['default'] const Calendar: typeof import('./src/components/ui/calendar/Calendar.vue')['default'] diff --git a/src/components/special/AnimText.vue b/src/components/special/AnimText.vue new file mode 100644 index 0000000..21641cb --- /dev/null +++ b/src/components/special/AnimText.vue @@ -0,0 +1,27 @@ + + + + + diff --git a/src/hooks/bus/index.ts b/src/hooks/bus/index.ts new file mode 100644 index 0000000..66e6197 --- /dev/null +++ b/src/hooks/bus/index.ts @@ -0,0 +1,4 @@ +export const keys = { + user: "user", + language: "language", +}; diff --git a/src/hooks/bus/languageChangeBus.ts b/src/hooks/bus/languageChangeBus.ts new file mode 100644 index 0000000..47e216e --- /dev/null +++ b/src/hooks/bus/languageChangeBus.ts @@ -0,0 +1,4 @@ +import { useEventBus } from "@vueuse/core"; +import { keys } from "./index"; + +export const languageChangeBus = useEventBus(keys.language); diff --git a/src/hooks/globalLanguageHook.ts b/src/hooks/globalLanguageHook.ts index 8e3b894..a099418 100644 --- a/src/hooks/globalLanguageHook.ts +++ b/src/hooks/globalLanguageHook.ts @@ -3,6 +3,7 @@ import { GlobalLanguage, languageMap, } from "@/stores/LanguageStore"; +import { languageChangeBus } from "./bus/languageChangeBus"; const languageStore = useLanguageStore(); @@ -20,8 +21,13 @@ function changeGlobalLanguage( language: GlobalLanguage, locale: WritableComputedRef, ) { - languageStore.setLanguage(language); - locale.value = language; + // 延迟切换先通知其他组件播放动画 + languageChangeBus.emit("language changed"); + + setTimeout(() => { + languageStore.setLanguage(language); + locale.value = language; + }, 300); } export const useGlobalLanguageHook = () => ({ diff --git a/src/pages/index.vue b/src/pages/index.vue index 6978b5b..11f3507 100644 --- a/src/pages/index.vue +++ b/src/pages/index.vue @@ -3,6 +3,7 @@ import DatePickerDisplayCard from "@/components/card/DatePickerDisplayCard.vue"; import DevelopProgressCard from "@/components/card/DevelopProgressCard.vue"; import FooterBar from "@/components/layout/FooterBar.vue"; import NavBar from "@/components/menu/NavBar.vue"; +import AnimText from "@/components/special/AnimText.vue"; import { navigateTo } from "@/utils/navigator"; const progress = ref([ @@ -46,17 +47,24 @@ const progress = ref([
-

{{ $t("home.welcome") }}

-

- {{ $t("home.intro_line1") }}
+ +

+ +

+
+ +
+
+ +
diff --git a/src/style.css b/src/style.css index 1b943aa..e8f22cb 100644 --- a/src/style.css +++ b/src/style.css @@ -9,8 +9,9 @@ @plugin "daisyui/theme" { name: "light"; - --color-primary: blue; - --color-secondary: teal; + --color-primary: #5092d4; + --color-secondary: #bfd7f1; + --color-accent: #76b9ef; } /* Custom Scrollbar Styles */