Chinese main menu: font atlas + GB2312 tables + Strings translation

- build_cjk.py: 2048x1024 UI atlas (original ASCII at 0,0 + full GB2312 at 12px) and
  cjk_glyph/cjk_metric tables.
- cn_strings.py + make_cn_strings.py: escape-aware GB2312 rewrite of Strings.dat (46 entries).
- install_cjk.py: one-shot deploy/restore (exe patch, atlas loose+res, strings).
- apply_cjk.py: fix metrics cave code byte order (was (second<<8)|first) so CJK width
  measures correctly and centred labels are no longer flushed right.
- docs: DEVLOG + patch notes for the atlas and the fix.
This commit is contained in:
DragonHD
2026-09-20 10:22:49 +08:00
parent caf7376019
commit 9eed020634
9 changed files with 671 additions and 15 deletions
+28
View File
@@ -3,6 +3,34 @@
Working log for the *The I of the Dragon* localization / HD project.
Newest entries on top.
## 2026-09-20 — Chinese in the main menu (first playable)
- Built `tools/build_cjk.py`: renders the full GB2312 set (7445 double-byte codes) as **12x12**
glyphs with simsun (crisp/binary, matching the game's pixel font) into a **2048x1024** TGA.
The original 256x128 ASCII artwork is copied to (0,0), so all existing `Fonts.dat` rects keep
working unchanged (verified byte-identical). Also emits `cjk_glyph.bin` / `cjk_metric.bin`.
Advance/height = 12 (the UI font cap height is ~11-12px), drawn 1px up to fit the cell.
- `tools/cn_strings.py` + `tools/make_cn_strings.py`: translate the `English` column of
`Strings.dat` to GB2312 (46 entries; escape-aware so `\"%s\"` formats survive).
- `tools/install_cjk.py`: one-shot deploy/restore (backs up exe/res/strings; rebuilds `Textures.res`
with the new atlas, drops the loose atlas, patches the exe and the strings).
- **Result**: the main menu renders Chinese — 开始新游戏 / 载入游戏 / 选项 / 教程 / 制作人员 / 退出 /
载入上次存档:"…" — confirmed by the user on screen.
### Fixed a byte-order bug in the metrics cave
The draw cave decoded the code as `(first<<8)|second`, but the metrics cave used
`movzx eax,al; mov ah,[ebx+1]` which produced `(second<<8)|first`. Every CJK width measured as 0,
so centred labels (the "Start New Game" button) were flushed right. Fixed to
`movzx eax,al; shl eax,8; mov al,[ebx+1]`. Centring is now correct.
### Notes / next
- The menu button labels *are* dynamic (`Strings.dat`) — the earlier suspicion of baked button
images was wrong; the layer confusion came from the animated particle background.
- Remaining UI text that is baked into textures (credits, tutorial pics) still needs redrawing.
- Next: translate the rest of `Strings.dat`, scripts and `*Description.dat`; then HD textures.
## 2026-09-20 — Double-byte font patch proven
- Reverse-engineered the whole text pipeline (see `patch-notes.md`).
+33 -3
View File
@@ -64,17 +64,47 @@ Behaviour of each cave:
Slot `0xFF` glyph lives at `font+0x100C`, its metric at `font+0x1814`; these do not collide with the
real tables.
## Byte-order detail (important)
Both caves must build the code identically as `(first << 8) | second`:
- draw cave: `movzx ecx,al; shl ecx,8; movzx eax,[edx+1]; or ecx,eax`
- metrics cave: `movzx eax,al; shl eax,8; mov al,[ebx+1]` (`al` is free after the `shl`)
The metrics cave originally used `mov ah,[ebx+1]` which yields `(second<<8)|first`; CJK then
measured as width 0 and centred labels were flushed right. Fixed.
## Font atlas (implemented, `tools/build_cjk.py`)
`AddChar` normalises rects by the **actual D3D texture size**, so replacing the UI font texture
with a larger atlas that still contains the original ASCII art at pixel (0,0) keeps every existing
`Fonts.dat` rect valid — no `Fonts.dat` edits needed.
```
Shrift_gb_Germany.TGA 2048 x 1024, 32bpp TGA (type 2, bottom-up, desc 0x08, 26-byte footer)
(0,0) 256x128 original ASCII/German artwork (byte-identical copy)
(0,128)+ 12x12 cells, 170 per row, full GB2312 (7445 codes), simsun 12px, binary alpha
```
`cjk_glyph` holds normalised UVs `(x/2048, y/1024, (x+12)/2048, (y+12)/1024)`;
`cjk_metric` holds `(12, 12)` (advance, height). Deployed as a loose file and inside
`Textures.res` (see `tools/install_cjk.py`).
## Requirements / limits
- The font texture must contain **both** ASCII and CJK glyphs (one texture per draw).
Plan: replace the UI font `Texture` with a 2048x2048 atlas and re-point the ASCII `Char` rects.
- The font texture must contain **both** ASCII and CJK glyphs (one texture per draw); done via the
shared atlas above.
- Lead bytes >= `0x80` are reserved for DBCS. ASCII is untouched.
- Confirmed end to end: a GB2312-coded menu string rendered the mapped glyph on screen.
- Only the `UI` font atlas is extended; the `OldUI` / `UISmall` / Russian fonts still point at their
own textures, so CJK drawn with those would need their own atlas/tables too.
## Tools
- `tools/add_section.py` — append an executable PE section.
- `tools/apply_cjk.py` — assemble the caves (keystone), add `.cjk`, write hooks and tables.
- `tools/build_cjk.py` — build the atlas TGA + `cjk_glyph`/`cjk_metric` from a charset.
- `tools/make_cn_strings.py` + `tools/cn_strings.py` — GB2312 translation of `Strings.dat`.
- `tools/install_cjk.py` — deploy/restore everything into the game folder.
- `tools/decode_dat.py` — decode/encode the XOR `.dat` files.
- `tools/fontparse.py` — parse `Fonts.dat` into blocks + glyph rects.
- `tools/xrefs.py`, `tools/disasm.py`, `tools/scan_disp.py` — RE helpers.