第 16 课:Matallic Reflectance
实现:应该是混合metallic+fresnelSchlick
实现
uniform vec2 iResolution;
uniform float iTime;
uniform sampler2D iChannel0;
uniform sampler2D iChannel1;
uniform sampler2D iChannel2;
uniform mat4 inverseViewMatrix;
varying vec3 vPos;
varying vec3 vNormal;
varying vec2 vUv;
vec3 fresnelSchlick(float cosTheta, vec3 F0) {
float clampedCos = clamp(1.0 - cosTheta, 0.0, 1.0);
return F0 + (1.0 - F0) * pow(1.0 - clampedCos, 5.0);
}
vec3 getViewPos() {
return (inverseViewMatrix * vec4(0.0, 0.0, 0.0, 1.0)).xyz;
}
void main() {
vec3 viewPos = getViewPos();
vec3 fragColor = vec3(1.0, 0.6, 0.6);
vec3 fragNormal = normalize(vNormal);
float fragMetallic = 1.0;
vec3 fragPos = vPos;
vec3 lightColor = vec3(1.0, 1.0, 1.0);
vec3 lightPos = vec3(0.0, 0.5, -0.6);
vec3 lightDir = normalize(lightPos - fragPos);
vec3 viewDir = normalize(viewPos - fragPos);
vec3 halfwayDir = normalize(viewDir + lightDir);
// Phong Specular Component
float shininess = 8.0;
float specular = pow(max(dot(fragNormal, halfwayDir), 0.0), shininess);
float NoL = dot(fragNormal, lightDir);
// Base Reflectance
vec3 F0 = vec3(0.04);
F0 = mix(F0, fragColor, fragMetallic);
// Fresnel-Schlick Approximation
vec3 kS = fresnelSchlick(max(dot(halfwayDir, viewDir), 0.0), F0);
vec3 kD = vec3(1.0) - kS;
vec3 d = fragColor * NoL * lightColor * kD * (1.0-fragMetallic);
vec3 s = specular * lightColor * kS;
gl_FragColor = vec4(d + s, 1.0);
}
复盘笔记
- 应该是混合metallic+fresnelSchlick