Skip to content

Commit

Permalink
feat(maz-ui): useLanguageDisplayNames - new composable get and manage…
Browse files Browse the repository at this point in the history
… languages
  • Loading branch information
LouisMazel committed Oct 11, 2024
1 parent fd93594 commit 77adc06
Show file tree
Hide file tree
Showing 11 changed files with 501 additions and 23 deletions.
1 change: 1 addition & 0 deletions packages/docs/docs/.vitepress/configs/composables.mts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ export const composables = {
{ text: 'useDialog', link: '/composables/use-dialog' },
{ text: 'useFormValidator', link: '/composables/use-form-validator' },
{ text: 'useIdleTimeout', link: '/composables/use-idle-timeout' },
{ text: 'useLanguageDisplayNames', link: '/composables/use-language-display-names' },
{ text: 'useReadingTime', link: '/composables/use-reading-time' },
{ text: 'useStringMatching', link: '/composables/use-string-matching' },
{ text: 'useThemeHandler', link: '/composables/use-theme-handler' },
Expand Down
2 changes: 1 addition & 1 deletion packages/docs/docs/components/maz-accordion.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
---
title: MazAccordion
description: MazAccordion is a standalone component
description: MazAccordion is a standalone component that allows you to create an accordion with a title and content.
---

# {{ $frontmatter.title }}
Expand Down
9 changes: 8 additions & 1 deletion packages/docs/docs/components/maz-phone-number-input.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ npm install libphonenumber-js
:preferred-countries="['FR', 'BE', 'DE', 'US', 'GB']"
:ignored-countries="['AC']"
@update="results = $event"
:auto-format="false"
/>

<br />
Expand Down Expand Up @@ -141,6 +140,14 @@ Two ways to translate the country list:
/>
```

## Auto formatting

Becareful, the auto formatting is enabled by default and can have some issues with some countries with multiple valid number lengths like Anguilla (AI), you can disable it with the `auto-format` prop

```html
<MazPhoneNumberInput v-model="phoneNumber" :auto-format="false" />
```

## Orientation

`@default "responsive"`
Expand Down
174 changes: 174 additions & 0 deletions packages/docs/docs/composables/use-language-display-names.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,174 @@
---
title: useLanguageDisplayNames
description: useLanguageDisplayNames is a Vue 3 composable that provides functions to work with language display names based on ISO codes. It leverages the Intl.DisplayNames API to fetch and format language names. This composable is useful for applications that need to display language names in a user-friendly format based on different locales.
---

# {{ $frontmatter.title }}

{{ $frontmatter.description }}

## Introduction

`useLanguageDisplayNames` allows you to fetch and format language names based on ISO codes using the `Intl.DisplayNames` API. This composable is particularly useful for applications that need to display language names in a user-friendly format based on different locales.

## Key Features

- Fetches language display names based on ISO codes
- Supports multiple locales
- Provides functions to get display names for all possible languages
- Handles errors gracefully and provides fallback values

## Basic Usage

To see `useLanguageDisplayNames` in action, you can try out the following demo. This demo showcases how to use the composable to fetch and display language names dynamically based on user input.

<ComponentDemo>
<div class="maz-flex maz-flex-col maz-gap-4 maz-items-start">
<MazSelect
v-model="selectedLocale"
label="Select a locale"
:maxListHeight="350"
:options="[
{ value: 'en-US', label: 'English (en-US)' },
{ value: 'fr-FR', label: 'French (fr-FR)' },
{ value: 'es-ES', label: 'Spanish (es-ES)' },
{ value: 'zh-CN', label: 'Chinese (zh-CN)' },
{ value: 'de-DE', label: 'German (de-DE)' },
{ value: 'it-IT', label: 'Italian (it-IT)' },
{ value: 'ja-JP', label: 'Japanese (ja-JP)' },
{ value: 'ko-KR', label: 'Korean (ko-KR)' },
{ value: 'pt-BR', label: 'Portuguese (pt-BR)' },
{ value: 'ru-RU', label: 'Russian (ru-RU)' },
]"
search
/>
<MazSelect
v-model="isoCode"
label="Select a language"
:options="localeOptions"
search
/>
<p>Language Display Name: {{ languageDisplayName || 'undefined' }}</p>
</div>

<template #code>

```vue
<template>
<MazSelect
v-model="selectedLocale"
label="Select a locale"
:maxListHeight="350"
:options="[
{ value: 'en-US', label: 'English (en-US)' },
{ value: 'fr-FR', label: 'French (fr-FR)' },
{ value: 'es-ES', label: 'Spanish (es-ES)' },
{ value: 'zh-CN', label: 'Chinese (zh-CN)' },
{ value: 'de-DE', label: 'German (de-DE)' },
{ value: 'it-IT', label: 'Italian (it-IT)' },
{ value: 'ja-JP', label: 'Japanese (ja-JP)' },
{ value: 'ko-KR', label: 'Korean (ko-KR)' },
{ value: 'pt-BR', label: 'Portuguese (pt-BR)' },
{ value: 'ru-RU', label: 'Russian (ru-RU)' },
]"
search
/>
<MazSelect
v-model="isoCode"
label="Select a language"
:options="localeOptions"
search
/>
<p>Language Display Name: {{ languageDisplayName || 'undefined' }}</p>
</template>
<script lang="ts" setup>
import { ref, computed } from 'vue'
import { useLanguageDisplayNames } from 'maz-ui'
const selectedLocale = ref('en-US')
const isoCode = ref('')
const { getLanguageDisplayName, getAllPossibleLanguages } = useLanguageDisplayNames(selectedLocale)
const languageDisplayName = getLanguageDisplayName({ isoCode })
const localeOptions = computed(() => getAllPossibleLanguages('en-US').value.map(({ language, code }) => ({
label: `${language} (${code})`,
value: code
})))
</script>
```

</template>

</ComponentDemo>

In this example, the `useLanguageDisplayNames` composable is used to fetch and display the language name based on the selected locale and ISO code.

The returned value is reactive and will update automatically when the locale or ISO code changes if arguments are reactive (use ref or computed).

## Functions

`useLanguageDisplayNames` can take a locale and ISO code as arguments to avoid pass this value each time you call the function. It is useful when you need to fetch language display names based on the same locale.

It provides the following functions:

### `getLanguageDisplayName`

Fetches the display name of a language based on the provided locale and ISO code.

```ts
function getLanguageDisplayName(options: {
locale?: MaybeRefOrGetter<string>,
isoCode?: MaybeRefOrGetter<string>
}): ComputedRef<string | undefined>
```

### `getAllPossibleLanguages`

Fetches all possible language display names for a given locale.

```ts
function getAllPossibleLanguages(
locale?: MaybeRefOrGetter<string>
): ComputedRef<{ language: string; code: string }[]>
```

### `getDisplayNamesForIsoCodes`

Fetches the display names for all predefined ISO codes for a given locale.

```ts
function getLanguageDisplayNamesForIsoCodes(
locale?: MaybeRefOrGetter<string>
): ComputedRef<{ language: string; code: string }[]>
```

## Notes

- The `useLanguageDisplayNames` composable is designed to be used with Vue 3.
- The composable functions return `ComputedRef` values, which are reactive and will update automatically when their dependencies change.
- Handle errors gracefully by providing fallback values when the display name cannot be fetched.
- The `Intl.DisplayNames` API is used internally to fetch and format the language names based on the provided locale and ISO code.
- The composable supports multiple locales, allowing you to fetch language names in different languages.
- Use the `getAllPossibleLanguages` function to fetch all possible language display names for a given locale.
- Use the `getDisplayNamesForIsoCodes` function to fetch the display names for all predefined ISO codes for a given locale.

<script lang="ts" setup>
import { ref, computed } from 'vue'
import { useLanguageDisplayNames } from 'maz-ui'

const selectedLocale = ref('en-US')
const isoCode = ref('')

const { getLanguageDisplayName, getAllPossibleLanguages } = useLanguageDisplayNames(selectedLocale)

const languageDisplayName = getLanguageDisplayName({ isoCode })

const localeOptions = computed(() => getAllPossibleLanguages('en-US').value.map(({ language, code }) => ({
label: `${language} (${code})`,
value: code
})))
</script>
9 changes: 1 addition & 8 deletions packages/docs/docs/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,8 @@ hero:
<MazBtn href="/composables/use-theme-handler" color="theme" size="md" pastel rounded>Composables</MazBtn>
<MazBtn href="/helpers/currency" color="theme" size="md" pastel rounded>Helpers</MazBtn>
<MazBtn href="/directives/zoom-img" color="theme" size="md" pastel rounded>Directives</MazBtn>
<MazBtn rounded v-if="typeof starCount === 'number'" href="https://github.com/LouisMazel/maz-ui" target="blank" outline color="theme" size="sm">
<template #left-icon>
<GithubIcon class="maz-text-lg" />
</template>
<MazBtn rounded v-if="typeof starCount === 'number'" href="https://github.com/LouisMazel/maz-ui" target="blank" outline color="theme" left-icon="github" size="md" :right-icon="StarIcon">
<MazAnimatedCounter :count="starCount" class="maz-text-xl maz-pl-2" />
<template #right-icon>
<StarIcon class="maz-text-lg" />
</template>
</MazBtn>
</div>

Expand Down Expand Up @@ -101,7 +95,6 @@ hero:

<script lang="ts" setup>
import { ref } from 'vue'
import GithubIcon from 'maz-ui/icons/github.svg'
import StarIcon from 'maz-ui/icons/star-solid.svg'

const GITHUB_TOKEN = import.meta.env.VITE_GITHUB_TOKEN;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import { normalizeString, type NormalizeStringOptions } from '../modules/helpers
import { computed, defineAsyncComponent, ref, watch } from 'vue'
import MazCardSpotlight from './MazCardSpotlight.vue'
import MazCheckbox from './MazCheckbox.vue'
import MazInput from './MazInput.vue'
export type ItemOption = {
label: string
Expand Down Expand Up @@ -75,6 +74,7 @@ const props = withDefaults(
color: 'primary',
},
)
const emits = defineEmits<{
/**
* Emitted when the query change
Expand All @@ -87,11 +87,14 @@ const emits = defineEmits<{
*/
'update:model-value': [value?: T[]]
}>()
const MazInput = defineAsyncComponent(() => import('./MazInput.vue'))
const SearchIcon = defineAsyncComponent(
() => import('maz-ui/icons/magnifying-glass.svg'),
() => import('../icons/magnifying-glass.svg'),
)
const NoResultsIcon = defineAsyncComponent(
() => import('maz-ui/icons/no-symbol.svg'),
() => import('../icons/no-symbol.svg'),
)
const internalQuery = ref<string | undefined>(props.query)
Expand Down
1 change: 1 addition & 0 deletions packages/lib/modules/composables/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ export * from './useDialog'
export * from './useFormValidator'
export * from './useIdleTimeout'
export * from './useInstanceUniqId'
export * from './useLanguageDisplayNames'
export * from './useReadingTime'
export * from './useStringMatching'
export * from './useSwipe'
Expand Down
Loading

0 comments on commit 77adc06

Please sign in to comment.