Results 1 to 8 of 8

Thread: My displacement shader is not working.

  1. #1
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60

    My displacement shader is not working.

    Hi! I would like to re-use the fragments of my previous frame to generate the new one, so I coded a displacement shader.

    But it doesn't work, how can I get view coordinates of gl_FragPos and then transform it to the other frame coordinates ?

    Code :
    const std::string transfFragVertexShader =
                    R"(#version 130
                    out mat4 newViewMatrix;
                    out mat4 projMat;
                    void main() {
                        gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
                        gl_TexCoord[0] = gl_TextureMatrix[0] * gl_MultiTexCoord0;
                        gl_FrontColor = gl_Color;
                        newViewMatrix = gl_ModelViewMatrix;
                        projMat = gl_ProjectionMatrix;
                    })";
                    const std::string transfFragFragmentShader =
                    R"(#version 130
                    uniform mat4 oldViewMatrix;
                    in mat4 newViewMatrix;
                    in mat4 projMat;
                    uniform vec3 resolution;
                    uniform sampler2D oldFrameBuffer;
                    void main() {
                        vec4 oldFragPos = inverse(projMat) * gl_FragCoord;
                        oldFragPos /= oldFragPos.w;
                        oldFragPos = inverse(newViewMatrix) * oldViewMatrix * oldFragPos;
                        oldFragPos /= oldFragPos.w;
                        oldFragPos = oldFragPos * projMat;
                        vec2 position = (resolution.xy / oldFragPos.xy);
                        gl_FragColor = texture2D(oldFrameBuffer, position);
                    })";

  2. #2
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Tried this but not work too.
    Code :
     const std::string transfFragFragmentShader =
                    R"(#version 130
                    uniform mat4 oldViewMatrix;
                    in mat4 newViewMatrix;
                    in mat4 projMat;
                    uniform vec3 resolution;
                    uniform sampler2D oldFrameBuffer;
                    uniform vec4 viewport;
                    void main() {
                        vec4 ndcPos;
                        ndcPos.xy = ((2.0 * gl_FragCoord.xy) - (2.0 * viewport.xy)) / (viewport.zw) - 1;
                        ndcPos.z = (2.0 * gl_FragCoord.z - gl_DepthRange.near - gl_DepthRange.far) /
                            (gl_DepthRange.far - gl_DepthRange.near);
                        ndcPos.w = 1.0;
                        vec4 clipPos = ndcPos / gl_FragCoord.w;
                        vec4 eyePos = inverse(projMat) * clipPos;
                        vec4 worldPos = inverse(newViewMatrix) * eyePos;
                        eyePos = oldViewMatrix * worldPos;
                        clipPos = (eyePos * projMat) / gl_FragCoord.w;
                        ndcPos.xy = ((2.0 * clipPos.xy) - (2.0 * viewport.xy)) / (viewport.zw) - 1;
                        ndcPos.z =  (2.0 * clipPos.z - gl_DepthRange.near - gl_DepthRange.far) /
                            (gl_DepthRange.far - gl_DepthRange.near);
                        vec4 oldFragPos;
                        oldFragPos.x = (ndcPos.x + 1) * viewport.z * 0.5 + viewport.x;
                        oldFragPos.y = (ndcPos.y + 1) * viewport.w * 0.5 + viewport.y;
                        oldFragPos.z = ndcPos.z;
                        oldFragPos.w = 1 / clipPos.w;
                        vec2 position = (resolution.xy / oldFragPos.xy);
                        gl_FragColor = texture2D(oldFrameBuffer, position);
                    })";

    How to pass from view pos to window pos ?

  3. #3
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Dont work too. (Black screen)

    Code :
    const std::string transfFragFragmentShader =
                    R"(#version 130
                    uniform mat4 oldViewMatrix;
                    in mat4 newViewMatrix;
                    in mat4 projMat;
                    uniform vec3 resolution;
                    uniform sampler2D oldFrameBuffer;
                    uniform vec4 viewport;
                    void main() {
                        vec4 ndcPos;
                        ndcPos.xy = ((2.0 * gl_FragCoord.xy) - (2.0 * viewport.xy)) / (viewport.zw) - 1;
                        ndcPos.z = (2.0 * gl_FragCoord.z - gl_DepthRange.near - gl_DepthRange.far) /
                            (gl_DepthRange.far - gl_DepthRange.near);
                        ndcPos.w = 1.0;
                        vec4 clipPos = ndcPos / gl_FragCoord.w;
                        vec4 eyePos = inverse(projMat) * clipPos;
                        vec4 worldPos = inverse(newViewMatrix) * eyePos;
                        eyePos = oldViewMatrix * worldPos;
                        clipPos = eyePos * projMat;
                        clipPos.xyz /= clipPos.w;
                        vec4 oldFragPos;
                        oldFragPos.x = (clipPos.x + 1) * viewport.z * 0.5 + viewport.x;
                        oldFragPos.y = (clipPos.y + 1) * viewport.w * 0.5 + viewport.y;
                        oldFragPos.z = clipPos.z;
                        oldFragPos.w = 1 / clipPos.w;
                        vec2 position = (oldFragPos.xy / resolution.xy);
                        gl_FragColor = texture2D(oldFrameBuffer, position);
                    })";

    I really don't know how to perform this.

  4. #4
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Mmmm It seems the texture is empy, when I clear my framebuffer fbo the previousframe fbo is cleared too!!!

    I think that the opengl context of the previousFrame FBO stay activated so it clears both.

    I'll try to use them in a single opengl context and see if the bug persist.

  5. #5
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Ok the problem is not my shader code but the opengl context created with SFML, when I use only one context for all my FBO, my second component display something at the first draw call. But at the second draw call the texture is empty.
    Code :
    std::cout<<"draw previous frame!"<<std::endl;
                    currentStates.blendMode = sf::BlendNone;
                    currentStates.shader = nullptr;
                    frameBuffer.draw(previousFrameBufferSprite, currentStates);
                    frameBuffer.display();
                    const Texture& text = frameBuffer.getTexture();
                    Image img = text.copyToImage();
                    bool found = false;
                    for (unsigned int x = 0; x < img.getSize().x && !found; x++) {
                        for (unsigned int y = 0; y < img.getSize().y && !found; y++) {
                            if ((int) img.getPixel(x, y).r > 0) {
                                std::cout<<(int) img.getPixel(x, y).r<<std::endl;
                                found = true;
                            }
                        }
                    }
    The texture of the previous frame buffer is not empty but the texture of the framebuffer is empty at the second draw call.

    And for my second component that's doesn't draw me nothing.

    This is really strange, I suspect a bug with opengl context created with SFML.

  6. #6
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Ok I've found why it didn't draw nothing it seems that if I let the depthtest enabled before drawing to the FBO (with a depth attachment) it doesn't work.

    But the shader is not working it didn't get me the fragment of the previous frame with the previous view matrix...

  7. #7
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    Ok I'm forced to activate the depthtest, because I need to have the nearest fragments.
    But for the first draw the depth test never pass, it seems that every values in the depthbuffer are initialized with a very big value and even if I call glClear(GL_DEPTH_BITS), it doesn't draw anything. The values in the depthBuffer should be initialized to 0.

    For the shader, it works fine.

  8. #8
    Member Contributor
    Join Date
    Oct 2015
    Posts
    60
    I had to make this otherwise the depthTest doesn't pass : (I've added a variable secondDraw to redraw everything at the second draw call)

    Code :
    if (viewUpdated || firstDraw || secondDraw) {
                    depthBuffer.clear(sf::Color::Transparent);
                    frontBuffer.clear(sf::Color::Transparent);
                    currentStates.blendMode = BlendNone;
                    for (unsigned int i = 0; i < m_newInstances.size(); i++) {
                         if (m_newInstances[i].getMaterial().getTexture() == nullptr) {
                            depthBufferGenerator.setParameter("haveTexture", 0);
                            simpleShader.setParameter("haveTexture", 0);
                         } else {
                            depthBufferGenerator.setParameter("haveTexture", 1);
                            simpleShader.setParameter("haveTexture", 1);
                         }
                         currentStates.shader=&depthBufferGenerator;
                         currentStates.texture=m_newInstances[i].getMaterial().getTexture();
                         depthBuffer.draw(m_newInstances[i].getAllVertices(),currentStates);
                         currentStates.shader = nullptr;/*&simpleShader;*/
                         frontBuffer.draw(m_newInstances[i].getAllVertices(), currentStates);
                    }
                    frontBuffer.display();
                    frontBufferSprite.setCenter(view.getPosition());
                    //simpleShader.setParameter("haveTexture", 1);
                    currentStates.blendMode = sf::BlendMode(sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::DstAlpha, sf::BlendMode::Add, sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::One, sf::BlendMode::Equation::Add);
                    frameBuffer.draw(frontBufferSprite, currentStates);
                    if (twoLayers) {
                        currentStates.shader=&frameBufferGenerator;
                        currentStates.blendMode=sf::BlendMode(sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::DstAlpha, sf::BlendMode::Equation::Add, sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::One, sf::BlendMode::Equation::Add);
                        for (unsigned int i = 0; i < m_newInstances.size(); i++) {
                            if (m_newInstances[i].getMaterial().getTexture() == nullptr)
                                frameBufferGenerator.setParameter("haveTexture", 0);
                             else
                                frameBufferGenerator.setParameter("haveTexture", 1);
                            currentStates.texture = m_newInstances[i].getMaterial().getTexture();
                            frameBuffer.draw(m_newInstances[i].getAllVertices(), currentStates);
                        }
                    } else {
     
                        /*depthBuffer.bind();
                        glCheck(glBindBuffer(GL_PIXEL_PACK_BUFFER, pboIds[0]));
                        glCheck(glReadBuffer(GL_COLOR_ATTACHMENT0_EXT));
                        glCheck(glReadPixels(0, view.getSize().y - (view.getPosition().y + view.getSize().y), view.getSize().x, view.getSize().y, GL_RGBA, GL_UNSIGNED_BYTE, 0));
                        glCheck(glBindBuffer(GL_PIXEL_PACK_BUFFER, pboIds[1]));
                        GLubyte* src = (GLubyte*) glMapBuffer(GL_PIXEL_PACK_BUFFER, GL_READ_ONLY);
                        unsigned int nbLayers = 0;
                        unsigned int layerValue = 0;
                        if(src) {
                            for (unsigned int i = 0; i < view.getSize().x * view.getSize().y; i++) {
                                if ((unsigned int) (src[i*4+2]) > layerValue) {
                                    nbLayers++;
                                    layerValue = (unsigned int) (src[i*4+2]);
                                }
                            }
                        }
                        glCheck(glUnmapBuffer(GL_PIXEL_PACK_BUFFER));
                        glCheck(glBindBuffer(GL_PIXEL_PACK_BUFFER, 0));*/
                        /*unsigned int nbLayers = 0;
                        unsigned int size = view.getSize().x * view.getSize().y * 4;
                        const sf::Uint8 * data = new unsigned char[size];
                        depthBuffer.display();
                        sf::Image img = depthBuffer.getTexture().copyToImage();
                        data = img.getPixelsPtr();
                        for (unsigned int i = 0; i < size / 4; i++) {
                            if ((float)(data[i*4+2])  > nbLayers) {
                                nbLayers++;
                            }
                            //std:cout<<"depthBufferdata "<<" i : "<<((float)(data[i*4]))<<","<<((float)(data[i*4+1]))<<","<<((float)(data[i*4+2]))<<","<<((float)(data[i*3]))<<std::endl;
                        }*/
                        unsigned int nbLayers = newBatcher.getNbLayers()-1;
                        std::cout<<"nb layers : "<<nbLayers<<std::endl;
                        for (unsigned int i = 0; i < nbLayers; i++) {
                            currentStates.shader = &frameBufferGenerator;
                            currentStates.blendMode = sf::BlendNone;
                            frontBuffer.clear(sf::Color::Transparent);
                            for (unsigned int i = 0; i < m_newInstances.size(); i++) {
                                 if (m_newInstances[i].getMaterial().getTexture() == nullptr) {
                                    frameBufferGenerator.setParameter("haveTexture", 0);
                                 } else {
                                    frameBufferGenerator.setParameter("haveTexture", 1);
                                 }
                                 currentStates.texture=m_newInstances[i].getMaterial().getTexture();
                                 frontBuffer.draw(m_newInstances[i].getAllVertices(), currentStates);
                            }
                            frontBuffer.display();
                            frontBufferSprite.setCenter(view.getPosition());
                            currentStates.shader = &depthPeelingGenerator;
                            currentStates.texture = &depthBuffer.getTexture();
                            depthBuffer.setActive();
                            glCheck(glClear(GL_DEPTH_BUFFER_BIT));
                            for (unsigned int i = 0; i < m_newInstances.size(); i++) {
                                 depthBuffer.draw(m_newInstances[i].getAllVertices(), currentStates);
                            }
                            depthBuffer.display();
                            //Problem, depthTexture is emplty!!!
                            currentStates.shader = nullptr;/*&simpleShader;
                            simpleShader.setParameter("haveTexture", 1);*/
                            currentStates.blendMode = sf::BlendMode(sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::DstAlpha, sf::BlendMode::Add, sf::BlendMode::Factor::OneMinusDstAlpha, sf::BlendMode::Factor::One, sf::BlendMode::Equation::Add);
                            frameBuffer.draw(frontBufferSprite, currentStates);
                        }
                    }
                    /*for (unsigned int j = 0; j < m_newInstances.size(); j++) {
                        m_instances.push_back(m_newInstances[j]);
                    }
                    m_newInstances.clear();
                    newBatcher.clear();*/
                    for (unsigned int i = 0; i < drawables.size(); i++) {
                        frameBuffer.draw(drawables[i].first.get(), drawables[i].second);
                    }
                    frameBuffer.display();
                    previousFrame.clear(backgroundColor);
                    currentStates.blendMode = sf::BlendNone;
                    currentStates.shader = nullptr;
                    frameBufferSprite.setCenter(view.getPosition());
                    previousFrame.draw(frameBufferSprite, currentStates);
                    previousFrame.display();
                    previousFrameBufferSprite.setCenter(view.getPosition());                //std::cout<<"view updated!"<<std::endl;
                    if (!firstDraw)
                        secondDraw = false;
                    firstDraw = false;
                    viewUpdated = false;
                } else {
                    //std::cout<<"draw previous frame!"<<std::endl;
                    currentStates.blendMode = sf::BlendNone;
                    currentStates.shader = nullptr;
                    frameBuffer.draw(previousFrameBufferSprite, currentStates);
                    frameBuffer.display();
                    const Texture& text = frameBuffer.getTexture();
                    Image img = text.copyToImage();
                    bool found = false;
                    for (unsigned int x = 0; x < img.getSize().x && !found; x++) {
                        for (unsigned int y = 0; y < img.getSize().y && !found; y++) {
                            if ((int) img.getPixel(x, y).r > 0) {
                                std::cout<<(int) img.getPixel(x, y).r<<std::endl;
                                found = true;
                            }
                        }
                    }
                }

Similar Threads

  1. VBO & VAO not working without shader
    By pppmaccm in forum OpenGL: Basic Coding
    Replies: 1
    Last Post: 01-15-2019, 09:49 AM
  2. Problem creating a Mesh + Displacement Shader
    By boehmi in forum OpenGL: Basic Coding
    Replies: 2
    Last Post: 01-20-2011, 02:31 AM
  3. Displacement of a particle in vertex shader
    By Englesson in forum OpenGL: GLSL
    Replies: 12
    Last Post: 05-16-2010, 12:44 PM
  4. Displacement shader
    By Dawgmatix in forum OpenGL: GLSL
    Replies: 9
    Last Post: 09-19-2008, 01:46 PM
  5. Texture acces from Vertex Shader for displacement
    By markisbcn in forum OpenGL: GLSL
    Replies: 9
    Last Post: 07-03-2005, 06:03 PM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Proudly hosted by Digital Ocean