177 lines
6.3 KiB
Python
177 lines
6.3 KiB
Python
import os
|
||
import json
|
||
import traceback
|
||
|
||
def load_json(path):
|
||
"""讀取JSON檔案,順便在控制台顯示加載狀態"""
|
||
if not os.path.exists(path):
|
||
print(f"⚠ 檔案不存在,已略過:{path}")
|
||
return {}
|
||
try:
|
||
with open(path, "r", encoding="utf-8") as f:
|
||
data = json.load(f)
|
||
print(f"✔ 已從 {os.path.basename(path)} 載入 {len(data)} 條翻譯項")
|
||
return data
|
||
except Exception as e:
|
||
print(f"❌ 載入 {path} 時發生錯誤:{str(e)}")
|
||
return {}
|
||
|
||
def parse_key(full_key):
|
||
"""解析包含路徑的鍵值,返回相對路徑、檔案名和行號"""
|
||
try:
|
||
# 範例鍵值:"Room1/dialogue.txt__3"
|
||
path_part, line_part = full_key.rsplit("__", 1)
|
||
line_no = int(line_part)
|
||
*folders, filename = path_part.split("/")
|
||
return os.path.join(*folders), filename, line_no
|
||
except Exception as e:
|
||
print(f"❌ 解析鍵值 '{full_key}' 失敗:{str(e)}")
|
||
return None, None, None
|
||
|
||
def apply_translation(root_path):
|
||
"""從根目錄套用集中式翻譯"""
|
||
print(f"\n🔍 正在處理根目錄:{root_path}")
|
||
|
||
# 集中式翻譯文件路徑
|
||
translate_dir = os.path.join(root_path, "translate")
|
||
trans_files = {
|
||
"normal": os.path.join(translate_dir, "translation_normal.json"),
|
||
"special": os.path.join(translate_dir, "translation_special.json"),
|
||
"namedesc": os.path.join(translate_dir, "translation_namedesc.json")
|
||
}
|
||
|
||
# 載入所有翻譯數據
|
||
translations = {
|
||
"normal": load_json(trans_files["normal"]),
|
||
"special": load_json(trans_files["special"]),
|
||
"namedesc": load_json(trans_files["namedesc"])
|
||
}
|
||
|
||
# 合併普通和特殊翻譯
|
||
combined = {}
|
||
combined.update(translations["normal"])
|
||
combined.update(translations["special"])
|
||
print(f"📦 合併普通+特殊翻譯共 {len(combined)} 條")
|
||
|
||
# 處理名稱描述類翻譯
|
||
namedesc_count = 0
|
||
for full_key, value in translations["namedesc"].items():
|
||
# 解析鍵值中的路徑信息
|
||
rel_path, filename, line_no = parse_key(full_key)
|
||
if not filename:
|
||
continue
|
||
|
||
# 構建完整文件路徑
|
||
src_path = os.path.join(root_path, rel_path, filename)
|
||
if not os.path.exists(src_path):
|
||
print(f"⚠ 找不到來源檔案:{src_path}")
|
||
continue
|
||
|
||
try:
|
||
with open(src_path, "r", encoding="utf-8") as f:
|
||
lines = f.readlines()
|
||
|
||
if line_no >= len(lines):
|
||
print(f"⚠ 行號 {line_no} 在 {filename} 超出範圍(最大 {len(lines)-1})")
|
||
continue
|
||
|
||
# 提取前綴並組合
|
||
original = lines[line_no].strip()
|
||
prefix = next((f for f in ["name:", "desc:", "menuDesc:"] if original.startswith(f)), "")
|
||
if prefix:
|
||
combined[full_key] = prefix + value
|
||
namedesc_count += 1
|
||
else:
|
||
print(f"⚠ 在 {src_path} 第 {line_no} 行找不到前綴:{original[:50]}...")
|
||
except Exception as e:
|
||
print(f"❌ 處理 {src_path} 時發生錯誤:{str(e)}")
|
||
|
||
print(f"📦 新增 {namedesc_count} 條名稱描述翻譯")
|
||
|
||
# 建立檔案修改對照表
|
||
file_map = {}
|
||
total_updates = 0
|
||
|
||
for full_key, value in combined.items():
|
||
rel_path, filename, line_no = parse_key(full_key)
|
||
if not filename:
|
||
continue
|
||
|
||
# 構建完整目標路徑
|
||
target_path = os.path.join(root_path, rel_path, filename)
|
||
if not os.path.exists(target_path):
|
||
print(f"⚠ 找不到目標檔案:{target_path}")
|
||
continue
|
||
|
||
# 初始化文件緩存
|
||
if target_path not in file_map:
|
||
try:
|
||
with open(target_path, "r", encoding="utf-8") as f:
|
||
file_map[target_path] = {
|
||
"lines": f.readlines(),
|
||
"modified": False
|
||
}
|
||
except Exception as e:
|
||
print(f"❌ 讀取 {target_path} 失敗:{str(e)}")
|
||
continue
|
||
|
||
# 檢查行號有效性
|
||
if line_no >= len(file_map[target_path]["lines"]):
|
||
print(f"⚠ 行號 {line_no} 在 {target_path} 超出範圍")
|
||
continue
|
||
|
||
# 準備替換內容
|
||
original = file_map[target_path]["lines"][line_no].strip()
|
||
new_line = f"{value}\n"
|
||
|
||
if file_map[target_path]["lines"][line_no] != new_line:
|
||
file_map[target_path]["lines"][line_no] = new_line
|
||
file_map[target_path]["modified"] = True
|
||
total_updates += 1
|
||
print(f"✏ 更新 {os.path.join(rel_path, filename)} 第 {line_no} 行:")
|
||
print(f" 原始內容:{original[:50]}...")
|
||
print(f" 新內容:{new_line.strip()[:50]}...")
|
||
|
||
# 寫入修改
|
||
success_count = 0
|
||
for file_path, data in file_map.items():
|
||
if data["modified"]:
|
||
try:
|
||
# 建立備份(禁用)
|
||
# backup_path = file_path + ".bak"
|
||
# os.replace(file_path, backup_path)
|
||
|
||
with open(file_path, "w", encoding="utf-8") as f:
|
||
f.writelines(data["lines"])
|
||
|
||
print(f"✔ 成功更新:{os.path.relpath(file_path, root_path)}(備份已建立)")
|
||
success_count += 1
|
||
except Exception as e:
|
||
print(f"❌ 寫入 {file_path} 失敗:{str(e)}")
|
||
traceback.print_exc()
|
||
|
||
print(f"\n🎯 總共套用 {total_updates} 處更新")
|
||
print(f"✅ 成功修改 {success_count}/{len(file_map)} 個檔案")
|
||
|
||
def walk_and_apply(root="."):
|
||
"""主處理流程"""
|
||
root = os.path.abspath(root)
|
||
print(f"🔎 開始從以下路徑進行翻譯作業:{root}")
|
||
|
||
# 檢查翻譯目錄是否存在
|
||
translate_dir = os.path.join(root, "translate")
|
||
if not os.path.exists(translate_dir):
|
||
print(f"❌ 找不到集中式翻譯目錄:{translate_dir}")
|
||
return
|
||
|
||
print(f"\n{'='*50}")
|
||
try:
|
||
apply_translation(root)
|
||
except Exception as e:
|
||
print(f"❌ 發生嚴重錯誤:{str(e)}")
|
||
traceback.print_exc()
|
||
print(f"{'='*50}")
|
||
|
||
if __name__ == "__main__":
|
||
walk_and_apply()
|
||
print("\n🏁 翻譯作業執行完畢!") |