--- name: fantasia-i18n description: >- Manages vue-i18n messages and locale structure for Fantasia Archive. Use when adding or changing user-facing strings, locale files under repo-root i18n/, or markdown-backed documents wired into i18n. --- # Fantasia Archive — i18n ## Setup - **Plugin**: `vue-i18n` v11 (`package.json` **`^11`**) - **Registry**: **`i18n/index.ts`** at repo root — import **`app/i18n`** - **Types**: schema/augmentation in **`types/vueI18nModuleAugmentation.ts`**; **`src/boot/i18n.ts`** side-effect-imports (may keep **`@ts-expect-error`** for TS2665) — [eslint-typescript.mdc](../../rules/eslint-typescript.mdc) ## Folder structure (`i18n/en-US/`) ``` i18n/ index.ts externalFileLoader.ts specialCharactersFixer.ts _tests/ en-US/ index.ts documents/ — .md via ?raw + specialCharacterFixer components/// dialogs/ floatingWindows/ pages/ globalFunctionality/ ``` No locale files elsewhere. Unmatched → **`globalFunctionality/`**. **Naming**: locale files **`L_` prefix**; types elsewhere use **`T_`**. ## Key naming rules - Top-level keys from **`index.ts`**: camelCase, lowercase first (**`globalWindowButtons`**, **`dialogs`**, …) - Sub-keys in **`L_*.ts`**: same - **`index.ts`**: imports + composed export only — no hardcoded user strings - **`documents`**: processed markdown only; **`specialCharacterFixer`**. Avoid literal **`{...}`** in Markdown — [fantasia-changelog-en-us](../fantasia-changelog-en-us/SKILL.md). No CSS rule blocks with brace delimiters — [fantasia-markdown-dialogs](../fantasia-markdown-dialogs/SKILL.md) - Literal **`|`** in user text: **`\\|`** in TS source (Intlify escape) - App-wide uncategorized: **`globalFunctionality/L_unsortedAppTexts.ts`** ## English (`en-US`) capitalization - **Sentence-style**: running prose, tooltips, changelog sentence refs — [en-us-ui-copy-capitalization.mdc](../../rules/en-us-ui-copy-capitalization.mdc) - **Headline-style**: menu rows, keybind commands, dialog/floating-window titles - **`appControlMenus`** top four **`title`** strings: menu-bar title casing - Other locales: mirror semantic roles, not English caps ## index.ts rules - Imports + export object only - Import order: markdown documents → **`components/`** → **`dialogs/`** → **`floatingWindows/`** → **`globalFunctionality/`** → **`pages/`** ## Using strings in code - **Vue templates**: **`$t('camelCaseKey.subKey')`** - **TS / Pinia**: **`import { i18n } from 'app/i18n/externalFileLoader'`** → **`i18n.global.t(...)`** - No hardcoded user prose in **`.vue`**, **`_data/`**, scripts ## Tests tied to copy changes Key changes affecting **`toHaveText`**, **`aria-label`**, **`L_*`** in Playwright → grep + run matching Vitest/Playwright; rebuild Electron when bundle matters — [fantasia-testing](../fantasia-testing/SKILL.md). ## Adding new strings 1. Pick folder (`components/`, `dialogs/`, `pages/`, `globalFunctionality/`) 2. Create/edit **`L_.ts`** 3. Import in **`index.ts`** → new camelCase top-level key 4. Use full dot-path in **`$t`** / **`i18n.global.t`** 5. Mirror in other locales when maintained ## Storybook integration - Import focused **`L_*`** modules — not **`i18n/en-US/index.ts`** (pulls markdown) - Placeholder **`documents.*`** in **`externalFileLoader.ts`** - **Mandatory**: new **`L_*`** in **`i18n/en-US/index.ts`** used by stories → same PR adds import + key to **`defaultMessages`** ## Related - [en-us-ui-copy-capitalization.mdc](../../rules/en-us-ui-copy-capitalization.mdc) - [fantasia-testing](../fantasia-testing/SKILL.md) - [fantasia-markdown-dialogs](../fantasia-markdown-dialogs/SKILL.md) ## Types Shared types → **`types/`**. See [types-folder.mdc](../../rules/types-folder.mdc).