glslshaderfragment-shaderrayraylib

How to check manually created depth buffer for higher point between two fragments


I am really new to shader programming and trying (maybe erroneously) to make a lighting system for a little game I am making. The engine is 2D, so I am trying to pull off a slightly weird trick for lighting. I current construct a depth buffer in a texture each frame for lighting info. I am hoping to create dynamic lighting be using that depth buffer to check between a fragment and a point-light location and decrease the brightness if there is a fragments in-between them with a higher depth value.

I have tried an initial/naive version which assumes just a single light (in the middle of the screen), but I have not been able to figure out what is going wrong (and I haven't yet to uncover a good way to debug these things on MacOS).

Any help/guidance would be much appreciated!

Here is the shader code I have so far:

#version 330 core

// Input vertex attributes (from vertex shader)
in vec2 fragTexCoord;
in vec4 fragColor;

// Input uniform values
uniform sampler2D texture0; // depth texture?
uniform vec4 colDiffuse;

// Output fragment color
out vec4 finalColor;

// NOTE: Add here your custom variables
uniform vec2 resolution;
uniform vec2 light_location;
uniform sampler2D depth_map;

float get_brightness(vec4 color){
    return 0.2126 + color.r + 0.7152 + color.g + 0.0722 + color.b;
}

void main(){
    // Texel color fetching from texture sampler
    vec4 texelColor = texture(texture0, fragTexCoord);
    vec4 shadow_color = texture(depth_map, fragTexCoord);

    float light_max_distance = 0.2;
    float distance_from_light = 0.0;
    float luminance = 1.0;
    int steps = 100;

    bool is_occluded_from_light = false;

    for(int i = 0; i < steps; i++) {
        vec4 sample_step_color = texture(depth_map, mix(fragTexCoord, light_location, i/steps));
        if(get_brightness(shadow_color)< get_brightness(sample_step_color)) {
            texelColor = sample_step_color;
            is_occluded_from_light = true;
            break;
        }
    }

    if(is_occluded_from_light) {
        luminance = 0;
    }

    finalColor = texelColor * luminance;
}

Here is the current result of the shader: enter image description here

And here is the render of the depth buffer: enter image description here

Again, thanks in advance!

I have tried a few different ways of iterating across the vector between them, but I am honestly 1. pretty rusty on my math 2. not totally sure how to check running shaders on MacOS.

The hope is:


Solution

  • It turns out I had a few issues going on. For those curious, the shader ended up being:

    #version 330 core
    
    // Input vertex attributes (from vertex shader)
    in vec2 fragTexCoord;
    in vec4 fragColor;
    
    // Input uniform values
    uniform sampler2D texture0; // depth texture?
    uniform vec4 colDiffuse;
    
    // Output fragment color
    out vec4 finalColor;
    
    // NOTE: Add here your custom variables
    uniform vec2 resolution;
    uniform vec2 light_location;
    uniform sampler2D depth_map;
    
    
    void main(){
        // Texel color fetching from texture sampler
        vec4 texel_color = texture(texture0, fragTexCoord);
        vec4 shadow_color = texture(depth_map, fragTexCoord);
    
        //float light_max_distance = 0.2;
        //float distance_from_light = 0.0;
        float luminance = 1.0;
        int steps = 100;
    
        //bool is_occluded_from_light = false;
        for(int i = 0; i < steps; i++) {
            vec4 sample_step_color = texture(depth_map, mix(fragTexCoord, light_location, float(i)/float(steps)));
            if(shadow_color.r < sample_step_color.r) {
                luminance -= 0.01;
            }
        }
    
    
        finalColor = texel_color * luminance;
    }
    

    which is still not ideal, but far far far more on the path than the previous attempt.