Як ми робимо World of Warships: автоматизація експорту та верифікація контенту

image

Після прем'єрних закритих показів World of Warships на gamescom і «ИгроМире» офіційний запуск гри все ближче і ближче. Зараз у розпалі закрите альфа-тестування, і нам, розробникам Lesta Studio, пітерського підрозділу Wargaming, ще належить вирішити цілу купу питань. При цьому чимало перешкод все-таки вдалося залишити позаду. Нижче — розповідь про те, як ми адаптували експортер нашого двигуна під потреби «Кораблів» і вибудовували процес верифікації контенту.

Стандартна поставка движка

Будь движок включає в комплект поставки інструментарій для експортера 3D-моделей з 3D-редакторів у свій власний формат даних. Наш Bigworld, на основі якого зроблений і World of Tanks, не є винятком. Він підтримує експорт з 3D-Max і Maya. Практично будь-який ігровий проект вимагає адаптації стандартних експортерів під специфіку проекту. У нашому проекті специфікою є моделі кораблів.

Перша версія адаптованого експортера з Maya просто «дообучила» його розпізнавати більш складну структуру сцени кораблів. До існуючого C++ коду додалося трохи керуючого коду на Python, а також плагін для Maya з UI на wxWidget. Виглядало це приблизно так:

image
UI адаптованого експортера

Отриманий інструмент володів масою недоліків.

Експорт можна було здійснювати тільки з участю користувача, який повинен був «сказати» експортеру, що містить сцена. Про використання даного інструменту в автоматизації різних процесів, наприклад, автоматичної верифікації контенту на етапі складання дистрибутива, не могло бути й мови.

Експортер вимагав від користувача знань про далеко не очевидних параметрах, повільно працював, практично не підтримував верифікацію сцени, а також вимагав величезна кількість ресурсів на підтримку.

Архітектура була основною проблемою для розширення функціональності в майбутньому. Експорт був фактично атомарної операцією (набір спагетті-функцій), яка транслювала дані з однієї структури (завантаженої сцени Maya) в іншу структуру (Bigworld) безпосередньо у фізичні файли. Коли сериализаторы і бізнес-логіка реалізовані «в моноліті», а модель даних просто відсутній, то неможливо додавати обробку даних (pre/post-processing), а також повторно використовувати (code reuse) сериализаторы і модель даних інших інструментах, що реалізують власну бізнес-логіку. Будувати більш складні процеси виробництва контенту було неможливо.

З часом нарощувати нову функціональність в існуючому коді стало практично неможливо. Було прийнято рішення переписати експортер «з нуля», заклавши в нього нову архітектуру.

Суворі будні

Рівень нашого проекту підвищив вимоги до якості, складності та обсягом контенту. За останні кілька років наша студія сильно зросла. У нас з'явилися можливість виділяти достатню кількість ресурсів на завдання, пов'язані з виробництвом контенту. До нас прийшли професіонали, які мають великий бекграунд у розробці архітектури, технологіях на C++/C#. При цьому для розробників експортера це був перший досвід використання Python і Maya API. Це внесло додаткові ризики, які потрібно враховувати.

Рефакторинг експортера ми оцінили у два-три людино-місяця. Без оптимізму в геймдеве ніяк не можна.

До ризиків ми віднесли:

• відсутність формальних вимог
• рівень володіння Python
• складність Maya API
• рефакторинг алгоритмів обробки примітивів

Багато фактичного часу пішло на збір вимог з неформалізованих джерел, таких як розробники, які стали менеджерами, «старожили», торсіонні поля та код існуючого експортера. Ці крихти знань були формалізовані і записані у вигляді вимог, специфікацій та UML-діаграм в Confluence.

Перші прототипи показали необхідність використання концепції namespaces і модулів Python (__init__.py). Також був опрацьований механізм, що дозволяє «прозоро» використовувати функціональність з C++ бібліотек (.pyd).

Про складності і заплутаності Maya API можна написати окрему книгу. Будь-яка функціональність вимагала прототипування, консультацій з 3D-художниками і з розробниками движка (rendering).

