mirror of
https://github.com/panatgithub/AnkiHeadingSync.git
synced 2026-07-22 06:51:43 +00:00
- 新增完整双语 i18n 支持,支持按 Obsidian 语言自动切换 - 实现结构化 warning / user error 渲染 - Added full bilingual i18n support with automatic switching based on Obsidian language settings - Implemented structured warning and user error rendering
59 lines
No EOL
1.9 KiB
TypeScript
59 lines
No EOL
1.9 KiB
TypeScript
import { resolvePluginLocale, formatList, type PluginLocale } from "./locale";
|
|
import { en } from "./messages/en";
|
|
import { zh } from "./messages/zh";
|
|
|
|
type PrimitiveMessageValue = string | number | boolean | undefined;
|
|
type MessageParamValue = PrimitiveMessageValue | PrimitiveMessageValue[];
|
|
|
|
type NestedTranslationKeys<T> = {
|
|
[K in keyof T & string]: T[K] extends string ? K : `${K}.${NestedTranslationKeys<T[K]>}`
|
|
}[keyof T & string];
|
|
|
|
export type TranslationKey = NestedTranslationKeys<typeof en>;
|
|
export type MessageParams = Record<string, MessageParamValue>;
|
|
|
|
function lookupMessage(dictionary: Record<string, unknown>, key: TranslationKey): string | undefined {
|
|
const segments = key.split(".");
|
|
let current: unknown = dictionary;
|
|
|
|
for (const segment of segments) {
|
|
if (!current || typeof current !== "object" || !(segment in current)) {
|
|
return undefined;
|
|
}
|
|
|
|
current = (current as Record<string, unknown>)[segment];
|
|
}
|
|
|
|
return typeof current === "string" ? current : undefined;
|
|
}
|
|
|
|
function interpolate(template: string, params: MessageParams | undefined, locale: PluginLocale): string {
|
|
if (!params) {
|
|
return template;
|
|
}
|
|
|
|
return template.replace(/\{\{\s*([\w.]+)\s*\}\}/g, (_match, name: string) => {
|
|
const value = params[name];
|
|
if (value === undefined) {
|
|
return "";
|
|
}
|
|
|
|
if (Array.isArray(value)) {
|
|
return formatList(locale, value.filter((entry): entry is PrimitiveMessageValue => entry !== undefined).map((entry) => String(entry)));
|
|
}
|
|
|
|
return String(value);
|
|
});
|
|
}
|
|
|
|
export function t(key: TranslationKey, params?: MessageParams): string {
|
|
const locale = resolvePluginLocale();
|
|
const dictionary = locale === "zh" ? zh : en;
|
|
const template = lookupMessage(dictionary as Record<string, unknown>, key)
|
|
?? lookupMessage(en as Record<string, unknown>, key)
|
|
?? key;
|
|
|
|
return interpolate(template, params, locale);
|
|
}
|
|
|
|
export { formatList, resolvePluginLocale, type PluginLocale }; |