片段着色器在组合 GL_TEXTURE_BUFFER 和 GL_TEXTURE_1D 后似乎失败

Fragment Shader seems to fail after combining GL_TEXTURE_BUFFER and GL_TEXTURE_1D

目前,我正在尝试实现一个片段着色器,它通过结合粒子内流体相的百分比来混合不同流体粒子的颜色。因此,例如,如果流体 1 拥有 15% 的粒子而流体 2 拥有 85%,则生成的颜色应反映该比例。因此,我有一个缓冲区纹理,其中包含反映为每个粒子和每个阶段 [0,1] 中浮点值的百分比,以及一个包含流体颜色的纹理。

缓冲区纹理当前包含后续列表中每个粒子的百分比。例如:

|粒子 1 百分比 1 |粒子 1 百分比 2 |粒子 2 百分比 1 |粒子 2 百分比 2 | ...

我已经通过将纹理直接分配给粒子或将 volFrac 分配给最终颜色的红色部分来测试纹理的正确性。我还尝试了不同的 GLSL 调试器来分析问题,但 none 的流行选项在尝试后确实在我的机器上工作。

#version 330

uniform float radius;
uniform mat4 projection_matrix;

uniform uint nFluids;

uniform sampler1D colorSampler;
uniform samplerBuffer volumeFractionSampler;

in block
{
    flat vec3 mv_pos;
    flat float pIndex;
}
In;

out vec4 out_color;

void main(void)
{
    vec3 fluidColor = vec3(0.0, 0.0, 0.0);

    for (int fluidModelIndex = 0; fluidModelIndex < int(nFluids); fluidModelIndex++)
    {
        float volFrac = texelFetch(volumeFractionSampler, int(nFluids * In.pIndex) + fluidModelIndex).x;

        vec3 phaseColor = texture(colorSampler, float(fluidModelIndex)/(int(nFluids) - 1)).xyz;

        fluidColor = volFrac * phaseColor;
    }

    out_color = vec4(fluidColor, 1.0);
}

还有一小段纹理初始化

    //Texture Initialisation and Manipulation here
    glActiveTexture(GL_TEXTURE0);
    glBindTexture(GL_TEXTURE_1D, m_textureMap);

    glTexImage1D(GL_TEXTURE_1D, 0, GL_RGB, nFluids, 0, GL_RGB, GL_FLOAT, color_map);

    //Creation and Initialisation for Buffer Texture containing the volume Fractions
    glBindBuffer(GL_TEXTURE_BUFFER, m_texBuffer);
    glBufferData(GL_TEXTURE_BUFFER, nFluids * nParticles * sizeof(float), m_volumeFractions.data(), GL_STATIC_DRAW);
    glBindBuffer(GL_TEXTURE_BUFFER, 0);

    glBindTexture(GL_TEXTURE_BUFFER, m_bufferTexture);
    glTexBuffer(GL_TEXTURE_BUFFER, GL_R32F, m_texBuffer);

现在的问题是,如果我将缓冲区纹理的信息与纹理的信息相乘,应该渲染的粒子完全消失,没有任何警告或其他错误消息。因此,如果我使用以下语句,粒子就会消失:

fluidColor = volFrac * phaseColor;

有谁知道,为什么会这样,或者我该如何进一步调试这个问题?

Does anybody know, why this is the case

是的。您似乎对 colorSamplervolumeFractionSampler 使用了相同的纹理单元,这在规范中是不允许的。引用 OpenGL 4.6 core profile spec 的第 7.11 节:

It is not allowed to have variables of different sampler types pointing to the same texture image unit within a program object. This situation can only be detected at the next rendering command issued which triggers shader invocations, and an INVALID_OPERATION error will then be generated.

因此,虽然您可以绑定不同的纹理同时执行纹理单元 0 的不同目标,但每个绘制调用只能使用每个纹理单元的一个特定目标。如果您只使用一个采样器或另一个采样器(如果它们不影响着色器的输出,着色器编译器将积极优化它们),您处于合法用例中,但一旦您同时使用两者,它就会不工作。