in the source code of the pbr.fragment.fx shader that does the rendering of the PBRMaterial, I have seen that energy conservation is applied to the diffuse albedo with the following code (when using the specular workflow):
surfaceAlbedo.rgb = (1. - reflectance) * surfaceAlbedo.rgb;
float reflectance = max(max(surfaceReflectivityColor.r, surfaceReflectivityColor.g), surfaceReflectivityColor.b);
This means that the diffuse albedo is reduced by the maximum channel of the specular albedo. I do agree that this ensures energy conservation, but I am wondering that the maximum channel is used, instead of treating each channel separately (treating each RGB-channel as light of a specific wavelength that does not interact with the others).
By doing it in the way, it is programmed in the code, will one channel of the specular albedo with a value of 1.0 take away the whole diffuse contribution. Furthermore, if I have a diffuse and a specular texture, where the sum of each pixel pair is <= 1.0, will this shading model further reduce my diffuse values.
For example will a diffuse albedo of (0.5, 0.5, 0.5) and a specular albedo of (0.5, 0.5, 0.5) result in final diffuse albedo of (0.25, 0.25, 0.25).
This seems to me a little bit too restrictive, although it is part of the glTF specification (glTF/extensions/2.0/Khronos/KHR_materials_pbrSpecularGlossiness at master · KhronosGroup/glTF · GitHub).
Is there some point I am missing on this topic?
Is there a way in Babylon to deactivate this behaviour somehow?
After reading some publications about PBR, I noticed that a lot of times it is suggested to weight the diffuse albedo with the result of the Fresnel equation. Something like:
surfaceAlbedo.rgb = (vec3(1.0) - Fresnel(VdotH, F0)) * surfaceAlbedo.rgb;
This is the correct way of simulating light transport, isn’t it?
The Fresnel equations describe the light that gets reflected at the surface of an object, dependent on the viewing direction. The amount of light that does not get reflected at the surface, penetrates into the material, scatters around and gets reflected in a diffuse way thereafter.
The Babylon (glTF) shading is missing the dependency on the viewing direction.
One more note: For the project I am doing, I have to use the specular workflow. The metallic workflow is no option for me.
It would be a pleasure, if you share your thoughts on this topic with me.