UNPKG

@yamada-ui/react

Version:

React UI components of the Yamada, by the Yamada, for the Yamada built with React and Emotion

125 lines (121 loc) 4.03 kB
"use client"; import { useUpdateEffect } from "../../utils/effect.js"; import { utils_exports } from "../../utils/index.js"; import { DEFAULT_DIRECTION, DEFAULT_LOCALE } from "../../core/constant.js"; import intl_default from "./intl/index.js"; import { createContext, useCallback, useContext, useEffect, useMemo, useState } from "react"; import { jsx } from "react/jsx-runtime"; import IntlMessageFormat from "intl-messageformat"; //#region src/providers/i18n-provider/i18n-provider.tsx const DEFAULT_LANGUAGE = { dir: DEFAULT_DIRECTION, locale: DEFAULT_LOCALE }; const LOCALES = Object.keys(intl_default); function getLanguage(locale, dir) { locale ??= (0, utils_exports.createdDom)() ? navigator.language : DEFAULT_LOCALE; try { Intl.DateTimeFormat.supportedLocalesOf([locale]); } catch (_err) { locale = DEFAULT_LOCALE; } dir ??= (0, utils_exports.isRtl)(locale) ? "rtl" : "ltr"; return { dir, locale }; } const I18nContext = createContext({ ...DEFAULT_LANGUAGE, changeLanguage: utils_exports.noop, getTranslation: () => () => "", t: () => "" }); const I18nProvider = ({ children, dir: forcedDir, formats, intl = intl_default, intlMessageFormatOptions, locale: forcedLocale }) => { const [language, setLanguage] = useState(getLanguage(forcedLocale, forcedDir)); const controlled = !(0, utils_exports.isUndefined)(forcedLocale); const { locale } = language; const messages = useMemo(() => intl[locale], [intl, locale]); const changeSystemLanguage = useCallback(() => { setLanguage(getLanguage()); }, []); const changeLanguage = useCallback((locale$1, dir) => { setLanguage(getLanguage(locale$1, dir)); }, []); const getValue = useCallback((path) => { const value$1 = (0, utils_exports.getMemoizedObject)(messages, path); if (!(0, utils_exports.isUndefined)(value$1)) return value$1; else { path = path.toString().replace(/^[^.]+\./g, ""); return (0, utils_exports.getMemoizedObject)(messages, path); } }, [messages]); const getTranslation = useCallback((key) => (path, replaceValues) => { const value$1 = getValue(key ? `${key}.${path}` : path) ?? path; if ((0, utils_exports.isUndefined)(replaceValues)) return value$1; try { const resolvedReplaceValues = Object.entries(replaceValues).reduce((prev, [key$1, pathOrValue]) => { if ((0, utils_exports.isString)(pathOrValue)) { const resolvedPathOrValue = String(pathOrValue); prev[key$1] = getValue(key$1 ? `${key$1}.${resolvedPathOrValue}` : resolvedPathOrValue) ?? resolvedPathOrValue; } else prev[key$1] = pathOrValue; return prev; }, {}); return new IntlMessageFormat(value$1, locale, formats, intlMessageFormatOptions).format(resolvedReplaceValues); } catch (e) { if (e instanceof Error) console.warn(e.message); return value$1; } }, [ getValue, locale, formats, intlMessageFormatOptions ]); const value = useMemo(() => { const rest = { changeLanguage, getTranslation, t: getTranslation() }; return { ...language, ...rest }; }, [ changeLanguage, getTranslation, language ]); useEffect(() => { if (controlled) return; window.addEventListener("languagechange", changeSystemLanguage); return () => { window.removeEventListener("languagechange", changeSystemLanguage); }; }, [controlled, changeSystemLanguage]); useUpdateEffect(() => { setLanguage(getLanguage(forcedLocale, forcedDir)); }, [forcedLocale, forcedDir]); return /* @__PURE__ */ jsx(I18nContext, { value, children }); }; function useI18n(key) { const context = useContext(I18nContext); const translation = useCallback((path, replaceValues) => context.getTranslation(key)(path, replaceValues), [key, context]); if ((0, utils_exports.isEmptyObject)(context)) return { ...DEFAULT_LANGUAGE, changeLanguage: utils_exports.noop, t: () => "" }; if (key) return { ...context, t: translation }; else return context; } //#endregion export { I18nContext, I18nProvider, LOCALES, getLanguage, useI18n }; //# sourceMappingURL=i18n-provider.js.map