Skip to content

Commit

Permalink
Merge pull request #12082 from CesiumGS/ibl-diffuse
Browse files Browse the repository at this point in the history
Correct diffuse component for image-based lighting
  • Loading branch information
ggetz authored Jul 16, 2024
2 parents 7b93161 + 3ffd571 commit 1baec1d
Show file tree
Hide file tree
Showing 6 changed files with 77 additions and 76 deletions.
62 changes: 31 additions & 31 deletions Apps/Sandcastle/gallery/Image-Based Lighting.html
Original file line number Diff line number Diff line change
Expand Up @@ -65,63 +65,63 @@
);
}

const environmentMapURL =
"https://cesium.com/public/SandcastleSampleData/kiara_6_afternoon_2k_ibl.ktx2";
const modelURL = "../../SampleData/models/Pawns/Pawns.glb";

// This environment map was processed using Khronos's glTF IBL Sampler. To process your own:
// 1 - Download and build the Khronos glTF IBL Sampler (https://github.com/KhronosGroup/glTF-IBL-Sampler).
// 2 - Run `cli -inputPath /path/to/image.hdr -outCubeMap /path/to/output.ktx2`. Run `cli -h` for all options.
const environmentMapURL =
"https://cesium.com/public/SandcastleSampleData/kiara_6_afternoon_2k_ibl.ktx2";

// To generate the spherical harmonic coefficients below, use Google's Filament project:
// 1 - Download the Filament release (https://github.com/google/filament/releases).
// 2 - Run `cmgen --type=ktx --deploy=/path/to/output /path/to/image.hdr`. Other formats are also supported. Run `cmgen --help` for all options.
// 2 - Run `cmgen --no-mirror --type=ktx --deploy=/path/to/output /path/to/image.hdr`.
// Other formats are also supported. Run `cmgen --help` for all options.
// 3 - Take the generated coefficients and load them in CesiumJS as shown below.

const L00 = new Cesium.Cartesian3(
1.234709620475769,
1.221461296081543,
1.273156881332397
1.234897375106812,
1.221635103225708,
1.273374080657959
);
const L1_1 = new Cesium.Cartesian3(
1.135921120643616,
1.171217799186707,
1.287644743919373
1.136140108108521,
1.171419978141785,
1.287894368171692
);
const L10 = new Cesium.Cartesian3(
1.245193719863892,
1.245591878890991,
1.282818794250488
1.245410919189453,
1.245791077613831,
1.283067107200623
);
const L11 = new Cesium.Cartesian3(
-1.106930732727051,
-1.112522482872009,
-1.153198838233948
1.107124328613281,
1.112697005271912,
1.153419137001038
);
const L2_2 = new Cesium.Cartesian3(
-1.086226940155029,
-1.079731941223145,
-1.101912498474121
1.08641505241394,
1.079904079437256,
1.10212504863739
);
const L2_1 = new Cesium.Cartesian3(
1.189834713935852,
1.185906887054443,
1.214385271072388
1.190043210983276,
1.186099290847778,
1.214627981185913
);
const L20 = new Cesium.Cartesian3(
0.01778045296669,
0.02013735473156,
0.025313569232821
0.017783647403121,
0.020140396431088,
0.025317270308733
);
const L21 = new Cesium.Cartesian3(
-1.086826920509338,
-1.084611177444458,
-1.111204028129578
1.087014317512512,
1.084779262542725,
1.111417651176453
);
const L22 = new Cesium.Cartesian3(
-0.05241484940052,
-0.048303380608559,
-0.041960217058659
-0.052426788955927,
-0.048315055668354,
-0.041973855346441
);
const coefficients = [L00, L1_1, L10, L11, L2_2, L2_1, L20, L21, L22];

Expand Down
57 changes: 29 additions & 28 deletions Apps/Sandcastle/gallery/glTF PBR Extensions.html
Original file line number Diff line number Diff line change
Expand Up @@ -79,52 +79,53 @@

