Gaming
Игры РФ· DTF· Sungoro

Как я переводил «Якудзу: Мертвецы» на PS3: сеговская клинопись, пистолет с салютами и прятки с котом нагишом

Хотел написать продолжение прошлого поста про «Мертвецов». А потом вспомнил, что у меня на Boosty лежат файлы по Ишину, которые я туда тяп-ляп закинул, что билд 9.5 для пятёрки уже не совсем 9.5, и что редко пишу — значит, надо всё сразу.

Ишин:

начинал с него, прошёл кое-как, на переходах глючило, разбираться стало лень, удалил. Возвращаться не хочу — уже прошёл. Закинул файлы на Boosty и в Телегу. Честно — вообще не помню, что там внутри. Скорее всего, переведены только катсцены, но вдруг кому-то сгодится на растерзание. Сам я к Ишину возвращаться точно не планирую, лень возиться по второму кругу).

Пятёрка:

Я выложил билд 9.5, но честно скажу: после всех откатов и правок он уже не тянет на 9.5. Там что-то испортилось, что-то не применилось, что-то обрезалось. Я игру проверял — один раз целиком, пару раз начало, — но параллельно же менял сборки, так что где-то могли вылезти новые обрезки, а старые не исправиться. Скрины ещё попринимаю, попеределываю, потом удалю игру. Что получится — то получится. После финала правки уже не принимаю, иначе так и буду перепроверять по третьему кругу.

ТЕХНИЧЕСКАЯ ЧАСТЬ (СВОДКА ПО СБОРКАМ)
UID-папки (диалоги, субтитры, сабстори):
uid00: 2 959 файлов, 30 702 перевода
uid01: 1 784 файла, 48 946 переводов
uid02: 203 файла, 70 переводов
uid03: 268 файлов, 1 627 переводов
Итого: 5 214 файлов, 81 345 переводов
In-place: 9 255 | Append: 72 090 | Указателей: 72 095
Ошибок: 0
PAC/STID (меню, катсцены, системные тексты):
262 файла, 33 658 переводов
UTF-8: 23 966 | Latin-1: 9 692
Обрезано: 0 | Размер: 0 байт (хирургический сдвиг)
shop_built (магазины, инвентарь):
178 файлов, 12 776 переводов
Указателей обновлено: 12 104
Append: 12 097 | Обрезано: 0
subtitle_final_build (субтитры):
207 файлов, 4 785 строк
+1 619 строк за счёт разбивки
Ошибок: 0
ARMP (msg, msg_replacer, reactor_name):
3 файла, 6 580 переводов
In-place: 478 | Append: 6 102
Обрезано: 0
Плагин RGG Studio (boot, pause, stay, wdr и прочие .par):
~10 000 переводов
Установлено в игру: bootpar, staypar, pausepar
ОБЩИЙ ИТОГ:
Собрано файлов: ~6 064
Применено переводов: ~149 000
Ошибок сборки: 0

Прям такие числа приличные, хотя на деле, наверное, не всё так страшно по чистым строкам. Тут и не всё ещё учтено — некоторые файлы я давно не обновлял, так что реальная картина скромнее. Но общий масштаб примерно такой.

А теперь к технической дичи из «Мертвецов».

Первым делом я полез в файлы диалогов. Казалось бы: вытащи текст, переведи, собери обратно. Но внутри меня ждал сюрприз.

1. Слэш ценой в 60 000 иен

В диалогах цены отображаются странно: \60,000. Оказалось, в японских шрифтах байт 0x5C (обратный слэш) аппаратно выводит значок иены ¥. Мой самописный фильтр мусора поначалу принимал этот слэш за путь к системным папкам и безжалостно выкидывал нормальные сюжетные фразы. Пришлось учить парсер на лету превращать \60,000 в понятное ¥60,000, а перед сборкой в бинарник возвращать нужный байт обратно.

2. Дроби вместо знаков препинания

Открываю английский текст, а там: A tasty tuna burger with a unique½ sweet flavor. Made¼ to go.Зачем там дроби? Оказалось, программисты Sega для западного релиза использовали подмену в однобайтовой кодировке CP1252:

  • Символ ½ (байт 0xBD) — это обычная запятая ,.
  • Символ ¼ (байт 0xBC) — двойные кавычки ".
  • Символ ¾ (байт 0xBE) — дефис -.
  • Символ ² (байт 0xB2) — латинская буква é (для слов вроде Rosé).

