-
Notifications
You must be signed in to change notification settings - Fork 0
/
phong.frag
99 lines (81 loc) · 2.88 KB
/
phong.frag
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
#version 330 core
in vec4 light_pos;
in vec4 world_position;
in vec4 world_normal;
in vec2 frag_uv;
out vec4 final_color;
struct PointLight
{
vec3 intensity;
vec3 position;
};
struct DirectionalLight
{
vec3 intensity;
vec3 direction;
};
struct Material
{
vec3 ambient;
vec3 diffuse;
vec3 specular;
float phong_exponent;
};
uniform Material material;
uniform vec3 ambient_light;
uniform PointLight point_light[8];
uniform int number_of_point_lights;
uniform DirectionalLight directional_light;
uniform vec3 camera_position;
uniform sampler2D tex;
uniform sampler2D shadowTex;
vec3 get_diffuse()
{
#ifdef HAS_UV
return texture(tex, frag_uv).rgb;
#endif
return material.diffuse;
}
float visible(PointLight l)
{
float bias = max(0.05 * (1.0 - dot(vec3(world_normal), normalize(l.position - vec3(world_position)))), 0.005);
vec3 projCoords = light_pos.xyz / light_pos.w;
projCoords = projCoords * 0.5 + 0.5;
float closestDepth = texture(shadowTex, projCoords.xy).r;
float currentDepth = projCoords.z;
return currentDepth - bias/2 > closestDepth ? 0.0 : 1.0;
}
vec3 computeRadiancePointLight(PointLight pointlight, float distance);
vec3 computeRadianceDirectionalLight(DirectionalLight directional_light);
vec3 computeDiffuseReflectance(Material material, vec3 to_light, vec3 normal);
vec3 computeReflectance(Material material, vec3 to_light, vec3 normal, vec3 to_eye);
void main()
{
vec3 color = material.ambient * ambient_light;
vec3 to_eye = normalize(camera_position - vec3(world_position));
for (int i = 0; i < number_of_point_lights; ++i)
{
vec3 to_light = point_light[i].position - vec3(world_position);
float distance = length(to_light);
to_light /= distance;
color += computeReflectance(material, to_light, vec3(world_normal), to_eye) * computeRadiancePointLight(point_light[i], distance) * visible(point_light[i]);
}
vec3 to_light = -directional_light.direction;
color += computeReflectance(material, to_light, vec3(world_normal), to_eye) * computeRadianceDirectionalLight(directional_light);
final_color = vec4(color, 1.0f);
//final_color = vec4(texture(shadowTex, gl_FragCoord.xy/1024.f).r, texture(shadowTex, gl_FragCoord.xy/1024.f).r, texture(shadowTex, gl_FragCoord.xy/1024.f).r, 1.0f);
}
vec3 computeRadiancePointLight(PointLight point_light, float distance)
{
return point_light.intensity / (distance * distance);
}
vec3 computeRadianceDirectionalLight(DirectionalLight directional_light)
{
return directional_light.intensity;
}
vec3 computeReflectance(Material material, vec3 to_light, vec3 normal, vec3 to_eye)
{
vec3 diffuse_reflectance = max(dot(to_light, normal), 0.0f) * get_diffuse();
vec3 specular_reflectance = pow(max(dot(normalize(to_light + to_eye), normal), 0.0f), material.phong_exponent) * material.specular;
return diffuse_reflectance + specular_reflectance;
}