У меня есть движок 2D игры, который рисует карты тайлов, рисуя плитки из изображения набора тайлов. Поскольку по умолчанию OpenGL может оборачивать только всю текстуру ( GL_REPEAT
), а не только ее часть, каждая плитка разделяется на отдельную текстуру. Затем области одной и той же плитки оказываются смежными друг с другом. Вот как это выглядит, когда работает как задумано:
Однако, как только вы введете дробное масштабирование, появятся швы:
Почему это происходит? Я думал, что это связано с линейной фильтрацией, смешивающей границы квадратов, но это все же происходит с точечной фильтрацией. Единственное решение, которое я нашел до сих пор, состоит в том, чтобы обеспечить позиционирование и масштабирование только при целочисленных значениях и использовать точечную фильтрацию. Это может ухудшить визуальное качество игры (в частности, субпиксельное позиционирование больше не работает, поэтому движение не так плавно).
Вещи, которые я пробовал / рассматривал:
- сглаживание уменьшает, но не полностью устраняет швы
- отключение mipmapping, не имеет никакого эффекта
- Визуализируйте каждую плитку отдельно и вытяните края на 1 пиксель - но это неоптимизация, поскольку она больше не может рендерить области плиток за один раз и создает другие артефакты по краям областей прозрачности
- добавьте границу в 1 пиксель вокруг исходных изображений и повторите последние пиксели - но тогда они перестают быть степенью двойки, вызывая проблемы совместимости с системами без поддержки NPOT
- написание собственного шейдера для обработки мозаичных изображений - но что бы вы сделали по-другому?
GL_REPEAT
Следует захватывать пиксель с противоположной стороны изображения на границах, а не подбирать прозрачность. - геометрия точно смежна, ошибок округления с плавающей запятой нет.
- если фрагментный шейдер жестко запрограммирован для возврата того же цвета, швы исчезают .
- если
GL_CLAMP
вместо текстур заданы текстурыGL_REPEAT
, швы исчезают (хотя рендеринг неправильный). - если текстуры установлены на
GL_MIRRORED_REPEAT
, швы исчезают (хотя рендеринг снова неверный). - если я сделаю фон красным, швы по-прежнему белые. Это говорит о том, что это выборка непрозрачного белого цвета откуда-то, а не прозрачность.
Так что швы появляются только тогда, когда GL_REPEAT
установлено. По какой-то причине только в этом режиме, по краям геометрии есть некоторая утечка / утечка / прозрачность. Как это может быть? Вся текстура непрозрачна.
GL_NEAREST
выборкой в R
направлении координат также работают так же хорошо, как массивные текстуры для большинства вещей в этом сценарии. Mipmapping не будет работать, но, судя по вашему приложению, вам, вероятно, все равно не нужны mipmaps.