feat(module): support i18n in components (#2553)

Co-authored-by: Benjamin Canac <canacb1@gmail.com>
This commit is contained in:
Alex
2024-11-08 21:22:57 +05:00
committed by GitHub
parent 1e7638bd03
commit 26362408b1
30 changed files with 673 additions and 18 deletions

View File

@@ -79,6 +79,11 @@ const updatedNavigation = computed(() => navigation.value?.map(item => ({
title: 'Installation',
active: route.path.startsWith('/getting-started/installation'),
children: []
}),
...(child.path === '/getting-started/i18n' && {
title: 'I18n',
active: route.path.startsWith('/getting-started/i18n'),
children: []
})
})) || []
})))

View File

@@ -0,0 +1,181 @@
---
navigation.title: Nuxt
title: Internationalization (i18n) in a Nuxt app
description: 'Learn how to internationalize your Nuxt app and support multi-directional support (LTR/RTL).'
select:
items:
- label: Nuxt
icon: i-logos-nuxt-icon
to: /getting-started/i18n/nuxt
- label: Vue
icon: i-logos-vue
to: /getting-started/i18n/vue
---
## Usage
Nuxt UI provides an [App](/components/app) component that wraps your app to provide global configurations.
### Locale
Use the `locale` prop with the locale you want to use from `@nuxt/ui/locale`:
```vue [app.vue]
<script setup lang="ts">
import { fr } from '@nuxt/ui/locale'
</script>
<template>
<UApp :locale="fr">
<NuxtPage />
</UApp>
</template>
```
#### Custom locale
You also have the option to add your own locale using `defineLocale`:
```vue [app.vue]
<script setup lang="ts">
const locale = defineLocale('My custom locale', {
// implement pairs
})
</script>
<template>
<UApp :locale="locale">
<NuxtPage />
</UApp>
</template>
```
#### Dynamic locale
To dynamically switch between languages, you can use the [NuxtI18n](https://i18n.nuxtjs.org/docs/getting-started) module.
1. Install the `@nuxtjs/i18n` package:
::code-group{sync="pm"}
```bash [pnpm]
pnpm add @nuxtjs/i18n@next
```
```bash [yarn]
yarn add @nuxtjs/i18n@next
```
```bash [npm]
npm install @nuxtjs/i18n@next
```
```bash [bun]
bun add @nuxtjs/i18n@next
```
::
2. Add the `@nuxtjs/i18n` module to your `nuxt.config.ts`{lang="ts-type"} and define the locales you want to support:
```ts [nuxt.config.ts]
export default defineNuxtConfig({
modules: [
'@nuxt/ui',
'@nuxtjs/i18n'
],
i18n: {
locales: [{
code: 'de',
name: 'Deutsch'
}, {
code: 'en',
name: 'English'
}, {
code: 'fr',
name: 'Français'
}]
}
})
```
3. Use the `locale` prop with the `useI18n` locale you want to use from `@nuxt/ui/locale`:
```vue [app.vue]
<script setup lang="ts">
import * as locales from '@nuxt/ui/locale'
const { locale } = useI18n()
</script>
<template>
<UApp :locale="locales[locale]">
<NuxtPage />
</UApp>
</template>
```
### Direction
Use the `dir` prop with `ltr` or `rtl` to set the global reading direction of your app:
```vue [app.vue]
<template>
<UApp dir="rtl">
<NuxtPage />
</UApp>
</template>
```
#### Dynamic direction
To dynamically change the global reading direction of your app, you can use the [useTextDirection](https://vueuse.org/core/useTextDirection/) composable.
1. Install the `@vueuse/core` package:
::code-group{sync="pm"}
```bash [pnpm]
pnpm add @vueuse/core
```
```bash [yarn]
yarn add @vueuse/core
```
```bash [npm]
npm install @vueuse/core
```
```bash [bun]
bun add @vueuse/core
```
::
2. Then in your `app.vue`:
```vue [app.vue]
<script setup lang="ts">
import { useTextDirection } from '@vueuse/core'
const textDirection = useTextDirection({ initialValue: 'ltr' })
const dir = computed(() => textDirection.value === 'rtl' ? 'rtl' : 'ltr')
</script>
<template>
<UApp :dir="dir">
<NuxtPage />
</UApp>
</template>
```
## Supported languages
<!-- TODO: add auto generating language list https://github.com/nuxt/ui/issues/2565 -->
* `de` - Deutsch
* `en` - English (default)
* `fr` - Français
* `ru` - Русский
If you need any other languages, a [PR](https://github.com/nuxt/ui/pulls) is always welcome, you only need to add a language file [here](https://github.com/nuxt/ui/tree/v3/src/runtime/locale).

View File

@@ -0,0 +1,190 @@
---
navigation.title: Vue
title: Internationalization (i18n) in a Vue app
description: 'Learn how to internationalize your Vue app and support multi-directional support (LTR/RTL).'
select:
items:
- label: Nuxt
icon: i-logos-nuxt-icon
to: /getting-started/i18n/nuxt
- label: Vue
icon: i-logos-vue
to: /getting-started/i18n/vue
---
## Usage
Nuxt UI provides an [App](/components/app) component that wraps your app to provide global configurations.
### Locale
Use the `locale` prop with the locale you want to use from `@nuxt/ui/locale`:
```vue [App.vue]
<script setup lang="ts">
import { fr } from '@nuxt/ui/locale'
</script>
<template>
<UApp :locale="fr">
<RouterView />
</UApp>
</template>
```
#### Custom locale
You also have the option to add your locale using `defineLocale`:
```vue [App.vue]
<script setup lang="ts">
import { defineLocale } from '@nuxt/ui/runtime/composables/defineLocale'
const locale = defineLocale('My custom locale', {
// implement pairs
})
</script>
<template>
<UApp :locale="locale">
<RouterView />
</UApp>
</template>
```
#### Dynamic locale
To dynamically switch between languages, you can use the [VueI18n](https://vue-i18n.intlify.dev/) plugin.
1. Install the `vue-i18n` package:
::code-group{sync="pm"}
```bash [pnpm]
pnpm add vue-i18n@10
```
```bash [yarn]
yarn add vue-i18n@10
```
```bash [npm]
npm install vue-i18n@10
```
```bash [bun]
bun add vue-i18n@10
```
::
2. Define the `createI18n` instance and register the `i18n` plugin in your `main.ts` file:
```ts{3-19,22} [main.ts]
import { createApp } from 'vue'
import App from './App.vue'
import { createI18n } from 'vue-i18n'
const messages = {
en: {
// ...
},
de: {
// ...
},
}
const i18n = createI18n({
legacy: false,
locale: 'en',
availableLocales: ['en', 'de'],
messages,
})
createApp(App)
.use(i18n)
.mount('#app')
```
3. Use the `locale` prop with the `useI18n` locale you want to use from `@nuxt/ui/locale`:
```vue [App.vue]
<script setup lang="ts">
import { useI18n } from 'vue-i18n'
import * as locales from '@nuxt/ui/locale'
const { locale } = useI18n()
</script>
<template>
<UApp :locale="locales[locale]">
<RouterView />
</UApp>
</template>
```
### Direction
Use the `dir` prop with `ltr` or `rtl` to set the global reading direction of your app:
```vue [App.vue]
<template>
<UApp dir="rtl">
<NuxtPage />
</UApp>
</template>
```
#### Dynamic direction
To dynamically change the global reading direction of your app, you can use the [useTextDirection](https://vueuse.org/core/useTextDirection/) composable.
1. Install the `@vueuse/core` package:
::code-group{sync="pm"}
```bash [pnpm]
pnpm add @vueuse/core
```
```bash [yarn]
yarn add @vueuse/core
```
```bash [npm]
npm install @vueuse/core
```
```bash [bun]
bun add @vueuse/core
```
::
2. Then in your `App.vue`:
```vue [App.vue]
<script setup lang="ts">
import { computed } from 'vue'
import { useTextDirection } from '@vueuse/core'
const textDirection = useTextDirection()
const dir = computed(() => textDirection.value === 'rtl' ? 'rtl' : 'ltr')
</script>
<template>
<UApp :dir="dir">
<RouterView />
</UApp>
</template>
```
## Supported languages
<!-- TODO: add auto generating language list https://github.com/nuxt/ui/issues/2565 -->
* `de` - Deutsch
* `en` - English (default)
* `fr` - Français
* `ru` - Русский
If you need any other languages, a [PR](https://github.com/nuxt/ui/pulls) is always welcome, you only need to add a language file [here](https://github.com/nuxt/ui/tree/v3/src/runtime/locale).

View File

@@ -27,6 +27,14 @@ Use it as at the root of your app:
</template>
```
::tip{to="/getting-started/i18n/nuxt#locale"}
Learn how to use the `locale` prop to change the locale of your app.
::
::tip{to="/getting-started/i18n/nuxt#direction"}
Learn how to use the `dir` prop to change the global reading direction of your app.
::
## API
### Props

View File

@@ -57,6 +57,7 @@ export default defineNuxtConfig({
routeRules: {
'/': { redirect: '/getting-started', prerender: false },
'/getting-started/installation': { redirect: '/getting-started/installation/nuxt', prerender: false },
'/getting-started/i18n': { redirect: '/getting-started/i18n/nuxt', prerender: false },
'/composables': { redirect: '/composables/define-shortcuts', prerender: false },
'/components': { redirect: '/components/app', prerender: false }
},