У стандартному експортері була власна реалізація великої кількості алгоритмів, наприклад, тріангуляція полігонів, розрахунок матриць трансформацій вкладених вузлів і т.д. Ми відмовилися від них на користь використання Maya API, що сильно підвищило продуктивність експортера.

До законів Мерфі давно пора дописати правило, що будь-який задуманий вами проект обов'язково буде реалізований за час не більш ніж «x3» від запланованого, якщо ви його не кинете.

Результат коштував доданих нами зусиль. Зрештою, навіть наш головний художник, який відповідає за експорт моделей, після пари місяців експлуатації знайшов наш експортер «майже ідеальним».

Заглянемо під капот

У нашій студії активно використовуються скрипти на Python. Ми намагалися реалізувати на ньому і весь експортер. Природно, Python не підходить для обробки великих бінарних даних — таких, як контейнери вершин (vertex buffer), контейнери індексів вершин (index buffer) і т.д. Модель даних і сериализаторы подібних контейнерів були реалізовані на C++ у вигляді бібліотеки (.pyd), яка природним чином «вписалися» в модель даних на Python. Вся бізнес-логіка була реалізована на Python.

Фреймворк експортера планувалося застосовувати не тільки для завдання «ручного» експорту з Maya, але і для будь-яких завдань, де його функціональність можна було б повторно використовувати, наприклад, для автоматизації верифікації контенту. Від будь-якого розробляється інструментарію ми вимагаємо наявність інтерфейсів (API) для Python, командного рядка (command line) і UI інструментів.

Архітектура

Архітектура фреймворку експортера модульна, пошарова. Існують фізичний і логічний шари, а також шар предметної області. Кожен шар містить окремі модулі: модель даних, бізнес-логіка, сериализаторы, а також конвертори, які вміють перетворювати модель даних одного шару в модель даних іншого шару. Фізичний і логічний шари фактично реалізують аналог ORM-архітектури.

Архітектура шару предметної області спроектована для зручної обробки моделі даних бізнес-логікою. Вона повністю ізольована і не містить ніяких припущень про те, яким чином вона буде сериализована у фізична сховище.

image
Пошарова архітектура експортера

Процес експорту

Пошарова архітектура вносить певні особливості процесу експорту. Фактично ми десериализуем дві (або більше) моделей з різних джерел (Maya і BigWorld Engine). Після цього відбувається об'єднання (merge) цих моделей в одну нову. Далі нова модель серіалізуются в BigWorld-Engine-формат.

image
Процес експорту

Гнучкість процесу виробництва контенту

Реалізована архітектура дозволяє досить просто вибудовувати складні процеси виробництва контенту. Наприклад, первинна модель корабля у нас технологічно складається з трьох окремих сцен Maya, кожну з яких одночасно розробляють різні відділи:

• Перша сцена містить візуальну модель (visual model) і модель колізій (collision model).
• Друга сцена містить балістичну модель (ballistic model).
• Третя містить порти ефекти (effects ports).

Додатково до цього інструментарій движка (редактори) додає (редагує) власні дані похідної моделі формату движка (четверта сцена).

Експортер з легкістю вирішує нетривіальну задачу об'єднання всіх чотири сцен в одну комплексну модель корабля.

Верифікація контенту

Система верифікації контенту дозволяє нам шукати помилки вмісту в кожному шарі (джерелі) по-окремо, так і в остаточному контенті. Число верифікаторів зараз досягає декількох десятків. Автоматична перевірка вмісту вбудована в процес складання дистрибутива (build), що дозволяє максимально виключити людський фактор і гарантувати цілісність і технічну чистоту контенту.

image
Приклад верифікації моделі корабля в Maya

Бюджетів контенту та качечка у ванній

Важливою складовою процесу верифікації контенту є перевірка бюджетів, наприклад, верифікація полигонажных бюджетів. На рисунку відображено, зокрема, інформація про кількість трикутників для візуальної моделі по кожному лоду:

image
UI-плагіна Maya

