GLSL игнорирует равномерное сравнение bool в фрагментных шейдерах?

Я пытаюсь сравнить равномерный тип bool (type_2d) в GLSL, чтобы вывести один из двух типов сэмплера - sampler2D и samplerCube. Это используется исключительно для различения кубической карты (скайбокс, отражающие данные кубической карты и т. Д.) И sampler2d (альбедо-карты, карты нормалей и т. Д.).

Я попытался сравнить с целым числом, с плавающей точкой, а также с логическим значением, однако кадровый буфер всегда прибегает к черному экрану.

Принимая во внимание, результаты кубической карты работают отлично, если я жестко закодирую значение bool внутри "main", где, например, "type_2d = false" без равномерного присваивания, в отличие от анализа унифицированного значения из C++.

Вот код "GBuffer.f":

#version 420 core

layout(location = 0) out vec3 gPosition;    // Position texel colour
layout(location = 1) out vec3 gNormal;  // Normal texel colour
layout(location = 2) out vec4 gAlbedo;  // Albedo texel colour

in vec3 _texcoord;  
in vec3 _normal;
in vec3 _frag_pos;

uniform bool        type_2d;

uniform sampler2D   albedo;     // Albedo and specular map
uniform samplerCube cubemap;    // Skybox cubemap

vec4 final_colour;

void main()
{

    gPosition = _frag_pos;
    gNormal = normalize(_normal);

    if (type_2d)
    {
        final_colour.rgb = texture(albedo, _texcoord.st).rgb;
        final_colour.a = texture(albedo, _texcoord.st).a;   // Emission
    }
    else
    {
        final_colour.rgb = texture(cubemap, _texcoord).rgb;
        final_colour.a = texture(cubemap, _texcoord).a;
    }

    gAlbedo.rgba = final_colour;
}

Почему сравнения единообразных bool никогда не работают в фрагментном шейдере? Мне даже удалось получить единообразное значение из GLSL, и этап синтаксического анализа, кажется, работает отлично - это почти как если бы GLSL отказывался использовать его для сравнения, и, таким образом, возвращал образец текстуры NULL, создавая эффект черного экрана. Есть идеи?

2 ответа

Решение

В OpenGL один текстурный модуль имеет несколько целей привязки для разных типов текстур, например GL_TEXTURE_1D, GL_TEXTURE_2D, GL_TEXTURE_BUFFER, GL_TEXTURE_CUBE_MAP, Технически, вы можете привязать более одной текстуры к одному юниту.

По умолчанию, GL_TEXTURE0 является активной текстурной единицей, и все формы инициализируются 0, включая образцы сэмплера. Так что, если вы просто glBindTexture() 2D-текстура и карта куба, вы получите именно это.

Однако, хотя привязка нескольких разных типов текстур к одной единице в одно и то же время в GL вполне допустима, вы можете просто выбрать одну конкретную текстурную цель каждой единицы. Спецификация основного профиля OpenGL 4.6, раздел "Образцы 7.11", стр. 155, прямо заявляет:

Не допускается иметь переменные разных типов сэмплера, указывающие на один и тот же текстурный блок изображения в программном объекте. Эта ситуация может быть обнаружена только при следующей команде рендеринга, которая запускает вызовы шейдеров, и INVALID_OPERATION ошибка будет сгенерирована.

Таким образом, даже если вы используете униформу для переключения между обоими путями, в программном объекте технически активны обе формы сэмплера, и, не устанавливая их для выборки из разных текстурных блоков, вы попадаете в запрещенную зону.

По какой-то странной причине мне пришлось установить glActoveTexture(GL_TEXTURE1); и glUniform1i(id, 1); для рендеринга текстуры кубической карты (даже если я не вызываю GL_TEXTURE0 раньше внутри геометрии paas). Я предполагаю, что текстурам кубической карты нужно это дополнительное значение смещения из-за типа сэмплера? Не могу думать ни о какой другой причине.

Другие вопросы по тегам