3. Опкоды буфера

В файлах .msg длина реплики зашита намертво. Перед каждой фразой стоят управляющие команды: опкод [02 00 00 14] задаёт лимит символов на экране, а [01 01 00 00] — размер буфера в памяти.

Отдельно про свой редактор. Когда я сел за «Мертвецов», я готовился к тому, что Навигатор Сузуки придётся переписывать почти с нуля — всё-таки движок другой, PS3, зомби. Но, к моему удивлению, основную логику трогать почти не пришлось.

Что осталось как было:

  • In-place — работает без изменений. Если перевод влезает в оригинальный блок, он просто пишется поверх, и всё.
  • Append — тоже почти не зависит от структуры. Если не влезает и есть указатели, строка уходит в конец файла, указатели пересчитываются.
  • Чтение — парсер остался тем же самым «всеядным»: он не разбирает структуру, а ищет всё, что похоже на текст. Именно поэтому он и выжил — там, где специализированные утилиты давились японскими заголовками или двухбайтовой кодировкой, мой парсер просто читал то, что читается.

Что пришлось менять:

  • Ручная отсечка мусора. Парсер-то всеядный, но он тащит в перевод всё подряд: опкоды, технические ID, обрывки путей. Сидеть и вручную чистить это — самая нудная часть работы.
  • Кодировка. Та же беда, что и везде: 1-байтовый капс, потому что строчные буквы на PS3 вешают движок через Shift-JIS и байт 0xFF на букве «я».

Что не проверено:

Честно скажу: в игре я проверил только уличные фразы толпы. Всё остальное, что Навигатор Сузуки собрал, — это пока «должно работать». Скорее всего, оно и работает, но я не проверял.

Главные проблемы — универсальные:

Дроби вместо запятых, ноты вместо символов, зашитая длина строк, опкоды буфера, Big-Endian, капс — всё это одинаково бьёт по любому инструменту. Навигатор Сузуки пострадал от этого меньше, чем «Редактор Дракона», который пришлось переделывать куда серьёзнее.

А вот со Студией Баз Данных RGG — там вообще была отдельная война

1 Исходный тупик: больше 60 колонок японских кракозябр, где даже не найти текст. Плюс двухбайтовая кодировка с пятёрки, наглухо вешавшая игру на PS3.

2 Костыли: пронумеровал поля вслепую — галки заняли пол-экрана. Чужие JS-скрипты превращали буквы в вопросы или удаляло просто при сборке, а из-за сдвига пистолет Акиямы стёрся в ( null ) и получил описание пушки Боба с салютами.

Взял проверенные утилиты, распаковал, перевёл названия, собрал... Игра падает в чёрный экран.

Смотрю вес: оригинальный файл весил 219 КБ, а собранный — 158 КБ. Куда делись 60 килобайт данных?!

Оказалось, заголовки всех колонок базы в Dead Souls оставлены на японском языке (表示名 — Имя, 説明 — Описание). Западные утилиты их не понимали и молча удаляли при сборке.Нашёл японский компилятор (CP932). Он отлично читал заголовки, но давился русскими буквами, превращая весь мой перевод в знаки вопроса ?.

Решил обмануть его тактикой «Троянского коня». Мой скрипт подсовывал японскому компилятору английскую заглушку (например, ~RGG0001xxxxxxxx~), добивая остаток нулями. Компилятор собирал базу, а затем Питон хирургически вскрывал файл и вписывал поверх английских заглушек чистые русские байты. Идея — 10 из 10. Реализация — катастрофа.

Запускаю игру, открываю инвентарь. У Акиямы в руках стартовый уличный пистолет. Смотрю на экран:

  • Имя: ( null )
  • Описание: СТРЕЛЯЕТ ФЕЙЕРВЕРКАМИ С МОЩНЫМ РАЗРЫВОМ. ОРУЖИЕ БОБА.

Базовый пистолет превратился в секретную бонусную пушку торговца Боба!

3 Свой инструмент: написал свой сборщик на Python. Предметы встали строго на свои места, 1-байтовый капс пишется без потерь, а в меню остались только понятные поля («Название», «Описание»).Впереди ещё уйма усушки текста (на скрине как раз видны красные строки с перебором длины, которые в игре вылезут за рамки), но рабочий инструмент наконец-то на руках.

