Pull to refresh

Comments 7

Мощно Вы, конечно, углубились в освещение. Хотелось бы узнать подробнее как Вы делали туман войны. Спасибо.
К тому, что уже написано в статье, могу добавить что подмена шейдера осуществляется с помощью Camera.SetReplacementShader(), результатом рендера камеры является текстура — карта видимости (как на картинке в статье). Далее эта текстура записывается в глобальную переменную шейдеров (см. Shader.SetGlobalTexture()) откуда ей могут пользоваться любые другие шейдеры, в том числе и ImageEffect, рисующий те самые полоски на экране))
Кроме того, что описал мой коллега, могу добавить еще пару пунктов:
1. Все трехмерное окружение находится в 2х слоях. Первый слой (геометрия самого уровня) видят обе камеры, второй слой (пропсы, декали, мелкие 3D объекты) рендерит только основная игровая камера.
Стоит заметить что камера для тумана войны рендерит в 1/4 размера от основной камеры. Тут была сложность, из-за маленького разрешения и заниженных параметров источника света в персонаже, на финальной картинке присутствовал эффект Bias (такие полосы на стенах и поверхности пола.)
2. Мы влезли в работу источника света и заставили его считывать нормали с геометрии и создавать градиент, который смешивается с основными тенями и маскирует артефакты.
На картинке очень хорошо виден этот градиент.
Да уж, немаленькую работу вы проделали. Мне только предстоит окунуться во все эти радости и, учитывая, что опыта в подобных делах у меня практически нет, надеюсь, мне так же удастся всё это победить )
В какой-то момент, Unity напрочь отказывалась объединять одинаковые объекты при рендере, отрисовывая их по одному.

Потому что так работают все лайтпробы — они предназначены только для динамических объектов небольшого размера, на которых батчингом придется пожертвовать. Хочешь батчинг — делай количество вершин в меше <=300 (если без tangent) или <=250 (если с tangent).
Далее идут различные текстурные карты, которые я могу тут же в шейдере домножить на какой-либо цвет или значение.

Оно по определению не может быть быстрым — до сих пор карты-середнячки начинают умирать после 4 фетчей из разных семплеров, те суммарно должно быть максимум 4 разных текстуры, но не 7. Как вариант — упаковывать грейскейлы (если данные позволяют) в RGB каналы одной текстуры и потом пробовать сжимать.
Расскажу об одном из самых из самых гениальных и простых решений которые мы использовали в нашем проекте.
Туман войны реализован через point-light, находящийся в персонаже и рендерящийся отдельной камерой при максимально простом шейдере, который учитывает только освещение. Результатом является буфер видимости персонажа использующийся для пост-процесса тумана войны и в качествемаски в других шейдерах. Например, в зоне видимости охранников.

Это самое гениальное решение? Мы точно говорим про мобильные девайсы? Рендерить сцену еще раз с использованием шадоумап, которые работают не на всем зоопарке андроидов? Погоняйте билды на sgs2, nexus7 tegra3 и тп девайсах, что еще вполне можно встретить в качестве «середнячков» — там теней не будет и игрок получит негативный UX из-за того, что сцена будет показана ему не так, как задумал дизайнер.
Правильная реализация — рендерить видимость в 2 прохода — сначала генерить меш, содержащий вытянутые вертексы от точки обзора и рисовать его с небольшим смещением по высоте с ZWrite On + ColorMask None, а потом тупо рендерить круг геометрии полной видимости со смещением вниз — тогда она будет маскироваться Z-буфером после отрисовки геометрии обстаклов.
Потому что так работают все лайтпробы

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

Оно по определению не может быть быстрым — до сих пор карты-середнячки начинают умирать после 4 фетчей из разных семплеров, те суммарно должно быть максимум 4 разных текстуры, но не 7. Как вариант — упаковывать грейскейлы (если данные позволяют) в RGB каналы одной текстуры и потом пробовать сжимать.


Кажется я именно это и написал.
В процессе компиляции все это многообразие умещается в 4 текстуры.

Даже больше скажу — 4 текстуры это редкость. Куда чаще только 3.

Правильная реализация — рендерить видимость в 2 прохода

Затрудняюсь ответить на твой комментарий достоверно. Но из того что я знаю, это решение было самым первым, что мы реализовали. Негативный опыт. Выглядело хуже, и постоянное дрожание. По производительности все было так же. Одним из тестовых девайсов был Sony Experia L.
вся геометрия уровня статична и не работает с лайтпробами в принципе.

Тогда еще смешнее получается по рендеру — статическая геометрия вообще плохо работает в юнити в плане рендера (можно проверить фрейм дебаггером как оно криво клеит куски при движении / повороте камеры). А еще батчинг рвется при любых активных лайтах — так устроен рендер юнити — даже если лайты не действуют на рендер — они будут сгруппированы по N-одинаковых лайтов.
Выглядело хуже, и постоянное дрожание. По производительности все было так же.

Как оно может дрожать, если это геометрия? Оно будет даже точнее, чем шадоумапы:

Ну и про производительность — несоизмеримо быстрее. Про тестовые девайсы — перечислил примеры, где оно не будет работать.
Sign up to leave a comment.

Articles