Лучшее  🚀
12.03.2021 в 14:13 Evernews

Как дверь в Half-Life 2 сломалась из-за тяжелого охранника и физики

Тот самый случай, когда даже самая муторная отладка ничего не дала.

Кстати, на сайте читать удобнее

Продолжаем мини-сериал о том, какую боль разработчикам игр могут причинять обычные на первый взгляд двери. В первой серии мы вместе с Куртом Маргенау познакомились с дверями из The Last of Us 2, теперь поговорим о Half-Life 2.

«Нахер двери»: руководитель разработки The Last of Us 2 объясняет, почему двери в играх это сложно

Через много лет после релиза игре было решено добавить поддержку гарнитур виртуальной реальности. Проектом занялся программист Том Форсайт; в длинном треде он рассказывает, как старый код не выдержал столкновения с новыми технологиями и нанес разработчику коварный удар.

Когда Half-Life 2 добавляли поддержку VR, нам пришлось поменять код рендера, но трогать игровой код мы, конечно, не решились. Все работало нормально (хотя пришлось много итерировать с кодом, компенсирующим движение транспорта, чтобы игроков не укачивало).

Релиз был совсем рядом и я решил пройти игру целиком — полноценно, а не как раньше, телепортируясь читами к уровням, которые надо протестировать. Действительно, почему бы и нет: я не проходил игру годами, а теперь это можно сделать в замечательном VR.

Сошел с поезда, взял банку, ну и так далее. А потом есть момент, когда охранник приводит вас в комнату, закрывает дверь, снимает маску и оказывается, что это Барни. И вот мы с ним идем по коридору, Барни стучит в дверь, она открывается — и тут же захлопывается обратно. Никто никуда не идет.

Том Форсайт

На всякий случай Том несколько раз перезапустил игру и добрался до этого же момент — дверь не открывалась. Стало ясно, что у разработчиков серьезная проблема: на носу релиз, а VR-версию Half-Life 2 невозможно пройти из-за бага.

Похоже, решили разработчики, во время переделки рендеринга они потрогали что-то не то и сломали одну из геймплейных систем. Чтобы выяснить, в чем дело, было решено откатить все внесенные изменения.

Настало время для бинарного поиска — то есть вы откатываете все изменения, возвращаетесь к версии, когда все работало, а затем постепенно накатываете изменения обратно, пока ошибка снова не появится. Рано или поздно вы найдете код, из-за которого возникла проблема.

Но нет. Даже без нового кода с поддержкой VR баг никуда не делся: он проявлялся на ванильной версии игры. Код во всех файлах в последний раз менялся как минимум год назад. Какого хрена вообще? Похоже, это баг из серии «как оно вообще раньше-то работало».

Дело явно вышло за пределы моей компетенции, так что я позвал на помощь ребят, работавших над оригинальным кодом. Они тоже сильно удивились и начали изучать вопрос. В конце концов выяснилось, что дело в компиляторе.

Код, который я компилировал, был старым, но я использовал новую версию компилятора. Старый компилятор для всех вычислений пользовался набором инструкций 8087, а новый — нет. Сейчас для всей нашей математики, в том числе скалярной, используются инструкции SSE.

Но у 8087 и SSE немного разная точность вычислений. Не знаю, отследили ли мы в итоге место, где сгенерировался разный код — но, так или иначе, какая разница-то? В остальном ведь игра работала нормально.

А дело было вот в чем. Когда охранник толкал дверь и открывал ее, начинала работать физическая модель, распахивавшая дверь. Когда она открывалась до конца, физика отключалась, но во время открытия это был физический, а не заскриптованный объект.

Том Форсайт

Выяснилось, что охранник в комнате стоит недостаточно далеко от двери. Когда дверь открывается, самый краешек его bounding box, упрощенного представления модели для обсчета физики, касается самого краешка двери. То есть дверь, по сути, бьется об охранника.

В версии игры, скомпилированной с помощью набора инструкций 8087, дверь весила столько, что могла на лету отодвинуть охранника, нормально открывшись и закрывшись. Но в версии с SSE математика работала иначе: вес оказался меньше, так что дверь отскакивала от охранника и снова закрывалась.

Двери — отстой. Даже старые, безотказные двери, нормально работавшие десятилетиями. Друзья не бросают друг друга наедине с реализацией дверей.

Том Форсайт

Том уже не помнит, кто в итоге нашел баг, но рад, что его в принципе обнаружили. Одно время, вспоминает разработчик, в Valve даже подумывали перевыпустить Half-Life 2, чтобы точно избавить игру от странного дверного бага.

Читать далее