Normal/Height maps now working from models, and are only applied to models that have them.

This commit is contained in:
Zed A. Shaw 2026-09-30 17:36:48 -04:00
parent 4efe72b8d8
commit 8b41591360
8 changed files with 170 additions and 12 deletions

View file

@ -0,0 +1,82 @@
#version 330 core
out vec4 FragColor;
in vec3 FragPos;
in vec3 Normal;
in vec2 TexCoords;
in vec4 FragPosLightSpace;
in mat3 TBN;
uniform vec3 lightPos;
uniform vec3 viewPos;
uniform sampler2D shadowMap;
uniform sampler2D texture_diffuse1;
uniform sampler2D texture_specular1;
uniform sampler2D texture_height1; // bump/normal map
uniform bool hasHeight;
float ShadowCalculation(vec4 fragPosLightSpace, float bias)
{
// perform perspective divide
vec3 projCoords = fragPosLightSpace.xyz / fragPosLightSpace.w;
// transform to [0,1] range
projCoords = projCoords * 0.5 + 0.5;
// avoid the frustrum
if(projCoords.z > 1.0) return 0.0;
// get closest depth value from light's perspective (using [0,1] range fragPosLight as coords)
float closestDepth = texture(shadowMap, projCoords.xy).r;
// get depth of current fragment from light's perspective
float currentDepth = projCoords.z;
// check whether current frag pos is in shadow
// PCF
float shadow = 0.0;
vec2 texelSize = 1.0 / textureSize(shadowMap, 0);
for(int x = -1; x <= 1; ++x) {
for(int y = -1; y <= 1; ++y) {
float pcfDepth = texture(shadowMap, projCoords.xy + vec2(x, y) * texelSize).r;
shadow += currentDepth - bias > pcfDepth ? 1.0 : 0.0;
}
}
return shadow / 9.0;
}
void main()
{
vec3 color = texture(texture_diffuse1, TexCoords).rgb;
vec3 normal = normalize(Normal);
if(hasHeight) {
normal = texture(texture_height1, TexCoords).rgb;
normal = normal * 2.0 - 1.0;
normal = normalize(TBN * normal);
}
vec3 lightColor = vec3(0.7);
// ambient
vec3 ambient = 0.3 * lightColor;
// diffuse
vec3 lightDir = normalize(lightPos - FragPos);
float diff = max(dot(lightDir, normal), 0.0);
vec3 diffuse = diff * lightColor;
// specular
vec3 viewDir = normalize(viewPos - FragPos);
vec3 reflectDir = reflect(-lightDir, normal);
float spec = 0.0;
vec3 halfwayDir = normalize(lightDir + viewDir);
spec = pow(max(dot(normal, halfwayDir), 0.0), 64.0);
vec3 specular = spec * lightColor;
// calculate shadow
float bias = max(0.05 * (1.0 - dot(normal, lightDir)), 0.005);
float shadow = ShadowCalculation(FragPosLightSpace, bias);
vec3 lighting = (ambient + (1.0 - shadow) * (diffuse + specular)) * color;
FragColor = vec4(lighting, 1.0);
}

View file

@ -0,0 +1,31 @@
#version 330 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec3 aNormal;
layout (location = 2) in vec2 aTexCoords;
layout (location = 3) in vec3 aTangent;
layout (location = 4) in vec3 aBitangent;
out vec3 FragPos;
out vec3 Normal;
out vec2 TexCoords;
out vec4 FragPosLightSpace;
out mat3 TBN;
uniform mat4 projection;
uniform mat4 view;
uniform mat4 model;
uniform mat4 lightSpaceMatrix;
void main()
{
FragPos = vec3(model * vec4(aPos, 1.0));
Normal = transpose(inverse(mat3(model))) * aNormal;
TexCoords = aTexCoords;
FragPosLightSpace = lightSpaceMatrix * vec4(FragPos, 1.0);
gl_Position = projection * view * model * vec4(aPos, 1.0);
vec3 T = normalize(vec3(model * vec4(aTangent, 0.0)));
vec3 B = normalize(vec3(model * vec4(aBitangent, 0.0)));
vec3 N = normalize(vec3(model * vec4(aNormal, 0.0)));
TBN = mat3(T, B, N);
}