Add 小狩猎套装礼包: level-1 +9 set with full attributes, sold in the item mall
Server (tools/server/hunt-set, deployed on 203): game patch adds quest function item.set_attribute (CItem::SetForceAttribute); quest hunt_set turns the unused ITEM_QUEST 50307 into a per-class box of eight +9 pieces with five max-value attributes each. Item mall sells it for 2,000,000. Client locale: name overlay plus whole-row overlays for item_list.txt (gift-box icon) and itemdesc.txt (build_zh_locale.py ROW_FILES). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
20b189a9da
commit
7155785167
@@ -33,6 +33,9 @@ KEYED_FILES = ("locale_game.txt", "locale_interface.txt")
|
||||
IMAGE_DIRS = ("ui/windows",)
|
||||
# skilldesc.txt columns taken from Longju: names, description, conditions (2-8), affect texts (17/20/23).
|
||||
SKILL_COLUMNS = (2, 3, 4, 5, 6, 7, 8, 17, 20, 23)
|
||||
# vnum-keyed 40250 files whose rows an overlay (<stem>_zh_overlay.txt) replaces whole: items the server
|
||||
# gives a new use (tools/server/hunt-set) get a new icon and description.
|
||||
ROW_FILES = ("item_list.txt", "itemdesc.txt")
|
||||
|
||||
|
||||
def keyed_lines(path: Path, encoding: str):
|
||||
@@ -73,6 +76,27 @@ def convert_names(source: Path, destination: Path, overlay: Path = None):
|
||||
return {"converted": converted, "overlaid": len(overlaid), "unrepresentable_vnums": unrepresentable}
|
||||
|
||||
|
||||
def overlay_rows(path: Path, overlay: Path):
|
||||
"""Replace the rows of a vnum-keyed file by the overlay's (UTF-8, whole rows, no header); other rows keep
|
||||
their bytes (the English files are cp1252)."""
|
||||
rows = {}
|
||||
for line in overlay.read_text(encoding="utf-8").splitlines():
|
||||
if line and not line.startswith("#"):
|
||||
rows[line.split("\t", 1)[0]] = line.encode("gbk")
|
||||
lines = path.read_bytes().split(b"\n")
|
||||
replaced = []
|
||||
for index, line in enumerate(lines):
|
||||
key = line.split(b"\t", 1)[0].decode("ascii", "replace")
|
||||
if key in rows:
|
||||
lines[index] = rows[key] + (b"\r" if line.endswith(b"\r") else b"")
|
||||
replaced.append(key)
|
||||
missing = sorted(rows.keys() - set(replaced))
|
||||
if missing:
|
||||
raise ValueError(f"{path.name}: overlay rows {missing} not in the file")
|
||||
path.write_bytes(b"\n".join(lines))
|
||||
return {"replaced_rows": replaced}
|
||||
|
||||
|
||||
def merge_skilldesc(en: Path, zh: Path, destination: Path, overlay: Path = None):
|
||||
"""40250 rows with Longju's text columns; an affect text keeps the English one unless its format
|
||||
arguments match, since the client passes it to _snprintf with the min/max values."""
|
||||
@@ -212,6 +236,11 @@ def build(en: Path, zh: Path, output: Path, client_base: Path,
|
||||
en / "skilldesc.txt", zh / "skilldesc.txt", locale_dir / "skilldesc.txt",
|
||||
names_dir / "skilldesc_zh_overlay.txt" if names_dir else None)
|
||||
|
||||
for filename in ROW_FILES:
|
||||
overlay = names_dir / (Path(filename).stem + "_zh_overlay.txt") if names_dir else None
|
||||
if overlay and overlay.is_file():
|
||||
report["files"][filename] = overlay_rows(locale_dir / filename, overlay)
|
||||
|
||||
for folder in IMAGE_DIRS:
|
||||
english_files = {path.name for path in (en / folder).iterdir()}
|
||||
chinese_files = {path.name for path in (zh / folder).iterdir()}
|
||||
|
||||
@@ -82,6 +82,19 @@ class LocaleBuildTest(unittest.TestCase):
|
||||
self.assertEqual((root / "out.txt").read_bytes().decode("gbk"), "1\t金币\n2\t剑\n")
|
||||
self.assertEqual(result["overlaid"], 1)
|
||||
|
||||
def test_row_overlay_replaces_whole_rows(self):
|
||||
with tempfile.TemporaryDirectory() as directory:
|
||||
root = Path(directory)
|
||||
(root / "itemdesc.txt").write_bytes(b"50306\tBook\tCaf\xe9.\r\n50307\tBook\tEasy.\r\n")
|
||||
(root / "overlay.txt").write_text("# vnum\tname\tdescription\n50307\t礼包\t打开。\n")
|
||||
result = MODULE.overlay_rows(root / "itemdesc.txt", root / "overlay.txt")
|
||||
self.assertEqual((root / "itemdesc.txt").read_bytes(),
|
||||
b"50306\tBook\tCaf\xe9.\r\n" + "50307\t礼包\t打开。\r\n".encode("gbk"))
|
||||
self.assertEqual(result, {"replaced_rows": ["50307"]})
|
||||
(root / "overlay.txt").write_text("99\tx\ty\n")
|
||||
with self.assertRaises(ValueError):
|
||||
MODULE.overlay_rows(root / "itemdesc.txt", root / "overlay.txt")
|
||||
|
||||
def test_skilldesc_keeps_format_arguments(self):
|
||||
with tempfile.TemporaryDirectory() as directory:
|
||||
root = Path(directory)
|
||||
|
||||
Reference in New Issue
Block a user