From 6bcd4802aaf116ec609ecc1fa81a98e50ec02cbb Mon Sep 17 00:00:00 2001 From: Abdelrahman Date: Tue, 3 Dec 2024 21:29:50 +0000 Subject: [PATCH] Define material and light properties --- shaders/frag.glsl | 31 ++++++++++++++++++++++--------- shaders/light_frag.glsl | 4 +++- src/main.cc | 26 +++++++++++++++++++++----- 3 files changed, 46 insertions(+), 15 deletions(-) diff --git a/shaders/frag.glsl b/shaders/frag.glsl index b9a6c9e..3071b9d 100644 --- a/shaders/frag.glsl +++ b/shaders/frag.glsl @@ -1,27 +1,40 @@ #version 330 core +struct Material { + vec3 ambient; + vec3 diffuse; + vec3 specular; + float shininess; +}; + +struct Light { + vec3 position; + vec3 ambient; + vec3 diffuse; + vec3 specular; +}; + in vec3 vert_normal; in vec3 frag_position; out vec4 color; +uniform Material material; +uniform Light light; uniform vec3 camera_position; -uniform vec3 object_color; -uniform vec3 light_color; -uniform vec3 light_position; void main() { float ambient_strength = 0.15; float specular_strength = 0.5; vec3 normal = normalize(vert_normal); - vec3 light_direction = normalize(light_position - frag_position); + vec3 light_direction = normalize(light.position - frag_position); vec3 view_direction = normalize(camera_position - frag_position); vec3 reflect_direction = reflect(-light_direction, normal); float diff = max(dot(normal, light_direction), 0.0); - float spec = pow(max(dot(reflect_direction, view_direction), 0.0), 32); - vec3 ambient = light_color * ambient_strength; - vec3 diffuse = diff * light_color; - vec3 specular = specular_strength * spec * light_color; + float spec = pow(max(dot(reflect_direction, view_direction), 0.0), material.shininess); + vec3 ambient = light.ambient * material.ambient; + vec3 diffuse = light.diffuse * (diff * material.diffuse); + vec3 specular = light.specular * (spec * material.specular); - color = vec4(object_color * (ambient + diffuse + specular), 1.0); + color = vec4(ambient + diffuse + specular, 1.0); }; diff --git a/shaders/light_frag.glsl b/shaders/light_frag.glsl index b460b8c..f0fbad8 100644 --- a/shaders/light_frag.glsl +++ b/shaders/light_frag.glsl @@ -2,6 +2,8 @@ out vec4 color; +uniform vec3 light_diffuse; + void main() { - color = vec4(1.0); + color = vec4(light_diffuse, 1.0); } diff --git a/src/main.cc b/src/main.cc index 0d29f13..4b4e61a 100644 --- a/src/main.cc +++ b/src/main.cc @@ -32,6 +32,10 @@ #define WINDOW_HALF_WIDTH 640 #define WINDOW_HALF_HEIGHT 360 +#define min(a, b) (a < b ? a : b) +#define max(a, b) (a > b ? a : b) +#define clamp(v, a, b) (min(max(v, a), b)) + enum exit_codes : int { EXIT_CODE_SUCCESS, EXIT_CODE_SDL_INIT_FAILED, @@ -168,14 +172,12 @@ int main() { Shader main_shader {"shaders/vert.glsl", "shaders/frag.glsl"}; Shader light_shader {"shaders/vert.glsl", "shaders/light_frag.glsl"}; - main_shader.set_vec3("object_color", glm::vec3(1.0f, 0.5f, 0.31f)); - main_shader.set_vec3("light_color", glm::vec3(1.0f, 1.0f, 1.0f)); - const float camera_speed = 25.0f; glm::vec3 camera_position = glm::vec3(-2.0f, 0.0f, 6.0f); glm::vec3 camera_forward = glm::vec3(0.0f); glm::vec3 world_up = glm::vec3(0.0f, 1.0f, 0.0f); glm::vec3 light_position = glm::vec3(1.0f, 0.5f, 0.0f); + glm::vec3 light_diffuse = glm::vec3(0.5f, 0.5f, 0.5f); float yaw = -70.0f; float pitch = 0.0f; @@ -185,7 +187,14 @@ int main() { glm::mat4 projection = glm::perspective(glm::radians(45.0f), (float)WINDOW_WIDTH / (float)WINDOW_HEIGHT, 0.1f, 100.0f); glm::mat3 normal_mat = glm::mat3(1.0f); - main_shader.set_mat4("projection", projection); + main_shader.set_mat4 ("projection", projection); + main_shader.set_vec3 ("material.ambient", glm::vec3(1.0f, 0.5f, 0.31f)); + main_shader.set_vec3 ("material.diffuse", glm::vec3(1.0f, 0.5f, 0.31f)); + main_shader.set_vec3 ("material.specular", glm::vec3(0.5f, 0.5f, 0.5f)); + main_shader.set_float("material.shininess", 32.0f); + main_shader.set_vec3 ("light.ambient", glm::vec3(0.2f, 0.2f, 0.2f)); + main_shader.set_vec3 ("light.diffuse", light_diffuse); + main_shader.set_vec3 ("light.specular", glm::vec3(1.0f, 1.0f, 1.0f)); light_shader.set_mat4("projection", projection); const float light_radius = 3.0f; @@ -202,6 +211,11 @@ int main() { float seconds = ticks * 0.001f; delta = (ticks - last_frame) * 0.001f; light_position = glm::vec3(sin(seconds) * light_radius, light_position.y, cos(seconds) * light_radius); + light_diffuse = glm::vec3( + clamp(sin(seconds * 3.0f) + 1.0f, 0.0f, 1.0f), + clamp(cos(seconds * 8.0f) + 1.0f, 0.0f, 1.0f), + clamp(tan(seconds * 5.0f) + 3.0f, 0.0f, 1.0f) + ); last_frame = ticks; while (SDL_PollEvent(&event)) { @@ -275,7 +289,8 @@ int main() { model = glm::translate(glm::mat4(1.0f), glm::vec3(0.0f, 0.0f, 0.0f)); normal_mat = glm::transpose(glm::inverse(model)); main_shader.activate(); - main_shader.set_vec3("light_position", light_position); + main_shader.set_vec3("light.position", light_position); + main_shader.set_vec3("light.diffuse", light_diffuse); main_shader.set_mat4("model", model); main_shader.set_mat3("normal_mat", normal_mat); glBindVertexArray(vao); @@ -285,6 +300,7 @@ int main() { model = glm::scale(model, glm::vec3(0.2f)); light_shader.activate(); light_shader.set_mat4("model", model); + light_shader.set_vec3("light_diffuse", light_diffuse); glBindVertexArray(light_vao); glDrawElements(GL_TRIANGLES, indices.size(), GL_UNSIGNED_INT, (void *)0);