diff --git a/.gitignore b/.gitignore index 313b02a4f497fe12e0b022756543c5fa7b6805f5..da57c694e1f183176f15e045e711faa77c7ff8bb 100644 --- a/.gitignore +++ b/.gitignore @@ -27,3 +27,4 @@ pnpm-debug.log* # vitepress public .vitepress +docs/.vitepress/cache diff --git a/docs/.vitepress/theme/index.ts b/docs/.vitepress/theme/index.ts index 95be264b6981d2ac8e78c38c4e35655e5a143801..5d833c9b3183c1be7e4b232004224b4052e9ba62 100644 --- a/docs/.vitepress/theme/index.ts +++ b/docs/.vitepress/theme/index.ts @@ -1,20 +1,9 @@ -import { createI18n } from 'vue-i18n' - import DefaultTheme from 'vitepress/theme' -import en from '~/locales/en.yaml' import Funkwhale from '~/main' export default { ...DefaultTheme, enhanceApp({ app }) { - const i18n = createI18n({ - legacy: false, - locale: 'en', - fallbackLocale: 'en', - messages: { en } - }) - app.use(Funkwhale) - app.use(i18n) } } diff --git a/src/composables/useI18n.ts b/src/composables/useI18n.ts new file mode 100644 index 0000000000000000000000000000000000000000..525d0dc4b1889c5cfca29bc88587aae6c5ec2c8d --- /dev/null +++ b/src/composables/useI18n.ts @@ -0,0 +1,35 @@ +import type { I18n } from "vue-i18n" + +import { isRef, watch, type Ref } from "vue" + +import en from '~/locales/en.yaml' + +let i18nInstance: I18n +const provideI18n = (i18n: I18n) => { + if (!isRef(i18n.global.locale) || i18n.mode !== 'composition') { + console.warn('[vui] locales won\'t be updated when provided i18n instance is in legacy mode') + i18nInstance = i18n + return + } + + const globalMessages = i18n.global.messages as Ref<Record<string, typeof en>> + watch(i18n.global.locale, async (locale, from) => { + globalMessages.value[locale] ??= {} + if ('vui' in globalMessages.value[locale]) return + + try { + const { default: messages } = await import(`~/locales/${locale}.yaml`) + globalMessages.value[locale] = { ...globalMessages.value[locale], ...messages } + } catch (err) { + console.warn(`[vui] Locale '${locale}' not found`) + } + }, { immediate: true }) + + i18nInstance = i18n +} + +const useI18nInstance = () => { + return i18nInstance +} + +export { provideI18n, useI18nInstance } diff --git a/src/main.ts b/src/main.ts index 6b354846903b1a6ef4a2fe76bf399b499d5cbfae..da25feaa3f98d89806ae1c9b033d97377accd4c5 100644 --- a/src/main.ts +++ b/src/main.ts @@ -1,12 +1,33 @@ +import { createI18n, type I18n } from 'vue-i18n' import type { App } from 'vue' import '~/styles/funkwhale.scss' import * as components from '~/components' +import { provideI18n } from './composables/useI18n' +import en from '~/locales/en.yaml' + export * from '~/components' +interface VuiOptions { + i18n?: I18n +} + export default { - install (app: App) { + install (app: App, options: VuiOptions = {}) { + if (!options.i18n) { + options.i18n = createI18n({ + legacy: false, + locale: 'en', + fallbackLocale: 'en', + messages: { en } + }) + + app.use(options.i18n) + } + + provideI18n(options.i18n) + for (const prop in components) { const component = components[prop as keyof typeof components] app.component(prop, component) diff --git a/vite.config.ts b/vite.config.ts index 81ce4c84a4b091e373c4308d4da385f93335dc0b..e42eedeeb96f9d7036516df8a1fb3982a467615e 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -1,6 +1,7 @@ import { defineConfig } from 'vite' import { resolve } from 'path' +import yaml from '@modyfi/vite-plugin-yaml' import vue from '@vitejs/plugin-vue' import dts from 'vite-plugin-dts' @@ -8,6 +9,7 @@ import dts from 'vite-plugin-dts' export default defineConfig(() => ({ plugins: [ vue(), + yaml(), dts({ insertTypesEntry: true, outputDir: resolve(__dirname, 'dist/types')