如何清除绑扎问题?

时间:2018-06-23 11:07:13

标签: c++ opengl

每次模糊时,我都会遇到条带问题,对体积光照进行径向模糊,我明白了。

Radial blur banding 所有的代码似乎都是正确的,我看不出为什么它行不通。立体照明效果很好,但是条纹很烦人。

我已经进行了一些研究,发现抖动可能可以解决此问题,但是为了做到这一点,我在代码中一定有做错的地方。下面是您需要的所有代码。

径向模糊片段着色器

#version 330 core

out vec4 FragColour;
in vec2 _texcoord;

uniform float exposure;
uniform float decay;
uniform float density;
uniform float weight;
uniform vec2 lightPositionOnScreen;
uniform sampler2D lightScatterTexture;
const int NUM_SAMPLES = 128;

void main(void)
{
    vec2 deltaTextCoord = _texcoord - lightPositionOnScreen.xy;
    vec2 textCoo = _texcoord;

    deltaTextCoord *= 1.0 /  float(NUM_SAMPLES) * density;
    float illuminationDecay = 1.0;

    vec2 dir = lightPositionOnScreen - textCoo;
    dir /= NUM_SAMPLES;

    for(int i=0; i < NUM_SAMPLES ; i++)
    {
        textCoo -= deltaTextCoord;

        vec4 sample = texture2D(lightScatterTexture, textCoo );

        sample *= illuminationDecay * weight;

        FragColour += sample;

        textCoo += dir;

        illuminationDecay *= decay;
    }

    FragColour *= exposure;
}

体积光径向模糊

// blur pass
        glBindFramebuffer(GL_FRAMEBUFFER, _light_scatter_blur_fbo); // bind the gbuffer fbo to start the geometry pass
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // glclear the gbuffer before rendering to it

                                                            // bind the radial blur shader
        glUseProgram(blur_program);

        // get the light position in screenspace
        glm::mat4 viewProjectionMatrix = projection * view;
        glm::vec4 lightNDCPosition = viewProjectionMatrix * glm::vec4(2.0f, 10.0f, 20.0f, 1);
        lightNDCPosition /= lightNDCPosition.w;
        glm::vec2 lightScreenPosition = glm::vec2((lightNDCPosition.x + 1) * 0.5, (lightNDCPosition.y + 1) * 0.5);

        // set the uniforms for the light scattering
        glUniform1f(_u_exposure, 0.6050f);
        glUniform1f(_u_decay, 0.9f);
        glUniform1f(_u_density, 0.9f);
        glUniform1f(_u_weight, 5.0f);
        glUniform2f(_u_lightScreenPos, lightScreenPosition.x, lightScreenPosition.y); // TODO: Load this in within the constructer!
                                                                                                                        // bind the light scatter texture to radial blur
        glUniform1i(_u_lightScatterTexture, 0); // TODO: Load this in within the constructer!
        glActiveTexture(GL_TEXTURE0);
        glBindTexture(GL_TEXTURE_2D, _light_scatter_texture);

        // render the quad
        renderQuad();

        glBindFramebuffer(GL_FRAMEBUFFER, 0); // unbind the gbuffer, we dont need it anymore

体积光散射FBO设置

glGenFramebuffers(1, &_light_scatter_fbo);
        glBindFramebuffer(GL_FRAMEBUFFER, _light_scatter_fbo);

        glGenTextures(1, &_light_scatter_texture);
        glBindTexture(GL_TEXTURE_2D, _light_scatter_texture);

        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 1920, 1080, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);

        glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, _light_scatter_texture, NULL);

        if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
            std::cerr << "Error: Unable to create VLS fbo texture!" << std::endl;

        glGenFramebuffers(1, &_light_scatter_blur_fbo);
        glBindFramebuffer(GL_FRAMEBUFFER, _light_scatter_blur_fbo);

        glGenTextures(1, &_light_scatter_blur_texture);
        glBindTexture(GL_TEXTURE_2D, _light_scatter_blur_texture);

        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 1920, 1080, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);

        glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, _light_scatter_blur_texture, NULL);

        if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
            std::cerr << "Error: Unable to create VLS fbo texture!" << std::endl;

        glBindFramebuffer(GL_FRAMEBUFFER, 0);

0 个答案:

没有答案