Яскравою ілюстрацією необхідності такої верифікації служить байка, розказана мені колегами про одному з попередніх проектів. На карті було ділянку, забудований не руйнуються будиночками. Як тільки камера звертала свій погляд на цю ділянку, то FPS відразу ж дико падав. Після вивчення проблеми з'ясувалося, що всередині одного з будиночків стояла ванна, в якій плавала маленька «пластикова» качечка. Все це виглядало б кумедною витівкою художників, якби не та обставина, що модель качечки містила близько мільйона полігонів.

На практиці дуже важко дотримуватися бюджетне значення. Безліч моделей об'єктивно є винятками. Завдання бюджетного значення у вигляді діапазону також не вирішує проблему, так як з часом полигонаж моделей просто починає прагнути до верхнього значення діапазону. У нашому випадку, ми плануємо змінювати персональні бюджетів тих моделей, які не відповідають стандартному бюджету даного типу моделей.

Обробка вмісту

На кожному етапі експорту потрібно проводити обробку (pre/post-processing). Наприклад, перед конвертацією логічної моделі даних шару Maya в модель даних предметної області для гармат ППО потрібне попереднє обертання скелета гармати на 45 градусів по осі Y і видалення скелета. Наша архітектура дозволила прозоро вбудовувати різні обробки на будь-якому етапі експорту.

image
image
Приклад моделі до і після pre-processing

Підтримка x64

Досить недавно наші художники в масовому порядку перейшли з 32-бітної Maya 2012 на 64-бітну Maya 2014. Так як експортер майже повністю написаний на Python, у нас практично не виникло проблем з підтримкою x64. Лише бібліотека (.pyd), реалізована на C++, зажадала невеликого «шаманства».

Зараз експортер можна легко використовувати як в x32, так і x64 процесах, оскільки він сам визначає і завантажує потрібну збірку C++ бібліотеки (.pyd)

Верифікація карт

Розробляючи архітектуру експортера, ми не могли передбачити заздалегідь, у яких ще інструментах і автоматизациях вдасться його повторно використовувати. Автоматизація верифікації карт є прикладом того, як «правильна» архітектура експортера знайшла своє застосування в іншому інструменті.

Верифікація карт будує і веріфіцірует граф залежностей карти від інших об'єктів, розташованих на ній. Зокрема, на карті використовуються візуальні моделі ландшафту (камені, айсберги), будівель (будинки, ангари, пристані), техніки (літаки, човни) тощо

Особливість верифікатора карт полягає в тому, що він може верифікувати не просто наявність файлів цих візуальних моделей, але і самі моделі, використовуючи фреймворк експортера. Це дозволило виключити людський фактор, коли відділу розробки карт (LA) доводиться вірити на слово» відділу розробки 3D-моделей (3D-Art), що використовуються технічно коректні моделі.

Збірка дистрибутиву

Фреймворк експортера знайшов своє застосування і в процесі підготовки пакета контенту (content pack) для дистрибутива. У дистрибутив не повинні потрапити моделі, що:

• вже не використовуються;
• знаходяться ще на стадії розробки;
• призначені для наступних версій продукту.

За базовим списку ігрових об'єктів (root objects game) потрібно побудувати граф залежностей, за яким буде сформовано повний список необхідного контенту. Немає нічого простіше, ніж десериализовать модель за допомогою фреймворку експортера і «дізнатися», які ще моделі будуть потрібні (content references).

Підсумки

Історія розробки нашого експортера показала, як з простого вузькоспеціалізованого інструменту він еволюціонував у потужну систему, вирішальну свої безпосередні завдання, а також знайшов застосування в інших процесах виробництва контенту. Основою його успішного розвитку і повторного використання є модульна архітектура, що дозволяє використовувати його окремі «кубики» для побудови інших систем.

В найближчому майбутньому експортеру належить ще одне випробування, пов'язане зі зміною формату файлів Bigworld Engine. Ми впевнені, що закладена архітектура не зазнає ніяких труднощів і зможе підтримувати роботу як з існуючими, так і з новим форматом файлів.

Джерело: Хабрахабр

0 коментарів

Тільки зареєстровані та авторизовані користувачі можуть залишати коментарі.