c++ - OpenGL 延迟渲染不工作

标签 c++ opengl glsl deferred-rendering

我尝试在第一遍中渲染我的几何体,并在第二遍中将其从缓冲区渲染为四边形。
将几何体直接渲染到屏幕上是可行的,但是一旦我尝试通过多次渲染渲染到四边形,屏幕就会保持黑色(清晰颜色为灰色)。
我认为我的着色器可能是问题所在。如果需要,请索取更多代码。

顶点着色器:

#version 440

layout(location = 0) in vec3 vertexPosition;
layout(location = 1) in vec2 vertexUV;
layout(location = 2) in vec3 vertexNormal;

centroid out vec2 UV;
out vec4 position;
out vec3 normal;

uniform mat4 uniMatModel;
uniform mat4 uniMatView;
uniform mat4 uniMatProjection;
uniform mat4 uniMatModelView;
uniform mat4 uniMatModelViewProjection;
uniform mat3 uniMatNormal;

void main()
{
    UV = vertexUV;
    position = uniMatModelView * vec4(vertexPosition, 1.0);
    normal = normalize(uniMatNormal * vertexNormal);
    gl_Position = uniMatModelViewProjection * vec4(vertexPosition, 1.0);
}



片段着色器:

#version 440

centroid in vec2 UV;
in vec4 position;
in vec3 normal;

layout (location = 0) out vec4 fragColor;
layout (location = 1) out vec3 positionData;
layout (location = 2) out vec3 normalData;
layout (location = 3) out vec3 colorData;

subroutine void renderPassType();
subroutine uniform renderPassType renderPass;

uniform sampler2D uniSamTexture;
uniform sampler2D uniSamAlpha;

layout(binding = 0) uniform sampler2D positionTex;
layout(binding = 1) uniform sampler2D normalTex;
layout(binding = 2) uniform sampler2D colorTex;

subroutine (renderPassType)
void renderWorld()
{
    if (texture2D(uniSamAlpha, UV).rgb[0] == 1.0) // Alphamaps have to be inverted!
    {
        discard;
        colorData = vec3(0.0);
    }
    else
    {
        colorData = texture2D(uniSamTexture, UV).rgb;
    }

    positionData = vec3(position.x, position.y, position.z);
    normalData = normal;
}

subroutine (renderPassType)
void renderLight()
{
    fragColor = vec4(texture(colorTex, UV).rgb, 1.0);
}

void main()
{
    renderPass();
}



编辑:

void C0::Cocaine::makeFBO(GLuint &fbo)
{
    GLuint depthBuf;
    Texture
        posTex(this),
        normTex(this),
        colorTex(this)
    ;

    // Create and bind the FBO
    glGenFramebuffers(1, &fbo);
    glBindFramebuffer(GL_FRAMEBUFFER, fbo);

    // The depth buffer
    glGenRenderbuffers(1, &depthBuf);
    glBindRenderbuffer(GL_RENDERBUFFER, depthBuf);
    glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, static_cast<GLsizei>(resolution.x), static_cast<GLsizei>(resolution.y));

    // Create the textures for position, normal and color
    posTex.createGBuf(GL_TEXTURE0, GL_RGB32F, static_cast<int>(resolution.x), static_cast<int>(resolution.y));
    normTex.createGBuf(GL_TEXTURE1, GL_RGB32F, static_cast<int>(resolution.x), static_cast<int>(resolution.y));
    colorTex.createGBuf(GL_TEXTURE2, GL_RGB8, static_cast<int>(resolution.x), static_cast<int>(resolution.y));

    // Attach the textures to the framebuffer
    glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthBuf);
    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, posTex.getTextureID(), 0);
    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, normTex.getTextureID(), 0);
    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT2, GL_TEXTURE_2D, colorTex.getTextureID(), 0);

    GLenum drawBuffers[] = { GL_NONE, GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2 };
    glDrawBuffers(4, drawBuffers);

    glBindFramebuffer(GL_FRAMEBUFFER, 0);
}


void C0::Texture::createGBuf(GLenum texUnit, GLenum format, int width, int height)
{
    this->width = width;
    this->height = height;
    glActiveTexture(texUnit);
    glGenTextures(1, &textureID);
    glBindTexture(GL_TEXTURE_2D, textureID);
    glTexStorage2D(GL_TEXTURE_2D, 1, format, width, height);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
}



编辑:渲染方法:

void C0::Mesh::render()
{
    if (shader != nullptr)
    {
        shader->use();
        shader->setModelMatrix(modelMatrix);
    }

    glBindVertexArray(VAO);

    if (!is2D)
    {
        for (int i = 0x1; i <= 0xB; i++)
        {
            if (texture[i] != nullptr)
            {
                glBindMultiTextureEXT(GL_TEXTURE0 + i, GL_TEXTURE_2D, texture[i]->getTextureID());
            }
        }
    }

    glDrawArrays(GL_TRIANGLES, 0, indexCount);
    glBindVertexArray(0);
}



更多代码:

pass1->setRenderCallback([&]() {

    sp->useSubRoutine(srp1);
    cube->render();

    return true;
});

pass2->setRenderCallback([&]() {

    sp->useSubRoutine(srp2);
    sp->resetMatrices(); // it should be a 2D quad, so I reset the MVP uniforms to 1.0f
    sp->lockMVP(true); // workaround (still playing around with everything)
    dq->render(); // render display quad
    sp->lockMVP(false);

    return true;
});

e->setOnRender([&]() {

    pass1->render();
    pass2->render();

    /* handle input etc... */
});



传递渲染方法:

bool Pass::render()
{
    glBindFramebuffer(GL_FRAMEBUFFER, fbo);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    if (depthTest)
    {
        glEnable(GL_DEPTH_TEST);
    }
    else
    {
        glDisable(GL_DEPTH_TEST);
    }

    if (onRender != nullptr)
    {
        if (!onRender())
        {
            return false;
        }
    }

    if (fbo != 0)
    {
        glFinish();
    }

    return true;
}

最佳答案

使用您使用的着色器版本字符串:

#version 440

配置文件的默认值是 core。来自 GLSL 4.40 规范:

A profile argument can only be used with version 150 or greater. If no profile argument is provided and the version is 150 or greater, the default is core.

您在片段着色器中调用的 texture2D() 函数仅在兼容性配置文件中可用。在核心配置文件中,需要使用重载的texture():

if (texture(uniSamAlpha, UV).rgb[0] == 1.0) // Alphamaps have to be inverted!
...
    colorData = texture(uniSamTexture, UV).rgb;

如果您的着色器有问题,检查编译是否成功总是一个好主意。您可以为此使用以下调用:

glGetShaderiv(shaderId, GL_COMPILE_STATUS, ...);
glGetShaderInfoLog(shaderId, ...);

关于c++ - OpenGL 延迟渲染不工作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27088970/

相关文章:

c++ - opencv 3.0.0 c++ detectMultiScale 检测到大量的人脸

c++ - 一个自动分离 C++ header 和 implementation 的工具

opengl - glBlitFramebuffer 导致访问冲突

opengl - 两个对象之间的 Alpha 混合

opengl - GLSL 中的 Photoshop 投影样式

c++ - QString 关于缓冲区溢出是否安全?

python - pybind11 与 numpy 的矩阵乘积

linux - OpenGL 全屏纹理使帧率降至 12fps

c - OpenGL glAttachShader 不工作

c++ - 将顶点位置从顶点传递到片段着色器 - 仅在使用 Nsight 调试时有效