diff options
author | HampusM <hampus@hampusmat.com> | 2024-05-19 18:21:53 +0200 |
---|---|---|
committer | HampusM <hampus@hampusmat.com> | 2024-05-19 21:39:59 +0200 |
commit | 5ce6133e120bd5e3d7490db1872bc8b667a0fb4f (patch) | |
tree | deb418997d515a9762170c0d5f8c8896ecce1210 | |
parent | 2ab8ca293f9548238b22d96d4fd88ec93d6b2431 (diff) |
fix(engine): use ambient light from GlobalLight
-rw-r--r-- | engine/src/lighting.rs | 4 | ||||
-rw-r--r-- | engine/src/material.rs | 22 | ||||
-rw-r--r-- | engine/src/renderer/mod.rs | 39 |
3 files changed, 53 insertions, 12 deletions
diff --git a/engine/src/lighting.rs b/engine/src/lighting.rs index d08276e..f41437a 100644 --- a/engine/src/lighting.rs +++ b/engine/src/lighting.rs @@ -6,7 +6,6 @@ use crate::util::builder; #[derive(Debug, Clone, Component)] pub struct LightSource { - pub ambient: Color<f32>, pub diffuse: Color<f32>, pub specular: Color<f32>, } @@ -16,7 +15,6 @@ impl Default for LightSource fn default() -> Self { Self { - ambient: Color { red: 0.2, green: 0.2, blue: 0.2 }, diffuse: Color { red: 0.5, green: 0.5, blue: 0.5 }, specular: Color { red: 1.0, green: 1.0, blue: 1.0 }, } @@ -30,7 +28,7 @@ builder! { #[non_exhaustive] pub struct GlobalLight { - pub ambient_offset: Color<f32>, + pub ambient: Color<f32>, } } diff --git a/engine/src/material.rs b/engine/src/material.rs index 5e360cd..5c59a9a 100644 --- a/engine/src/material.rs +++ b/engine/src/material.rs @@ -3,6 +3,7 @@ use ecs::Component; use crate::color::Color; use crate::data_types::dimens::Dimens; use crate::texture::{Id as TextureId, Texture}; +use crate::util::builder; #[derive(Debug, Clone, Component)] #[non_exhaustive] @@ -176,6 +177,27 @@ impl Default for Builder } } +builder! { +/// Material flags. +#[builder(name = FlagsBuilder, derives = (Debug, Default, Clone))] +#[derive(Debug, Default, Clone, Component)] +#[non_exhaustive] +pub struct Flags +{ + /// Whether to use material's ambient color instead of the global ambient color. + /// Default is `false` + pub use_ambient_color: bool, +} +} + +impl Flags +{ + pub fn builder() -> FlagsBuilder + { + FlagsBuilder::default() + } +} + fn create_1x1_white_texture() -> Texture { Texture::new_from_color(&Dimens { width: 1, height: 1 }, &Color::WHITE_U8) diff --git a/engine/src/renderer/mod.rs b/engine/src/renderer/mod.rs index 2035a3c..4f9d7e6 100644 --- a/engine/src/renderer/mod.rs +++ b/engine/src/renderer/mod.rs @@ -13,7 +13,7 @@ use crate::color::Color; use crate::data_types::dimens::Dimens; use crate::event::{Present as PresentEvent, Start as StartEvent}; use crate::lighting::{GlobalLight, LightSource}; -use crate::material::Material; +use crate::material::{Flags as MaterialFlags, Material}; use crate::matrix::Matrix; use crate::mesh::Mesh; use crate::opengl::buffer::{Buffer, Usage as BufferUsage}; @@ -91,7 +91,13 @@ fn initialize(window: Single<Window>) } fn render( - query: Query<(Mesh, ShaderProgram, Material, Transform)>, + query: Query<( + Mesh, + ShaderProgram, + Material, + Option<MaterialFlags>, + Transform, + )>, light_source_query: Query<(LightSource, Transform)>, camera_query: Query<(Camera,)>, window: Single<Window>, @@ -125,7 +131,11 @@ fn render( clear_buffers(BufferClearMask::COLOR | BufferClearMask::DEPTH); - for (mesh, shader_program, material, transform) in &query { + for (mesh, shader_program, material, material_flags, transform) in &query { + let material_flags = material_flags + .map(|material_flags| material_flags.clone()) + .unwrap_or_default(); + let shader_program = gl_shader_programs .entry(shader_program.u64_hash()) .or_insert_with(|| create_gl_shader_program(&shader_program).unwrap()); @@ -139,6 +149,7 @@ fn render( apply_light( &material, + &material_flags, &global_light, shader_program, light_source @@ -346,6 +357,7 @@ fn apply_transformation_matrices( fn apply_light( material: &Material, + material_flags: &MaterialFlags, global_light: &GlobalLight, gl_shader_program: &mut GlShaderProgram, light_source: Option<(&LightSource, &Transform)>, @@ -361,11 +373,12 @@ fn apply_light( gl_shader_program.set_uniform_vec_3fv( cstr!("light.ambient"), - &light_source - .map_or(Color::WHITE_F32, |(light_source, _)| { - light_source.ambient.clone() - }) - .into(), + // There cannot be both a material ambient color and a global ambient color + &if material_flags.use_ambient_color { + Color::WHITE_F32.into() + } else { + global_light.ambient.clone().into() + }, ); gl_shader_program.set_uniform_vec_3fv( @@ -388,7 +401,15 @@ fn apply_light( gl_shader_program.set_uniform_vec_3fv( cstr!("material.ambient"), - &(material.ambient.clone() + global_light.ambient_offset.clone()).into(), + // When using the material ambient color is disabled, the ambient color has to be + // white and not black since the material's ambient color is multiplied + // with the global ambient light in the shader + &if material_flags.use_ambient_color { + material.ambient.clone() + } else { + Color::WHITE_F32 + } + .into(), ); gl_shader_program |