Итак, вы оптимизировали самые очевидные части своей игры. Однако на самом деле это не так. Вы упустили хитрый, не совсем заметный момент: оптимизацию иерархии сцены Unity.
А что не так с иерархией? Позвольте вам кое-что показать.
Запустите Unity и откройте проект своей игры. Затем запустите игру на целевом устройстве
и подключите к ней Unity Profiler. Запишите несколько кадров во время игрового процесса.
В Unity Profiler поищите следующие неприятные маркеры профайлера:
Не нашли? Продолжайте искать, уверен, найдётся хотя бы один.
Это могут быть UpdateRendererBoundingVolumes, Physics.SyncColliderTransform или TransformChangedDispatch.
Они появятся, когда вы уже будете готовы сдаться. Они возникнут, когда вы уже наведёте курсор мыши на кнопку закрытия Profiler.
Нашли? Если да, то вам повезло. Я тоже нашёл их в одном из своих предыдущих проектов и узнал, как полностью избавиться от них. Я понял, какое зло в них скрыто…
Хотите узнать секреты производительности иерархий сцен Unity?
Разработчик 1 уровня: типичная иерархия сцены Unity
Я всё ещё помню первый проект Unity, над которым работал десять с небольшим лет назад.
Я ещё толком не знал разницы между игровыми объектами (game object) и компонентами (components).
Но это было неважно, я всё равно создавал игры.
Была ли для меня привычна подобная хаотическая иерархия сцены unity? На самом деле да, потому что иногда она была гораздо хуже. Однако любопытно, что чаще всего вполне можно обойтись и таким видом иерархий. Но вы будете страдать. Позже вам придётся за это заплатить.
К счастью, прежде, чем я начал разрабатывать игры профессионально, я научился ценить более структурированные иерархии.
Качественная структура иерархии сцен может стать вашим лучшим другом. Структура сильно упрощает разработку и совместный труд.
Она не обязана быть идеальной, что бы это ни значило. Ей достаточно быть хорошей. Но будьте внимательны. Это важно.
Замусоренная иерархия сцены опасна, она доставит вам проблемы, потому что очень маловероятно, что вы напрямую заметите её побочные эффекты.
Пугающий призрак будет преследовать вас, тормозить вас и тянуть назад. Иногда вы будете оглядываться, но за спиной ничего не будет. Поэтому вы привыкнете двигаться медленно.
За годы работы я научился диагностировать подобные побочные эффекты. Главная проблема заключается в том, что побочные эффекты хаотичной иерархии не так легко отследить.
Вы увидите профайлер, но не будете знать, что значат маркеры. Их названия часто загадочны… какие секреты они хранят? Уверенным быть можно только в одном: загадочные маркеры говорят нам о чём-то, что стоит исследовать.
Когда мы обсуждаем улучшение структуры сцен, то обычно подразумеваем повышение понятности и снижение затрат на поддержку. Но о производительности при этом все забывают.
Давайте проанализируем показанную выше иерархию сцены. Она содержит 2 000 вращающихся сфер, вложенных одна в другую.
Что об этом скажет профайлер? Давайте посмотрим.
Оптимизация иерархии сцены Unity: обзор профайлера иерархии
Очень плохие показатели для простого префаба и скрипта вращения, применённого к обычной сфере. Как видите, огромную часть бюджета времени кадра занимают Physics.SyncColliderTransform и UpdateRendererBoundingVolumes. Но давайте не будем завершать анализ на этом, потому что мне очень любопытен этот случай.
Давайте разбираться глубже.
Подробности профайлера иерархии
Здесь скрывается ответ на вопрос статьи.
Неоптимизированные иерархии вызывают две БОЛЬШИЕ проблемы в Unity.
- Глубокие иерархии не позволяют системе заданий эффективно работать параллельно
- Вложенные иерархии вызывают «бутылочные горлышки» в некоторых подсистемах Unity.
Не забывайте об этом, потому что это относится ко всем типам динамических объектов, и особенно к интерфейсам пользователя.
Для справки: я работаю на Threadripper с 16 физическими ядрами и 32 потоками. Знаете, сколько из них работают эффективно в этом проекте? Только один.
Не нужно говорить, что от этого страдает производительность игры. А если вы попытаетесь исправить ситуацию, разбираясь во всех этих загадочных названиях, то преждевременно состаритесь.
Что бы сделал с 2 000 объектами разработчик 2 уровня?
Разработчик 2 уровня: оптимизированная иерархия сцены Unity
Unity-разработчик 2 уровня знает, что дочерние преобразования имеют свою цену. Также он знает, что ценой в этом случае являются миллисекунды времени ЦП. Или же часы лишней работы, потраченные разработчиком на решение этой проблемы.
Спросите себя: достаточен ли бюджет времени ЦП, чтобы платить за такую обширную иерархию?
У какой области вашей игры вы отбираете эти миллисекунды?
Придётся ли из-за этого снизить количество красивых частиц? Или количество монстров, с которыми должен сражаться игрок? Надеюсь, ничего этого вам делать не придётся, но лучше…
Создавать эффективные иерархии сцен и уничтожать неоптимальные.
Причина, по которой сложная вложенность дочерних объектов крадёт ресурсы игры, проста: каждое изменение transform влияет на дочерние элементы, а возможно, и на родительские с одноуровневыми.
При изменении позиции, поворота или масштаба объекта Unity пересчитывает множество аспектов. Движок занимается этим сам, чтобы вы могли сосредоточиться на игре. Это замечательно, но если не знать об этом, то цена может стать астрономической.
Каково же решение? Не усложняйте и придерживайтесь золотых правил чистой иерархии сцен Unity:
- Не больше 50 дочерних элементов в целом на один game object
- Не более 4 уровней вложенности на любой game object.
Разве это не просто? Разработчик 2 уровня создаёт как можно более плоские иерархии сцен unity.
Посмотрите на изображение ниже. То же количество объектов, но в этот раз структурированное в плоскую иерархию.
Экономия огромна.
Но сказать проще, чем сделать, не так ли? Разделение и уничтожение связей между объектами — это кропотливый, подверженный ошибкам и долгий труд.
Что бы сделал разработчик 3 уровня?
Разработчик 3 уровня: FAP Hierarchy Tool
Хороший Unity-разработчик выполняет свою работу. Отличный Unity-разработчик выполняет работу быстрее и точнее. Но как это ему удаётся? При помощи инструментов. Так как единственная дешёвая иерархия — это пустая иерархия, чтобы оценить игру, вам нужно ответить на следующие вопросы…
Насколько сложны ваши иерархии?
На этот вопрос можно ответить, методично проанализировав иерархии и поставив им числовую оценку.
Какие же математические формулы нужны для вычисления этой оценки? К счастью, никаких. Я всё сделал за вас. Я написал прототип инструмента для автоматического анализа и распознавания «бутылочных горлышек» в вашей иерархии на основании приведённых выше золотых правил.
Я назвал этот инструмент Fabulous Advanced Profiling Hierarchy Tool. Запустите игру. Дойдите до интересного вам момента. Откройте инструмент и позвольте ему сделать всё остальное.
Инструмент сообщит вам целочисленную оценку. Как только вы узнаете оценку, то будете знать, что делать… Или нет?
Потому что я даю вам не только этот инструмент, но и дополнительный скрипт, позволяющий усилить ваши способности по устранению проблем с иерархиями. Я даю вам мощь простого скрипта DetachGameObject.cs.
Редко можно встретить скрипт из 27 строк, позволяющий улучшить производительность за такое короткое время. Его работа проста: во время выполнения программы он перемещает тяжёлые и вложенные игровые объекты в корень иерархии сцены. Благодаря этому вы пользуетесь преимущствами структурированных иерархий во время разработки и получаете потрясающий рост производительности во время выполнения.
Высока вероятность того, что вы можете сделать это для большой части своей иерархии, которая для структурирования имеет сильно вложенность.
Скачать инструмент и скрипт можно в конце оригинала статьи.
Автор: PatientZero