PrismatiXEngine
Story and assets

Make a bilingual game

Configure locale files and the Story index, preserve shared identities, and test fonts and layout.

繁體中文

The documentation site's language and the game's locale are separate systems. This chapter makes your game available in Traditional Chinese and English. The CLI's --locale sets a tag; it does not translate dialogue for you.

1. Declare supported locales

Merge these fields into the project while preserving other configuration:

{
  "defaultLocale": "zh-TW",
  "supportedLocales": ["zh-TW", "en"],
  "storyIndex": "Content/story.pxstoryindex"
}

The filename extension is a convention chosen for this tutorial; the referenced document must conform to PrismatiXStoryIndex. If you already have an index, edit it rather than accidentally replacing existing chapters.

For every supported locale, the CLI loads Content/Localization/<locale>.json. Declaring English therefore requires the matching file.

2. Create UI translation documents

A minimal complete Content/Localization/zh-TW.json follows. Preserve additional translations and resources when editing an existing file:

{
  "format": "PrismatiXLocale",
  "schemaRevision": 2,
  "locale": "zh-TW",
  "fontChain": ["Content/Fonts/NotoSansTC-Bold.ttf"],
  "strings": {
    "ui.welcome": "歡迎來到第一道光",
    "ui.start": "開始遊戲",
    "ui.load": "讀取進度"
  },
  "resources": {}
}

Content/Localization/en.json:

{
  "format": "PrismatiXLocale",
  "schemaRevision": 2,
  "locale": "en",
  "fontChain": ["Content/Fonts/NotoSansTC-Bold.ttf"],
  "strings": {
    "ui.welcome": "Welcome to First Light",
    "ui.start": "Start game",
    "ui.load": "Load progress"
  },
  "resources": {}
}

strings maps keys to text; it is not a field for the entire Story script. TSX can use bind={{ text: 'locale.ui.welcome' }}. resources can map localized packaged assets such as translated images. All paths still need real files and must obey the safe-path rules.

3. Map language-specific Story sources

Keep the full Chinese story at Story/main.pxstory and copy it to Story/en/main.pxstory. Translate dialogue, narration, and choice text, preserving labels, command names, aliases, variables, resource references, and explicit IDs.

Corresponding excerpts might be:

; Excerpt from Story/main.pxstory
[id main.question]
@guide
今晚,你想先做什麼?
; Corresponding excerpt from Story/en/main.pxstory
[id main.question]
@guide
What would you like to do this evening?

These are excerpts, not replacements for the complete branching story. Keep choice IDs and goto targets when translating options.

Create Content/story.pxstoryindex:

{
  "format": "PrismatiXStoryIndex",
  "schemaRevision": 2,
  "id": "first-light.story",
  "entryScene": "main",
  "chapters": [
    {"id": "chapter-1", "title": "First Light", "scenes": ["main"]}
  ],
  "scenes": [
    {
      "id": "main",
      "title": "First evening",
      "sources": {
        "zh-TW": "Story/main.pxstory",
        "en": "Story/en/main.pxstory"
      },
      "requiredLabels": ["start"]
    }
  ]
}

This uses the default main scene. If your project already has a custom Story entry, align it with the index's entryScene. Keep chapters and scene lists consistent when expanding the game. An index maps scenes and localized sources; it does not add arbitrary cross-file jump syntax to the author compiler.

4. Why translated text needs stable identity

Switching language during execution requires mapping the current Story location to the corresponding operation in another locale. Equivalent text should retain its source identity, with compatible operation types, document identities, and structure.

Splitting one Chinese line into three English lines, changing dialogue into narration, removing an option, or changing a branch is more than replacing a string. Such changes may invalidate direct mapping and need explicit planning and testing. Keeping an ID string alone does not guarantee live language switching. Prefer one-to-one structure until you need something more complex.

5. Test both language paths

Run prismatix validate my-game. First perform a clean start with defaultLocale set to zh-TW, then another with en, and restore the default you intend to ship. If your UI exposes runtime language switching, test that separately across several scenes rather than only the first line.

Check longer English choices, Chinese punctuation and wrapping, missing glyphs, translated Save/Load and backlog content, and voice timing. A Story locale change does not automatically translate every literal display string in a .pxcharacter; inspect the actual source of visible text.

Create isolated saves in both languages, reopen the packaged Player, and verify locale and Story positioning. When using locale-specific resources, confirm that the distribution includes them.

Sources: Locale schema, Story index schema, CLI loading, Compatibility notes.

On this page