// To generate the spherical harmonic coefficients below, use Google's Filament project:
// 1 - Download the Filament release (https://github.com/google/filament/releases).
// 2 - Run `cmgen --type=ktx --deploy=/path/to/output /path/to/image.hdr`. Other formats are also supported. Run `cmgen --help` for all options.
// 2 - Run `cmgen --no-mirror --type=ktx --deploy=/path/to/output /path/to/image.hdr`.
// Other formats are also supported. Run `cmgen --help` for all options.
// 3 - Take the generated coefficients and load them in CesiumJS as shown below.
const L00 = new Cesium.Cartesian3(
1.234709620475769,
1.221461296081543,
1.273156881332397
1.234897375106812,
1.221635103225708,
1.273374080657959
);
const L1_1 = new Cesium.Cartesian3(
1.135921120643616,
1.171217799186707,
1.287644743919373
1.136140108108521,
1.171419978141785,
1.287894368171692
);
const L10 = new Cesium.Cartesian3(
1.245193719863892,
1.245591878890991,
1.282818794250488
1.245410919189453,
1.245791077613831,
1.283067107200623
);
const L11 = new Cesium.Cartesian3(
-1.106930732727051,
-1.112522482872009,
-1.153198838233948
1.107124328613281,
1.112697005271912,
1.153419137001038
);
const L2_2 = new Cesium.Cartesian3(
-1.086226940155029,
-1.079731941223145,
-1.101912498474121
1.08641505241394,
1.079904079437256,
1.10212504863739
);
const L2_1 = new Cesium.Cartesian3(
1.189834713935852,
1.185906887054443,
1.214385271072388
1.190043210983276,
1.186099290847778,
1.214627981185913
);
const L20 = new Cesium.Cartesian3(
0.01778045296669,
0.02013735473156,
0.025313569232821
0.017783647403121,
0.020140396431088,
0.025317270308733
);
const L21 = new Cesium.Cartesian3(
-1.086826920509338,
-1.084611177444458,
-1.111204028129578
1.087014317512512,
1.084779262542725,
1.111417651176453
);
const L22 = new Cesium.Cartesian3(
-0.05241484940052,
-0.048303380608559,
-0.041960217058659
-0.052426788955927,
-0.048315055668354,
-0.041973855346441
);
const coefficients = [L00, L1_1, L10, L11, L2_2, L2_1, L20, L21, L22];

Expand Down
1 change: 1 addition & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

