#version 330 core #ifndef LIGHT_GLSL #define LIGHT_GLSL #preinclude "vertex_data.glsl" struct Material { vec3 ambient; vec3 diffuse; vec3 specular; sampler2D ambient_map; sampler2D diffuse_map; sampler2D specular_map; float shininess; }; struct LightPhong { vec3 diffuse; vec3 specular; }; struct AttenuationProperties { float constant; float linear; float quadratic; }; struct PointLight { LightPhong phong; vec3 position; AttenuationProperties attenuation_props; }; vec3 calc_ambient_light(in Material material, in vec2 texture_coords) { return vec3(texture(material.ambient_map, texture_coords)) * material.ambient; } vec3 calc_diffuse_light( in Material material, in LightPhong light_phong, in vec3 light_dir, in vec3 norm, in vec2 texture_coords ) { float diff = max(dot(norm, light_dir), 0.0); return light_phong.diffuse * ( diff * (vec3(texture(material.diffuse_map, texture_coords)) * material.diffuse) ); } vec3 calc_specular_light( in Material material, in LightPhong light_phong, in vec3 light_dir, in vec3 norm, in vec3 view_pos, in vec3 frag_pos, in vec2 texture_coords ) { vec3 view_direction = normalize(view_pos - frag_pos); vec3 reflect_direction = reflect(-light_dir, norm); float spec = pow(max(dot(view_direction, reflect_direction), 0.0), material.shininess); return light_phong.specular * ( spec * (vec3(texture(material.specular_map, texture_coords)) * material.specular) ); } float calc_attenuation(in PointLight point_light, in vec3 position) { float light_distance = length(point_light.position - position); return 1.0 / (point_light.attenuation_props.constant + point_light.attenuation_props.linear * light_distance + point_light.attenuation_props.quadratic * pow(light_distance, 2)); } vec3 calc_point_light( in PointLight light, in VertexData vertex_data, in vec3 view_pos, in Material material ) { vec3 light_direction = normalize(light.position - vertex_data.world_space_pos); vec3 norm = normalize(vertex_data.world_space_normal); vec3 diffuse_light = calc_diffuse_light( material, light.phong, light_direction, norm, vertex_data.texture_coords ); vec3 specular_light = calc_specular_light( material, light.phong, light_direction, norm, view_pos, vertex_data.world_space_pos, vertex_data.texture_coords ); float attenuation = calc_attenuation(light, vertex_data.world_space_pos); diffuse_light *= attenuation; specular_light *= attenuation; return diffuse_light + specular_light; } #endif