Есть уже и 4 вариант

Слепой транслит убивает атмосферу. Вот пара примеров моей адаптации:(хотя конечно во многих моментах будет хуже)

1. Почему шкала Heat — это «ГНЕВ»

Во-первых, 4 буквы идеально ложатся в память консоли.

Во-вторых, когда брутальный мужик разносит толпу из дробовика, у него внутри ярость, а не «теплота».

Ну и да, это моя небольшая отсылка к фильму Гая Ричи со Стэтхемом — Wrath of Man («Гнев человеческий»). В зомби-сеттинге это легло как родное.

2. Бестиарий зомби-мутантов

Местами вместо дословного копирования спорного американского текста я сопоставил японские исходники с повадками тварей в бою:

  • Diptera (яп. ハエオトコ): У американцев — латинское название мух. У меня — Крылан. Звучит мрачно и по-хорроровски.
  • Aggro (яп. トライバル): В оригинале «Tribal» (племенной). Английское «Аггро» — чисто ММО-сленг. У меня он Дикарь.
  • Monkey Boy (яп. チビザル): «Мальчик-обезьяна» звучит нелепо. Учитывая, что он мелкий, юркий и прыгает на шею — стал Прыгуном.
  • Meathead (яп. デカマッチョ): Классический Громила.

3. Японский ликёр и абрикосы 🥃

В барном меню есть напиток Umeshu on the Rocks. Плод умэ в народе называют японской сливой, а ботаники зовут его японским абрикосом. На вкус он терпко-кислый.

Решил сделать вкусно:

  • В названии: Сливовый ликёр со льдом
  • В описании: Ликёр из плодов умэ, или японского абрикоса. Лёд раскрывает богатый сливовый вкус (Хотя, зная местные лимиты интерфейса, даже это название, скорее всего, придётся ещё урезать).

В «Мертвецах» у каждого из четырёх героев свои хостес и строгий порядок свиданий. Видимо, на случай, если логика сломается и герой попадёт не к той девушке, в игру вшили прямые предупреждения:• «Хина не может быть второй у Акиямы. Сообщите программисту!»• «Саая не появляется у Годы. Сообщите программисту.»• «Нельзя говорить с Мияби за Акияму. Сообщите программисту!»Не знаю, перевели ли это под чистую с оригинальных японских служебных надписей или западные локализаторы уже поверх добавили свои собственные заглушки, но наткнуться на такое в файлах было неожиданно.

У хостес просто много интересных историй.

• Дикобраз:

Юна рассказывает Акияме, что в детстве у неё жил домашний дикобраз. В один прекрасный день питомец просто пропал, а родители ей спокойно заявили, что они его приготовили и съели — потому что растили его на мясо.•

Голышом с котом:

Маджима спрашивает Сааю, чем она мается дома, на что та заявляет: «Вообще-то дома я очень даже дикая и хожу голышом». Маджима начинает пугать её скрытыми камерами на съёмных квартирах, отчего у неё шок: «То есть кто-то мог видеть, как я нагишом играю в прятки с котом Моном?!» Маджима тут же оживляется: «А можно к тебе в гости?», на что Саая его моментально осаживает: «Можно, но при гостях я одеваюсь!»•

Билингвы:

та же Юна признаётся, как на синхронных переводах от волнения путает японские и китайские созвучные слова и несёт чушь на деловых встречах.•

Космический якудза:

Аи Сакура упорно доказывает Годе существование НЛО и предлагает брутальному двухметровому Рюджи парные прозвища «Космический якудза» и «Мяуджи».

С интерфейсом пока успел поковырять только титульник и экраны заставок.

Оригинальные файлы почему-то ядовито-зелёные. Пришлось кустарно прогонять текстуру с русским логотипом через скрипт, чтобы она обесцветилась. Выглядит слегка инородно из-за замазываний, но работает.

А вот со словом «ЗАГРУЗКА» вместо «Now Loading» возиться не стал. Попробовал — движок рвёт буквы по зашитым координатам, угадывать их ради двух секунд экрана мне банально лень.

На этом пока всё. «Мертвецы» ещё никуда не выложены — я только разбираю игру, копаюсь в файлах и перевожу. Пишу в первую очередь для себя, чтобы не забыть, на чём спотыкался. Спасибо, кто дочитал. Если пригодится — уже хорошо.

Открыть оригинал