- Updated geometric self-shadowing function to improve direct lighting on models using physically-based rendering. [#12063](https://github.com/CesiumGS/cesium/pull/12063)
- Fixed environment map LOD selection in image-based lighting. [#12070](https://github.com/CesiumGS/cesium/pull/12070)
- Corrected calculation of diffuse component in image-based lighting. [#12082](https://github.com/CesiumGS/cesium/pull/12082)

### 1.119 - 2024-07-01

Expand Down
4 changes: 2 additions & 2 deletions packages/engine/Source/Scene/ImageBasedLighting.js
Original file line number Diff line number Diff line change
Expand Up @@ -186,8 +186,8 @@ Object.defineProperties(ImageBasedLighting.prototype, {
* </p>
*
* These values can be obtained by preprocessing the environment map using the <code>cmgen</code> tool of
* {@link https://github.com/google/filament/releases|Google's Filament project}. This will also generate a KTX file that can be
* supplied to {@link Model#specularEnvironmentMaps}.
* {@link https://github.com/google/filament/releases|Google's Filament project}.
* Be sure to use the <code>--no-mirror</code> option in <code>cmgen</code>.
*
* @memberof ImageBasedLighting.prototype
*
Expand Down
21 changes: 10 additions & 11 deletions packages/engine/Source/Shaders/Model/ImageBasedLightingStageFS.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,7 @@ float getSunLuminance(vec3 positionWC, vec3 normalEC, vec3 lightDirectionEC)
) {
vec3 viewDirectionEC = -normalize(positionEC);
vec3 positionWC = vec3(czm_inverseView * vec4(positionEC, 1.0));
vec3 reflectionWC = normalize(czm_inverseViewRotation * normalize(reflect(viewDirectionEC, normalEC)));
vec3 reflectionWC = normalize(czm_inverseViewRotation * reflect(viewDirectionEC, normalEC));
vec3 skyMetrics = getProceduralSkyMetrics(positionWC, reflectionWC);

float roughness = material.roughness;
Expand Down Expand Up @@ -202,34 +202,33 @@ vec3 textureIBL(
vec3 lightDirectionEC,
czm_modelMaterial material
) {
// Find the direction in which to sample the environment map
vec3 cubeDir = normalize(model_iblReferenceFrameMatrix * normalize(reflect(-viewDirectionEC, normalEC)));

#ifdef DIFFUSE_IBL
vec3 diffuseContribution = computeDiffuseIBL(cubeDir) * material.diffuse;
vec3 normalMC = normalize(model_iblReferenceFrameMatrix * normalEC);
vec3 diffuseContribution = computeDiffuseIBL(normalMC) * material.diffuse;
#else
vec3 diffuseContribution = vec3(0.0);
#endif

float roughness = material.roughness;

#ifdef USE_ANISOTROPY
// Update environment map sampling direction to account for anisotropic distortion of specular reflection
// Bend normal to account for anisotropic distortion of specular reflection
vec3 anisotropyDirection = material.anisotropicB;
vec3 anisotropicTangent = cross(anisotropyDirection, viewDirectionEC);
vec3 anisotropicNormal = cross(anisotropicTangent, anisotropyDirection);
float bendFactor = 1.0 - material.anisotropyStrength * (1.0 - roughness);
float bendFactor = 1.0 - material.anisotropyStrength * (1.0 - material.roughness);
float bendFactorPow4 = bendFactor * bendFactor * bendFactor * bendFactor;
vec3 bentNormal = normalize(mix(anisotropicNormal, normalEC, bendFactorPow4));
cubeDir = normalize(model_iblReferenceFrameMatrix * normalize(reflect(-viewDirectionEC, bentNormal)));
vec3 reflectEC = reflect(-viewDirectionEC, bentNormal);
#else
vec3 reflectEC = reflect(-viewDirectionEC, normalEC);
#endif

#ifdef SPECULAR_IBL
vec3 reflectMC = normalize(model_iblReferenceFrameMatrix * reflectEC);
float NdotV = abs(dot(normalEC, viewDirectionEC)) + 0.001;
vec3 halfwayDirectionEC = normalize(viewDirectionEC + lightDirectionEC);
float VdotH = clamp(dot(viewDirectionEC, halfwayDirectionEC), 0.0, 1.0);
vec3 f0 = material.specular;
vec3 specularContribution = computeSpecularIBL(cubeDir, NdotV, VdotH, f0, roughness);
vec3 specularContribution = computeSpecularIBL(reflectMC, NdotV, VdotH, f0, material.roughness);
#else
vec3 specularContribution = vec3(0.0);
#endif
Expand Down
8 changes: 4 additions & 4 deletions packages/engine/Source/Shaders/Model/LightingStageFS.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,12 @@ vec3 addClearcoatReflection(vec3 baseLayerColor, vec3 position, vec3 lightDirect

#ifdef SPECULAR_IBL
// Find the direction in which to sample the environment map
vec3 cubeDir = normalize(model_iblReferenceFrameMatrix * normalize(reflect(-viewDirection, normal)));
vec3 iblColor = computeSpecularIBL(cubeDir, NdotV, NdotV, f0, roughness);
vec3 reflectMC = normalize(model_iblReferenceFrameMatrix * reflect(-viewDirection, normal));
vec3 iblColor = computeSpecularIBL(reflectMC, NdotV, NdotV, f0, roughness);
color += iblColor * material.occlusion;
#elif defined(USE_IBL_LIGHTING)
vec3 positionWC = vec3(czm_inverseView * vec4(position, 1.0));
vec3 reflectionWC = normalize(czm_inverseViewRotation * normalize(reflect(viewDirection, normal)));
vec3 reflectionWC = normalize(czm_inverseViewRotation * reflect(viewDirection, normal));
vec3 skyMetrics = getProceduralSkyMetrics(positionWC, reflectionWC);

vec3 specularIrradiance = getProceduralSpecularIrradiance(reflectionWC, skyMetrics, roughness);
Expand All @@ -57,7 +57,7 @@ vec3 addClearcoatReflection(vec3 baseLayerColor, vec3 position, vec3 lightDirect
#endif
float maximumComponent = czm_maximumComponent(lightColorHdr);
vec3 clampedLightColor = lightColorHdr / max(maximumComponent, 1.0);
color += clampedLightColor* iblColor * material.occlusion;
color += clampedLightColor * iblColor * material.occlusion;
#endif

float clearcoatFactor = material.clearcoatFactor;
Expand Down

0 comments on commit 1baec1d

Please sign in to comment.