Атласы текстур: одна выборка — один draw call
Однажды я открыл profiler уровня и увидел позор: 180 draw call на коридор, где визуально метров двадцать. Причина была не в геометрии — её съели лоды. Причина была в тридцати отдельных текстурках: дверь, панель, лампа, табличка — каждая со своей картой. Знакомьтесь, атлас текстур — скучное изобретение, которое спасает кадры.
Что такое атлас
Атлас — это одна большая текстура, внутрь которой упакованы все мелкие: островки UV раскладываются плотно, как вещи в чемодан. Движку хватает одного материала и одной выборки, чтобы отрисовать всё, что на эти островки натянуто. Тридцать объектов из моего коридора слились в один draw call — GPU перестал каждый раз переключать состояние конвейера, а это, а не математика шейдеров, стоит дороже всего.
Ценовой вопрос: разрешение против швов
Атлас не бесплатен. Платят двумя валютами.
Разрешение. Площадь атласа конечна. 2048×2048 — это 4 миллиона пикселей на всех. Чем плотнее упаковал, тем меньше пикселей досталось каждому объекту. Герой-модель в атласе наравне с ящиком получит мыло вместо деталей. Отсюда правило: в общий атлас идёт окружение и мелочь, герои и всё, к чему подпустят камеру, — в отдельную карту.
Швы и кровоточивость. Соседние островки лежат вплотную, и при фильтрации выборка может захватить пиксели соседа — на гранях объектов проступают чужие полосы. Лечится паддингом: между островками оставляют 2–4 пикселя буфера, а края растягивают штампом. Ещё бывает микрошов из-за округления UV-координат — спасает смещение островков на полпикселя и запрет на обрезку UV ровно по границе.
Упаковщик (xatlas в Blender, TexturePacker, Riot Atlas) считает раскладку сам, но результат надо проверять глазами: хороший атлас выглядит как плотный парковочный ряд, а не как шахматная доска с дырами.
Virtual texture: атлас, который думает за вас
На крайний случай существует virtual texture — технология, при которой движок сам делит мир на страницы и подгружает в видеопамять только видимые. Crytek придумала это для «Рима», Unreal тащит на себе всю жизнь. Волшебно? Почти: шьётся дорого, кэшируется предательски, и на открытых мирах иногда выплёвывает мыльные текстуры в момент поворота камеры. Для коридора из тридцати дверей virtual texture — пушка по воробьям; обычный атлас решает задачу за вечер.
Практический чек-лист
- Группируйте объекты атласа по расстоянию до камеры: дальний план терпит мелкий паддинг и низкое разрешение.
- Держите texel density единой внутри атласа — иначе половина объектов будет резкой, половина мыльной.
- Не смешивайте в одном атласе сжатие разных типов: normal-картам нужен другой кодек, чем альбеде.
- После упаковки пройдитесь по уровню на 200% зуме — швы видно только там.
Пересоберите свой последний уровень в один атлас 2048. Когда profiler покажет вместо сотни draw call десяток, вы поймёте, что оптимизация — это не магия, а чемодан, собранный с умом.
Комментарии (1)
Атлас 4K на целый город вместо 30 текстур 1K — FPS сказал спасибо. Про швы на пакинге не знал.
Форма для гостей комментариев пока не принимается — писать можно автору (expeot@outlook.com) или через владельца блога. Все записи выше настоящие, никто их не модерирует молча.