diff --git a/src/5.advanced_lighting/9.ssao/ssao.cpp b/src/5.advanced_lighting/9.ssao/ssao.cpp index c8283d0..7834750 100644 --- a/src/5.advanced_lighting/9.ssao/ssao.cpp +++ b/src/5.advanced_lighting/9.ssao/ssao.cpp @@ -22,7 +22,7 @@ #include // Properties -const GLuint SCR_WIDTH = 800, SCR_HEIGHT = 600; +const GLuint SCR_WIDTH = 1280, SCR_HEIGHT = 720; // Function prototypes void key_callback(GLFWwindow* window, int key, int scancode, int action, int mode); @@ -87,12 +87,12 @@ int main() // Set samplers shaderLightingPass.Use(); - glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gPositionDepth"), 0); + glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gPosition"), 0); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gAlbedo"), 2); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "ssao"), 3); shaderSSAO.Use(); - glUniform1i(glGetUniformLocation(shaderSSAO.Program, "gPositionDepth"), 0); + glUniform1i(glGetUniformLocation(shaderSSAO.Program, "gPosition"), 0); glUniform1i(glGetUniformLocation(shaderSSAO.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderSSAO.Program, "texNoise"), 2); @@ -105,22 +105,22 @@ int main() // Set up G-Buffer // 3 textures: - // 1. Positions + depth (RGBA) + // 1. Positions (RGB) // 2. Color (RGB) // 3. Normals (RGB) GLuint gBuffer; glGenFramebuffers(1, &gBuffer); glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); - GLuint gPositionDepth, gNormal, gAlbedo; - // - Position + linear depth color buffer - glGenTextures(1, &gPositionDepth); - glBindTexture(GL_TEXTURE_2D, gPositionDepth); - glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); + GLuint gPosition, gNormal, gAlbedo; + // - Position buffer + glGenTextures(1, &gPosition); + glBindTexture(GL_TEXTURE_2D, gPosition); + glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPositionDepth, 0); + glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPosition, 0); // - Normal color buffer glGenTextures(1, &gNormal); glBindTexture(GL_TEXTURE_2D, gNormal); @@ -221,7 +221,6 @@ int main() glfwPollEvents(); Do_Movement(); - // 1. Geometry Pass: render scene's geometry/color data into gbuffer glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); @@ -239,7 +238,7 @@ int main() // Nanosuit model on the floor model = glm::mat4(); model = glm::translate(model, glm::vec3(0.0f, 0.0f, 5.0)); - model = glm::rotate(model, -90.0f, glm::vec3(1.0, 0.0, 0.0)); + model = glm::rotate(model, glm::radians(-90.0f), glm::vec3(1.0, 0.0, 0.0)); model = glm::scale(model, glm::vec3(0.5f)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); nanosuit.Draw(shaderGeometryPass); @@ -251,7 +250,7 @@ int main() glClear(GL_COLOR_BUFFER_BIT); shaderSSAO.Use(); glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, gPositionDepth); + glBindTexture(GL_TEXTURE_2D, gPosition); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); @@ -278,7 +277,7 @@ int main() glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderLightingPass.Use(); glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, gPositionDepth); + glBindTexture(GL_TEXTURE_2D, gPosition); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); @@ -318,10 +317,10 @@ void RenderQuad() { GLfloat quadVertices[] = { // Positions // Texture Coords - -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, + -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, - 1.0f, 1.0f, 0.0f, 1.0f, 1.0f, - 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, 1.0f, 1.0f, + 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, }; // Setup plane VAO glGenVertexArrays(1, &quadVAO); @@ -349,47 +348,47 @@ void RenderCube() { GLfloat vertices[] = { // Back face - -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // Bottom-left - 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right - 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 0.0f, // bottom-right - 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right - -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left - -0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 1.0f,// top-left + -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // Bottom-left + 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right + 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 0.0f, // bottom-right + 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right + -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left + -0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, 0.0f, 1.0f,// top-left // Front face - -0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left - 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, // bottom-right - 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right - 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right - -0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, // top-left - -0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left + -0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left + 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, // bottom-right + 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right + 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right + -0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, // top-left + -0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left // Left face - -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right - -0.5f, 0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-left - -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left - -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left - -0.5f, -0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-right - -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right + -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right + -0.5f, 0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-left + -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left + -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left + -0.5f, -0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-right + -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right // Right face - 0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left - 0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right - 0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-right - 0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right - 0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left - 0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-left + 0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left + 0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right + 0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-right + 0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right + 0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left + 0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-left // Bottom face - -0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right - 0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 1.0f, // top-left - 0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f,// bottom-left - 0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f, // bottom-left - -0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, // bottom-right - -0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right + -0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right + 0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 1.0f, // top-left + 0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f,// bottom-left + 0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f, // bottom-left + -0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, // bottom-right + -0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right // Top face - -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,// top-left - 0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right - 0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f, // top-right - 0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right - -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,// top-left - -0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f // bottom-left + -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,// top-left + 0.5f, 0.5f , 0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right + 0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f, // top-right + 0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right + -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,// top-left + -0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f // bottom-left }; glGenVertexArrays(1, &cubeVAO); glGenBuffers(1, &cubeVBO); @@ -436,8 +435,6 @@ void Do_Movement() draw_mode = 3; if (keys[GLFW_KEY_4]) draw_mode = 4; - if (keys[GLFW_KEY_5]) - draw_mode = 5; } GLfloat lastX = 400, lastY = 300; diff --git a/src/5.advanced_lighting/9.ssao/ssao.frag b/src/5.advanced_lighting/9.ssao/ssao.frag index 222afdf..a4b3713 100644 --- a/src/5.advanced_lighting/9.ssao/ssao.frag +++ b/src/5.advanced_lighting/9.ssao/ssao.frag @@ -2,7 +2,7 @@ out float FragColor; in vec2 TexCoords; -uniform sampler2D gPositionDepth; +uniform sampler2D gPosition; uniform sampler2D gNormal; uniform sampler2D texNoise; @@ -10,17 +10,18 @@ uniform vec3 samples[64]; // parameters (you'd probably want to use them as uniforms to more easily tweak the effect) int kernelSize = 64; -float radius = 1.0; +float radius = 0.5; +float bias = 0.025; // tile noise texture over screen based on screen dimensions divided by noise size -const vec2 noiseScale = vec2(800.0f/4.0f, 600.0f/4.0f); +const vec2 noiseScale = vec2(1280.0/4.0, 720.0/4.0); uniform mat4 projection; void main() { // Get input for SSAO algorithm - vec3 fragPos = texture(gPositionDepth, TexCoords).xyz; + vec3 fragPos = texture(gPosition, TexCoords).xyz; vec3 normal = texture(gNormal, TexCoords).rgb; vec3 randomVec = texture(texNoise, TexCoords * noiseScale).xyz; // Create TBN change-of-basis matrix: from tangent-space to view-space @@ -42,11 +43,11 @@ void main() offset.xyz = offset.xyz * 0.5 + 0.5; // transform to range 0.0 - 1.0 // get sample depth - float sampleDepth = -texture(gPositionDepth, offset.xy).w; // Get depth value of kernel sample + float sampleDepth = texture(gPosition, offset.xy).z; // Get depth value of kernel sample // range check & accumulate - float rangeCheck = smoothstep(0.0, 1.0, radius / abs(fragPos.z - sampleDepth )); - occlusion += (sampleDepth >= sample.z ? 1.0 : 0.0) * rangeCheck; + float rangeCheck = smoothstep(0.0, 1.0, radius / abs(fragPos.z - sampleDepth)); + occlusion += (sampleDepth >= sample.z + bias ? 1.0 : 0.0) * rangeCheck; } occlusion = 1.0 - (occlusion / kernelSize); diff --git a/src/5.advanced_lighting/9.ssao/ssao_geometry.frag b/src/5.advanced_lighting/9.ssao/ssao_geometry.frag index 381c16b..3213cc4 100644 --- a/src/5.advanced_lighting/9.ssao/ssao_geometry.frag +++ b/src/5.advanced_lighting/9.ssao/ssao_geometry.frag @@ -1,5 +1,5 @@ #version 330 core -layout (location = 0) out vec4 gPositionDepth; +layout (location = 0) out vec3 gPosition; layout (location = 1) out vec3 gNormal; layout (location = 2) out vec4 gAlbedoSpec; @@ -7,20 +7,10 @@ in vec2 TexCoords; in vec3 FragPos; in vec3 Normal; -const float NEAR = 0.1; -const float FAR = 50.0f; -float LinearizeDepth(float depth) -{ - float z = depth * 2.0 - 1.0; // Back to NDC - return (2.0 * NEAR * FAR) / (FAR + NEAR - z * (FAR - NEAR)); -} - void main() { // Store the fragment position vector in the first gbuffer texture - gPositionDepth.xyz = FragPos; - // And store linear depth into gPositionDepth's alpha component - gPositionDepth.a = LinearizeDepth(gl_FragCoord.z); // Divide by far to store depth in range 0.0 - 1.0 + gPosition = FragPos; // Also store the per-fragment normals into the gbuffer gNormal = normalize(Normal); // And the diffuse per-fragment color diff --git a/src/5.advanced_lighting/9.ssao/ssao_lighting.frag b/src/5.advanced_lighting/9.ssao/ssao_lighting.frag index fe97b41..40ba798 100644 --- a/src/5.advanced_lighting/9.ssao/ssao_lighting.frag +++ b/src/5.advanced_lighting/9.ssao/ssao_lighting.frag @@ -2,7 +2,7 @@ out vec4 FragColor; in vec2 TexCoords; -uniform sampler2D gPositionDepth; +uniform sampler2D gPosition; uniform sampler2D gNormal; uniform sampler2D gAlbedo; uniform sampler2D ssao; @@ -21,10 +21,9 @@ uniform int draw_mode; void main() { // Retrieve data from gbuffer - vec3 FragPos = texture(gPositionDepth, TexCoords).rgb; + vec3 FragPos = texture(gPosition, TexCoords).rgb; vec3 Normal = texture(gNormal, TexCoords).rgb; vec3 Diffuse = texture(gAlbedo, TexCoords).rgb; - float Depth = texture(gPositionDepth, TexCoords).a; float AmbientOcclusion = texture(ssao, TexCoords).r; // Then calculate lighting as usual @@ -49,11 +48,9 @@ void main() if(draw_mode == 1) FragColor = vec4(lighting, 1.0); else if(draw_mode == 2) - FragColor = vec4(vec3(Depth / 50.0), 1.0); - else if(draw_mode == 3) FragColor = vec4(FragPos, 1.0); - else if(draw_mode == 4) + else if(draw_mode == 3) FragColor = vec4(Normal, 1.0); - else if(draw_mode == 5) + else if(draw_mode == 4) FragColor = vec4(vec3(AmbientOcclusion), 1.0); }