123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151 |
- #define CLEARCOATREFLECTANCE90 1.0
- // Light Results
- struct lightingInfo
- {
- vec3 diffuse;
- #ifdef SPECULARTERM
- vec3 specular;
- #endif
- #ifdef CLEARCOAT
- // xyz contains the clearcoat color.
- // w contains the 1 - clearcoat fresnel to ease the energy conservation computation.
- vec4 clearCoat;
- #endif
- #ifdef SHEEN
- vec3 sheen;
- #endif
- };
- // Simulate area (small) lights by increasing roughness
- float adjustRoughnessFromLightProperties(float roughness, float lightRadius, float lightDistance) {
- #if defined(USEPHYSICALLIGHTFALLOFF) || defined(USEGLTFLIGHTFALLOFF)
- // At small angle this approximation works.
- float lightRoughness = lightRadius / lightDistance;
- // Distribution can sum.
- float totalRoughness = saturate(lightRoughness + roughness);
- return totalRoughness;
- #else
- return roughness;
- #endif
- }
- vec3 computeHemisphericDiffuseLighting(preLightingInfo info, vec3 lightColor, vec3 groundColor) {
- return mix(groundColor, lightColor, info.NdotL);
- }
- vec3 computeDiffuseLighting(preLightingInfo info, vec3 lightColor) {
- float diffuseTerm = diffuseBRDF_Burley(info.NdotL, info.NdotV, info.VdotH, info.roughness);
- return diffuseTerm * info.attenuation * info.NdotL * lightColor;
- }
- vec3 computeProjectionTextureDiffuseLighting(sampler2D projectionLightSampler, mat4 textureProjectionMatrix){
- vec4 strq = textureProjectionMatrix * vec4(vPositionW, 1.0);
- strq /= strq.w;
- vec3 textureColor = texture2D(projectionLightSampler, strq.xy).rgb;
- return toLinearSpace(textureColor);
- }
- #ifdef SS_TRANSLUCENCY
- vec3 computeDiffuseAndTransmittedLighting(preLightingInfo info, vec3 lightColor, vec3 transmittance) {
- float NdotL = absEps(info.NdotLUnclamped);
- // Use wrap lighting to simulate SSS.
- float wrapNdotL = computeWrappedDiffuseNdotL(NdotL, 0.02);
- // Remap transmittance from tr to 1. if ndotl is negative.
- float trAdapt = step(0., info.NdotLUnclamped);
- vec3 transmittanceNdotL = mix(transmittance * wrapNdotL, vec3(wrapNdotL), trAdapt);
- float diffuseTerm = diffuseBRDF_Burley(NdotL, info.NdotV, info.VdotH, info.roughness);
- return diffuseTerm * transmittanceNdotL * info.attenuation * lightColor;
- }
- #endif
- #ifdef SPECULARTERM
- vec3 computeSpecularLighting(preLightingInfo info, vec3 N, vec3 reflectance0, vec3 reflectance90, float geometricRoughnessFactor, vec3 lightColor) {
- float NdotH = saturateEps(dot(N, info.H));
- float roughness = max(info.roughness, geometricRoughnessFactor);
- float alphaG = convertRoughnessToAverageSlope(roughness);
- vec3 fresnel = fresnelSchlickGGX(info.VdotH, reflectance0, reflectance90);
- float distribution = normalDistributionFunction_TrowbridgeReitzGGX(NdotH, alphaG);
- #ifdef BRDF_V_HEIGHT_CORRELATED
- float visibility = smithVisibility_GGXCorrelated(info.NdotL, info.NdotV, alphaG);
- #else
- float visibility = smithVisibility_TrowbridgeReitzGGXFast(info.NdotL, info.NdotV, alphaG);
- #endif
- vec3 specTerm = fresnel * distribution * visibility;
- return specTerm * info.attenuation * info.NdotL * lightColor;
- }
- #endif
- #ifdef ANISOTROPIC
- vec3 computeAnisotropicSpecularLighting(preLightingInfo info, vec3 V, vec3 N, vec3 T, vec3 B, float anisotropy, vec3 reflectance0, vec3 reflectance90, float geometricRoughnessFactor, vec3 lightColor) {
- float NdotH = saturateEps(dot(N, info.H));
- float TdotH = dot(T, info.H);
- float BdotH = dot(B, info.H);
- float TdotV = dot(T, V);
- float BdotV = dot(B, V);
- float TdotL = dot(T, info.L);
- float BdotL = dot(B, info.L);
- float alphaG = convertRoughnessToAverageSlope(info.roughness);
- vec2 alphaTB = getAnisotropicRoughness(alphaG, anisotropy);
- alphaTB = max(alphaTB, square(geometricRoughnessFactor));
- vec3 fresnel = fresnelSchlickGGX(info.VdotH, reflectance0, reflectance90);
- float distribution = normalDistributionFunction_BurleyGGX_Anisotropic(NdotH, TdotH, BdotH, alphaTB);
- float visibility = smithVisibility_GGXCorrelated_Anisotropic(info.NdotL, info.NdotV, TdotV, BdotV, TdotL, BdotL, alphaTB);
- vec3 specTerm = fresnel * distribution * visibility;
- return specTerm * info.attenuation * info.NdotL * lightColor;
- }
- #endif
- #ifdef CLEARCOAT
- vec4 computeClearCoatLighting(preLightingInfo info, vec3 Ncc, float geometricRoughnessFactor, float clearCoatIntensity, vec3 lightColor) {
- float NccdotL = saturateEps(dot(Ncc, info.L));
- float NccdotH = saturateEps(dot(Ncc, info.H));
- float clearCoatRoughness = max(info.roughness, geometricRoughnessFactor);
- float alphaG = convertRoughnessToAverageSlope(clearCoatRoughness);
- float fresnel = fresnelSchlickGGX(info.VdotH, vClearCoatRefractionParams.x, CLEARCOATREFLECTANCE90);
- fresnel *= clearCoatIntensity;
- float distribution = normalDistributionFunction_TrowbridgeReitzGGX(NccdotH, alphaG);
- float visibility = visibility_Kelemen(info.VdotH);
- float clearCoatTerm = fresnel * distribution * visibility;
- return vec4(
- clearCoatTerm * info.attenuation * NccdotL * lightColor,
- 1.0 - fresnel
- );
- }
- vec3 computeClearCoatLightingAbsorption(float NdotVRefract, vec3 L, vec3 Ncc, vec3 clearCoatColor, float clearCoatThickness, float clearCoatIntensity) {
- vec3 LRefract = -refract(L, Ncc, vClearCoatRefractionParams.y);
- float NdotLRefract = saturateEps(dot(Ncc, LRefract));
- vec3 absorption = computeClearCoatAbsorption(NdotVRefract, NdotLRefract, clearCoatColor, clearCoatThickness, clearCoatIntensity);
- return absorption;
- }
- #endif
- #ifdef SHEEN
- vec3 computeSheenLighting(preLightingInfo info, vec3 N, vec3 reflectance0, vec3 reflectance90, float geometricRoughnessFactor, vec3 lightColor) {
- float NdotH = saturateEps(dot(N, info.H));
- float roughness = max(info.roughness, geometricRoughnessFactor);
- float alphaG = convertRoughnessToAverageSlope(roughness);
- // No Fresnel Effect with sheen
- // vec3 fresnel = fresnelSchlickGGX(info.VdotH, reflectance0, reflectance90);
- vec3 fresnel = reflectance0;
- float distribution = normalDistributionFunction_CharlieSheen(NdotH, alphaG);
- float visibility = visibility_Ashikhmin(info.NdotL, info.NdotV);
- vec3 sheenTerm = fresnel * distribution * visibility;
- return sheenTerm * info.attenuation * info.NdotL * lightColor;
- }
- #endif
|