diff options
author | HampusM <hampus@hampusmat.com> | 2024-05-22 20:39:26 +0200 |
---|---|---|
committer | HampusM <hampus@hampusmat.com> | 2024-05-22 20:39:26 +0200 |
commit | d4b61dd34b06119e87c8932ab7718d432dbc6a4f (patch) | |
tree | 2240158176c11eac545a1b50bbe644700b67ab51 /engine | |
parent | 8398025d7927564637e1ea67234665571dc7bcc5 (diff) |
feat(engine): add point light attenuation
Diffstat (limited to 'engine')
-rw-r--r-- | engine/fragment.glsl | 5 | ||||
-rw-r--r-- | engine/light.glsl | 16 | ||||
-rw-r--r-- | engine/src/lighting.rs | 23 | ||||
-rw-r--r-- | engine/src/renderer/mod.rs | 21 |
4 files changed, 63 insertions, 2 deletions
diff --git a/engine/fragment.glsl b/engine/fragment.glsl index 428e87f..a9d192b 100644 --- a/engine/fragment.glsl +++ b/engine/fragment.glsl @@ -30,5 +30,10 @@ void main() in_texture_coords ); + float attenuation = calc_attenuation(light, in_frag_pos); + + diffuse_light *= attenuation; + specular_light *= attenuation; + FragColor = vec4((ambient_light + diffuse_light + specular_light), 1.0); } diff --git a/engine/light.glsl b/engine/light.glsl index 49026ec..04a42f5 100644 --- a/engine/light.glsl +++ b/engine/light.glsl @@ -13,14 +13,17 @@ struct Material { float shininess; }; -struct Light { +struct PointLight { vec3 position; vec3 diffuse; vec3 specular; + float constant; + float linear; + float quadratic; }; uniform Material material; -uniform Light light; +uniform PointLight light; vec3 calc_ambient_light(in vec2 texture_coords) { @@ -56,4 +59,13 @@ vec3 calc_specular_light( ); } +float calc_attenuation(in PointLight point_light, in vec3 position) +{ + float light_distance = length(point_light.position - position); + + return 1.0 / (point_light.constant + point_light.linear + * light_distance + point_light.quadratic + * pow(light_distance, 2)); +} + #endif diff --git a/engine/src/lighting.rs b/engine/src/lighting.rs index bfc2d9b..ffa2645 100644 --- a/engine/src/lighting.rs +++ b/engine/src/lighting.rs @@ -11,6 +11,7 @@ pub struct PointLight { pub diffuse: Color<f32>, pub specular: Color<f32>, + pub attenuation_params: AttenuationParams, } } @@ -29,6 +30,7 @@ impl Default for PointLight Self { diffuse: Color { red: 0.5, green: 0.5, blue: 0.5 }, specular: Color { red: 1.0, green: 1.0, blue: 1.0 }, + attenuation_params: AttenuationParams::default(), } } } @@ -41,6 +43,27 @@ impl Default for PointLightBuilder } } +/// Parameters for light [attenuation](https://en.wikipedia.org/wiki/Attenuation). +#[derive(Debug, Clone)] +pub struct AttenuationParams +{ + pub constant: f32, + pub linear: f32, + pub quadratic: f32, +} + +impl Default for AttenuationParams +{ + fn default() -> Self + { + Self { + constant: 1.0, + linear: 0.0, + quadratic: 0.0, + } + } +} + builder! { /// Global light properties. #[builder(name = GlobalLightBuilder, derives = (Debug, Clone, Default))] diff --git a/engine/src/renderer/mod.rs b/engine/src/renderer/mod.rs index e736165..ad587b5 100644 --- a/engine/src/renderer/mod.rs +++ b/engine/src/renderer/mod.rs @@ -389,6 +389,27 @@ fn apply_light( .into(), ); + gl_shader_program.set_uniform_1fv( + cstr!("light.constant"), + point_light.map_or(1.0, |(light_source, _)| { + light_source.attenuation_params.constant + }), + ); + + gl_shader_program.set_uniform_1fv( + cstr!("light.linear"), + point_light.map_or(0.0, |(light_source, _)| { + light_source.attenuation_params.linear + }), + ); + + gl_shader_program.set_uniform_1fv( + cstr!("light.quadratic"), + point_light.map_or(0.0, |(light_source, _)| { + light_source.attenuation_params.quadratic + }), + ); + gl_shader_program.set_uniform_vec_3fv( cstr!("material.ambient"), &if material_flags.use_ambient_color { |