@zephyr3d/scene 0.9.27 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +60 -27
- package/dist/animation/animation_bank.js +634 -0
- package/dist/animation/animation_bank.js.map +1 -0
- package/dist/animation/animation_bank_gpu.js +256 -0
- package/dist/animation/animation_bank_gpu.js.map +1 -0
- package/dist/animation/animationset.js +54 -0
- package/dist/animation/animationset.js.map +1 -1
- package/dist/animation/cloth/gpu_cloth_component.js +406 -0
- package/dist/animation/cloth/gpu_cloth_component.js.map +1 -0
- package/dist/animation/cloth/gpu_cloth_system.js +332 -202
- package/dist/animation/cloth/gpu_cloth_system.js.map +1 -1
- package/dist/animation/gpu_animation_driver.js +289 -0
- package/dist/animation/gpu_animation_driver.js.map +1 -0
- package/dist/animation/joint_dynamics/collision.js +112 -1
- package/dist/animation/joint_dynamics/collision.js.map +1 -1
- package/dist/animation/joint_dynamics/controller.js +6 -0
- package/dist/animation/joint_dynamics/controller.js.map +1 -1
- package/dist/animation/joint_dynamics/joint_dynamics_system.js +11 -0
- package/dist/animation/joint_dynamics/joint_dynamics_system.js.map +1 -1
- package/dist/animation/joint_dynamics/solver.js +50 -12
- package/dist/animation/joint_dynamics/solver.js.map +1 -1
- package/dist/animation/joint_dynamics/types.js.map +1 -1
- package/dist/animation/skeleton.js +279 -55
- package/dist/animation/skeleton.js.map +1 -1
- package/dist/animation/skin_palette_atlas.js +252 -0
- package/dist/animation/skin_palette_atlas.js.map +1 -0
- package/dist/animation/spring/multi_chain_spring_system.js +298 -38
- package/dist/animation/spring/multi_chain_spring_system.js.map +1 -1
- package/dist/animation/spring/spring_chain.js +2 -0
- package/dist/animation/spring/spring_chain.js.map +1 -1
- package/dist/animation/spring/spring_collider.js +159 -21
- package/dist/animation/spring/spring_collider.js.map +1 -1
- package/dist/animation/spring/spring_particle.js +1 -0
- package/dist/animation/spring/spring_particle.js.map +1 -1
- package/dist/animation/spring/spring_solver.js +173 -0
- package/dist/animation/spring/spring_solver.js.map +1 -0
- package/dist/animation/spring/spring_system.js +249 -24
- package/dist/animation/spring/spring_system.js.map +1 -1
- package/dist/animation/spring_modifier.js +32 -1
- package/dist/animation/spring_modifier.js.map +1 -1
- package/dist/app/app.js +26 -0
- package/dist/app/app.js.map +1 -1
- package/dist/app/engine.js +86 -15
- package/dist/app/engine.js.map +1 -1
- package/dist/app/gamepad.js +191 -0
- package/dist/app/gamepad.js.map +1 -0
- package/dist/app/inputactions.js +271 -0
- package/dist/app/inputactions.js.map +1 -0
- package/dist/app/inputmgr.js +331 -22
- package/dist/app/inputmgr.js.map +1 -1
- package/dist/app/loading.js +138 -0
- package/dist/app/loading.js.map +1 -0
- package/dist/app/pipelinecache.js +209 -0
- package/dist/app/pipelinecache.js.map +1 -0
- package/dist/app/runtimescript.js +25 -0
- package/dist/app/runtimescript.js.map +1 -1
- package/dist/app/scriptingsystem.js +54 -0
- package/dist/app/scriptingsystem.js.map +1 -1
- package/dist/app/scriptregistry.js +7 -2
- package/dist/app/scriptregistry.js.map +1 -1
- package/dist/asset/asset_manifest.js +59 -0
- package/dist/asset/asset_manifest.js.map +1 -0
- package/dist/asset/asset_preload.js +258 -0
- package/dist/asset/asset_preload.js.map +1 -0
- package/dist/asset/assetmanager.js +117 -65
- package/dist/asset/assetmanager.js.map +1 -1
- package/dist/asset/loaders/ktx2/basis/LICENSE +201 -0
- package/dist/asset/loaders/ktx2/basis/basis_transcoder.js +2 -0
- package/dist/asset/loaders/ktx2/basis/basis_transcoder.wasm +0 -0
- package/dist/asset/loaders/ktx2/basis_location.js +17 -0
- package/dist/asset/loaders/ktx2/basis_location.js.map +1 -0
- package/dist/asset/loaders/ktx2/ktx2_loader.js +88 -0
- package/dist/asset/loaders/ktx2/ktx2_loader.js.map +1 -0
- package/dist/asset/loaders/ktx2/ktx2_targets.js +118 -0
- package/dist/asset/loaders/ktx2/ktx2_targets.js.map +1 -0
- package/dist/asset/loaders/ktx2/transcoder_pool.js +259 -0
- package/dist/asset/loaders/ktx2/transcoder_pool.js.map +1 -0
- package/dist/asset/mesh_lod_builder.js +104 -0
- package/dist/asset/mesh_lod_builder.js.map +1 -0
- package/dist/asset/mesh_settings.js +111 -0
- package/dist/asset/mesh_settings.js.map +1 -0
- package/dist/asset/meshopt_decoder.js +18 -0
- package/dist/asset/meshopt_decoder.js.map +1 -0
- package/dist/asset/meshopt_simplifier.js +26 -0
- package/dist/asset/meshopt_simplifier.js.map +1 -0
- package/dist/asset/model.js +171 -1
- package/dist/asset/model.js.map +1 -1
- package/dist/asset/texture_settings.js +231 -0
- package/dist/asset/texture_settings.js.map +1 -0
- package/dist/asset/zmsh_binary.js +131 -0
- package/dist/asset/zmsh_binary.js.map +1 -0
- package/dist/asset/zsdf_binary.js +111 -0
- package/dist/asset/zsdf_binary.js.map +1 -0
- package/dist/blitter/bilateralblur.js +1 -2
- package/dist/blitter/bilateralblur.js.map +1 -1
- package/dist/blitter/gaussianblur.js +1 -6
- package/dist/blitter/gaussianblur.js.map +1 -1
- package/dist/camera/base.js +31 -10
- package/dist/camera/base.js.map +1 -1
- package/dist/camera/camera.js +104 -178
- package/dist/camera/camera.js.map +1 -1
- package/dist/camera/follow.js +342 -0
- package/dist/camera/follow.js.map +1 -0
- package/dist/camera/fps.js +9 -7
- package/dist/camera/fps.js.map +1 -1
- package/dist/camera/orbit.js +46 -19
- package/dist/camera/orbit.js.map +1 -1
- package/dist/index.d.ts +25436 -15990
- package/dist/index.js +65 -11
- package/dist/index.js.map +1 -1
- package/dist/material/blinn.js +3 -0
- package/dist/material/blinn.js.map +1 -1
- package/dist/material/eye.js +1 -1
- package/dist/material/eye.js.map +1 -1
- package/dist/material/hair.js +2 -3
- package/dist/material/hair.js.map +1 -1
- package/dist/material/lambert.js +4 -1
- package/dist/material/lambert.js.map +1 -1
- package/dist/material/material.js +66 -4
- package/dist/material/material.js.map +1 -1
- package/dist/material/meshmaterial.js +118 -45
- package/dist/material/meshmaterial.js.map +1 -1
- package/dist/material/mixins/lightmodel/blinnphong.js +1 -1
- package/dist/material/mixins/lightmodel/blinnphong.js.map +1 -1
- package/dist/material/mixins/lightmodel/lambert.js +1 -1
- package/dist/material/mixins/lightmodel/lambert.js.map +1 -1
- package/dist/material/mixins/lightmodel/pbrblueprintmixin.js +34 -61
- package/dist/material/mixins/lightmodel/pbrblueprintmixin.js.map +1 -1
- package/dist/material/mixins/lightmodel/pbrmetallicroughness.js +16 -2
- package/dist/material/mixins/lightmodel/pbrmetallicroughness.js.map +1 -1
- package/dist/material/mixins/lightmodel/pbrspecularglossness.js +2 -1
- package/dist/material/mixins/lightmodel/pbrspecularglossness.js.map +1 -1
- package/dist/material/mixins/lit.js +191 -83
- package/dist/material/mixins/lit.js.map +1 -1
- package/dist/material/mixins/pbr/common.js +31 -206
- package/dist/material/mixins/pbr/common.js.map +1 -1
- package/dist/material/mtoon.js +1 -1
- package/dist/material/mtoon.js.map +1 -1
- package/dist/material/pbrmr.js +3 -0
- package/dist/material/pbrmr.js.map +1 -1
- package/dist/material/pbrsg.js +3 -0
- package/dist/material/pbrsg.js.map +1 -1
- package/dist/material/sdf_debug.js +78 -0
- package/dist/material/sdf_debug.js.map +1 -0
- package/dist/material/shader/helper.js +333 -191
- package/dist/material/shader/helper.js.map +1 -1
- package/dist/material/shader/terrain_blend.js +204 -43
- package/dist/material/shader/terrain_blend.js.map +1 -1
- package/dist/material/skin.js +331 -297
- package/dist/material/skin.js.map +1 -1
- package/dist/material/skinprofile.js +1058 -0
- package/dist/material/skinprofile.js.map +1 -0
- package/dist/material/sss.js +353 -0
- package/dist/material/sss.js.map +1 -0
- package/dist/material/sss_kernel.js +265 -0
- package/dist/material/sss_kernel.js.map +1 -0
- package/dist/material/sssprofile.js +879 -0
- package/dist/material/sssprofile.js.map +1 -0
- package/dist/material/subsurfaceprofile.js +4 -8
- package/dist/material/subsurfaceprofile.js.map +1 -1
- package/dist/material/terrain-cm.js +464 -188
- package/dist/material/terrain-cm.js.map +1 -1
- package/dist/material/unlit.js +3 -0
- package/dist/material/unlit.js.map +1 -1
- package/dist/material/water.js +1261 -1438
- package/dist/material/water.js.map +1 -1
- package/dist/node_modules/meshoptimizer/LICENSE +21 -0
- package/dist/node_modules/meshoptimizer/meshopt_decoder.js +197 -0
- package/dist/node_modules/meshoptimizer/meshopt_decoder.js.map +1 -0
- package/dist/node_modules/meshoptimizer/meshopt_simplifier.js +677 -0
- package/dist/node_modules/meshoptimizer/meshopt_simplifier.js.map +1 -0
- package/dist/physics/character.js +226 -0
- package/dist/physics/character.js.map +1 -0
- package/dist/physics/collider.js +209 -0
- package/dist/physics/collider.js.map +1 -0
- package/dist/physics/events.js +79 -0
- package/dist/physics/events.js.map +1 -0
- package/dist/physics/joint.js +272 -0
- package/dist/physics/joint.js.map +1 -0
- package/dist/physics/node_physics.js +234 -0
- package/dist/physics/node_physics.js.map +1 -0
- package/dist/physics/part.js +91 -0
- package/dist/physics/part.js.map +1 -0
- package/dist/physics/rigid_body.js +379 -0
- package/dist/physics/rigid_body.js.map +1 -0
- package/dist/physics/vehicle.js +335 -0
- package/dist/physics/vehicle.js.map +1 -0
- package/dist/physics/world.js +25 -0
- package/dist/physics/world.js.map +1 -0
- package/dist/posteffect/bloom.js +49 -14
- package/dist/posteffect/bloom.js.map +1 -1
- package/dist/posteffect/motionblur.js +106 -106
- package/dist/posteffect/motionblur.js.map +1 -1
- package/dist/posteffect/postsss.js +572 -0
- package/dist/posteffect/postsss.js.map +1 -0
- package/dist/posteffect/sao.js +2 -6
- package/dist/posteffect/sao.js.map +1 -1
- package/dist/posteffect/skinsss.js +605 -355
- package/dist/posteffect/skinsss.js.map +1 -1
- package/dist/posteffect/ssgi.js +91 -162
- package/dist/posteffect/ssgi.js.map +1 -1
- package/dist/posteffect/ssr.js +3 -11
- package/dist/posteffect/ssr.js.map +1 -1
- package/dist/posteffect/sss.js +4 -13
- package/dist/posteffect/sss.js.map +1 -1
- package/dist/posteffect/taa.js +1 -0
- package/dist/posteffect/taa.js.map +1 -1
- package/dist/render/abuffer_oit.js +3 -2
- package/dist/render/abuffer_oit.js.map +1 -1
- package/dist/render/clipmap.js +179 -64
- package/dist/render/clipmap.js.map +1 -1
- package/dist/render/cluster_light.js +958 -224
- package/dist/render/cluster_light.js.map +1 -1
- package/dist/render/cull_visitor.js +25 -5
- package/dist/render/cull_visitor.js.map +1 -1
- package/dist/render/debug_views.js +37 -0
- package/dist/render/debug_views.js.map +1 -0
- package/dist/render/depthpass.js +5 -1
- package/dist/render/depthpass.js.map +1 -1
- package/dist/render/drawable_mixin.js +53 -6
- package/dist/render/drawable_mixin.js.map +1 -1
- package/dist/render/dualdepthpeeling_oit.js +5 -5
- package/dist/render/dualdepthpeeling_oit.js.map +1 -1
- package/dist/render/envlight.js +196 -113
- package/dist/render/envlight.js.map +1 -1
- package/dist/render/fbm_wavegenerator.js +5 -10
- package/dist/render/fbm_wavegenerator.js.map +1 -1
- package/dist/render/fft_wavegenerator.js +247 -157
- package/dist/render/fft_wavegenerator.js.map +1 -1
- package/dist/render/gerstner_wavegenerator.js +16 -38
- package/dist/render/gerstner_wavegenerator.js.map +1 -1
- package/dist/render/gi/probe_volume.js +1334 -0
- package/dist/render/gi/probe_volume.js.map +1 -0
- package/dist/render/gi/scene_gi.js +282 -0
- package/dist/render/gi/scene_gi.js.map +1 -0
- package/dist/render/gi/voxel_atlas.js +198 -0
- package/dist/render/gi/voxel_atlas.js.map +1 -0
- package/dist/render/gi/voxel_lighting.js +652 -0
- package/dist/render/gi/voxel_lighting.js.map +1 -0
- package/dist/render/gi/voxel_scene.js +642 -0
- package/dist/render/gi/voxel_scene.js.map +1 -0
- package/dist/render/gi/voxelize_pass.js +223 -0
- package/dist/render/gi/voxelize_pass.js.map +1 -0
- package/dist/render/globalbindgroup_allocator.js +3 -2
- package/dist/render/globalbindgroup_allocator.js.map +1 -1
- package/dist/render/gpu_picking.js +9 -36
- package/dist/render/gpu_picking.js.map +1 -1
- package/dist/render/instance_culling.js +499 -0
- package/dist/render/instance_culling.js.map +1 -0
- package/dist/render/lightpass.js +19 -8
- package/dist/render/lightpass.js.map +1 -1
- package/dist/render/lod.js +46 -0
- package/dist/render/lod.js.map +1 -0
- package/dist/render/primitive.js +301 -9
- package/dist/render/primitive.js.map +1 -1
- package/dist/render/primitive_readback.js +209 -0
- package/dist/render/primitive_readback.js.map +1 -0
- package/dist/render/render_queue.js +162 -11
- package/dist/render/render_queue.js.map +1 -1
- package/dist/render/renderer.js +10 -7
- package/dist/render/renderer.js.map +1 -1
- package/dist/render/rendergraph/blackboard.js +14 -1
- package/dist/render/rendergraph/blackboard.js.map +1 -1
- package/dist/render/rendergraph/executor.js +136 -0
- package/dist/render/rendergraph/executor.js.map +1 -1
- package/dist/render/rendergraph/forward_plus_builder.js +272 -55
- package/dist/render/rendergraph/forward_plus_builder.js.map +1 -1
- package/dist/render/rendergraph/frame_graph_context.js +41 -0
- package/dist/render/rendergraph/frame_graph_context.js.map +1 -0
- package/dist/render/rendergraph/scene_render_context.js +31 -2
- package/dist/render/rendergraph/scene_render_context.js.map +1 -1
- package/dist/render/rendergraph/types.js.map +1 -1
- package/dist/render/renderpass.js +28 -5
- package/dist/render/renderpass.js.map +1 -1
- package/dist/render/sdf/box_allocator.js +98 -0
- package/dist/render/sdf/box_allocator.js.map +1 -0
- package/dist/render/sdf/global_sdf.js +865 -0
- package/dist/render/sdf/global_sdf.js.map +1 -0
- package/dist/render/sdf/scene_sdf.js +562 -0
- package/dist/render/sdf/scene_sdf.js.map +1 -0
- package/dist/render/sdf/sdf_atlas.js +227 -0
- package/dist/render/sdf/sdf_atlas.js.map +1 -0
- package/dist/render/sdf/sdf_programs.js +42 -0
- package/dist/render/sdf/sdf_programs.js.map +1 -0
- package/dist/render/sdf/sdf_view.js +199 -0
- package/dist/render/sdf/sdf_view.js.map +1 -0
- package/dist/render/sdf/waterline.js +610 -0
- package/dist/render/sdf/waterline.js.map +1 -0
- package/dist/render/shadow_mask_pass.js +142 -25
- package/dist/render/shadow_mask_pass.js.map +1 -1
- package/dist/render/shore_wave_generator.js +1193 -0
- package/dist/render/shore_wave_generator.js.map +1 -0
- package/dist/render/sky.js +516 -86
- package/dist/render/sky.js.map +1 -1
- package/dist/render/transmission_thickness_pass.js +477 -0
- package/dist/render/transmission_thickness_pass.js.map +1 -0
- package/dist/render/underwater.js +58 -158
- package/dist/render/underwater.js.map +1 -1
- package/dist/render/virtualtexture/virtual_texture.js +1214 -0
- package/dist/render/virtualtexture/virtual_texture.js.map +1 -0
- package/dist/render/volumetric_cloud/cloud_common.js +472 -0
- package/dist/render/volumetric_cloud/cloud_common.js.map +1 -0
- package/dist/render/volumetric_cloud/cloud_noise.js +189 -0
- package/dist/render/volumetric_cloud/cloud_noise.js.map +1 -0
- package/dist/render/volumetric_cloud/debug_view.js +131 -0
- package/dist/render/volumetric_cloud/debug_view.js.map +1 -0
- package/dist/render/volumetric_cloud/resources.js +380 -0
- package/dist/render/volumetric_cloud/resources.js.map +1 -0
- package/dist/render/volumetric_cloud/sky_cache.js +380 -0
- package/dist/render/volumetric_cloud/sky_cache.js.map +1 -0
- package/dist/render/volumetric_cloud/volumetric_cloud.js +318 -0
- package/dist/render/volumetric_cloud/volumetric_cloud.js.map +1 -0
- package/dist/render/water_caustics.js +134 -319
- package/dist/render/water_caustics.js.map +1 -1
- package/dist/render/water_foam.js +627 -0
- package/dist/render/water_foam.js.map +1 -0
- package/dist/render/water_interaction.js +1795 -0
- package/dist/render/water_interaction.js.map +1 -0
- package/dist/render/weightedblended_oit.js +3 -3
- package/dist/render/weightedblended_oit.js.map +1 -1
- package/dist/scene/basesprite.js +9 -4
- package/dist/scene/basesprite.js.map +1 -1
- package/dist/scene/batchgroup.js +108 -12
- package/dist/scene/batchgroup.js.map +1 -1
- package/dist/scene/environment.js +28 -7
- package/dist/scene/environment.js.map +1 -1
- package/dist/scene/foliage.js +1020 -0
- package/dist/scene/foliage.js.map +1 -0
- package/dist/scene/foliage_buckets.js +147 -0
- package/dist/scene/foliage_buckets.js.map +1 -0
- package/dist/scene/foliage_mask.js +358 -0
- package/dist/scene/foliage_mask.js.map +1 -0
- package/dist/scene/hair.js +15 -4
- package/dist/scene/hair.js.map +1 -1
- package/dist/scene/light.js +179 -13
- package/dist/scene/light.js.map +1 -1
- package/dist/scene/mesh.js +327 -45
- package/dist/scene/mesh.js.map +1 -1
- package/dist/scene/meshdrawable.js +6 -0
- package/dist/scene/meshdrawable.js.map +1 -1
- package/dist/scene/msdftext.js +9 -3
- package/dist/scene/msdftext.js.map +1 -1
- package/dist/scene/msdftextsprite.js +9 -3
- package/dist/scene/msdftextsprite.js.map +1 -1
- package/dist/scene/particlesys.js +8 -2
- package/dist/scene/particlesys.js.map +1 -1
- package/dist/scene/physics_settings.js +157 -0
- package/dist/scene/physics_settings.js.map +1 -0
- package/dist/scene/scene.js +190 -44
- package/dist/scene/scene.js.map +1 -1
- package/dist/scene/scene_node.js +147 -6
- package/dist/scene/scene_node.js.map +1 -1
- package/dist/scene/terrain-cm/bladegrassmaterial.js +735 -0
- package/dist/scene/terrain-cm/bladegrassmaterial.js.map +1 -0
- package/dist/scene/terrain-cm/grass.js +881 -42
- package/dist/scene/terrain-cm/grass.js.map +1 -1
- package/dist/scene/terrain-cm/grass_gpu.js +929 -0
- package/dist/scene/terrain-cm/grass_gpu.js.map +1 -0
- package/dist/scene/terrain-cm/grassmaterial.js +180 -9
- package/dist/scene/terrain-cm/grassmaterial.js.map +1 -1
- package/dist/scene/terrain-cm/terrain-cm.js +465 -36
- package/dist/scene/terrain-cm/terrain-cm.js.map +1 -1
- package/dist/scene/terrain-cm/terrain_gi_albedo.js +257 -0
- package/dist/scene/terrain-cm/terrain_gi_albedo.js.map +1 -0
- package/dist/scene/terrain-cm/terrain_rvt.js +395 -0
- package/dist/scene/terrain-cm/terrain_rvt.js.map +1 -0
- package/dist/scene/update_queue.js +54 -0
- package/dist/scene/update_queue.js.map +1 -0
- package/dist/scene/water.js +633 -268
- package/dist/scene/water.js.map +1 -1
- package/dist/scene/water_surface_sampler.js +324 -0
- package/dist/scene/water_surface_sampler.js.map +1 -0
- package/dist/scene/wind.js +317 -0
- package/dist/scene/wind.js.map +1 -0
- package/dist/shaders/atmosphere.js +388 -166
- package/dist/shaders/atmosphere.js.map +1 -1
- package/dist/shaders/fog.js +100 -32
- package/dist/shaders/fog.js.map +1 -1
- package/dist/shaders/gi.js +365 -0
- package/dist/shaders/gi.js.map +1 -0
- package/dist/shaders/ltc_rect.js +202 -0
- package/dist/shaders/ltc_rect.js.map +1 -0
- package/dist/shaders/misc.js +1 -10
- package/dist/shaders/misc.js.map +1 -1
- package/dist/shaders/noise.js +5 -1
- package/dist/shaders/noise.js.map +1 -1
- package/dist/shaders/probes.js +309 -0
- package/dist/shaders/probes.js.map +1 -0
- package/dist/shaders/sdf.js +537 -0
- package/dist/shaders/sdf.js.map +1 -0
- package/dist/shaders/shadow.js +104 -70
- package/dist/shaders/shadow.js.map +1 -1
- package/dist/shaders/skin_brdf.js +243 -0
- package/dist/shaders/skin_brdf.js.map +1 -0
- package/dist/shaders/ssgi.js +63 -0
- package/dist/shaders/ssgi.js.map +1 -0
- package/dist/shaders/ssgi_reprojection.js +118 -0
- package/dist/shaders/ssgi_reprojection.js.map +1 -0
- package/dist/shaders/ssr.js +6 -159
- package/dist/shaders/ssr.js.map +1 -1
- package/dist/shaders/temporal.js +38 -27
- package/dist/shaders/temporal.js.map +1 -1
- package/dist/shaders/water.js +32 -82
- package/dist/shaders/water.js.map +1 -1
- package/dist/shaders/water_medium.js +7 -21
- package/dist/shaders/water_medium.js.map +1 -1
- package/dist/shadow/dom.js +110 -19
- package/dist/shadow/dom.js.map +1 -1
- package/dist/shadow/esm.js +3 -3
- package/dist/shadow/esm.js.map +1 -1
- package/dist/shadow/pcf_opt.js +15 -48
- package/dist/shadow/pcf_opt.js.map +1 -1
- package/dist/shadow/pcf_pd.js +15 -53
- package/dist/shadow/pcf_pd.js.map +1 -1
- package/dist/shadow/pcss.js +34 -9
- package/dist/shadow/pcss.js.map +1 -1
- package/dist/shadow/shadow_impl.js +3 -8
- package/dist/shadow/shadow_impl.js.map +1 -1
- package/dist/shadow/shadow_region.js +40 -2
- package/dist/shadow/shadow_region.js.map +1 -1
- package/dist/shadow/shadowmapper.js +93 -53
- package/dist/shadow/shadowmapper.js.map +1 -1
- package/dist/shadow/ssm.js +18 -72
- package/dist/shadow/ssm.js.map +1 -1
- package/dist/shadow/vsm.js +3 -3
- package/dist/shadow/vsm.js.map +1 -1
- package/dist/shapes/shape.js +44 -1
- package/dist/shapes/shape.js.map +1 -1
- package/dist/utility/buoyancy.js +287 -0
- package/dist/utility/buoyancy.js.map +1 -0
- package/dist/utility/physical.js +10 -1
- package/dist/utility/physical.js.map +1 -1
- package/dist/utility/pmrem.js +17 -43
- package/dist/utility/pmrem.js.map +1 -1
- package/dist/utility/sdf/bake.js +435 -0
- package/dist/utility/sdf/bake.js.map +1 -0
- package/dist/utility/sdf/bvh.js +576 -0
- package/dist/utility/sdf/bvh.js.map +1 -0
- package/dist/utility/serialization/manager.js +34 -6
- package/dist/utility/serialization/manager.js.map +1 -1
- package/dist/utility/serialization/scene/animation.js +46 -5
- package/dist/utility/serialization/scene/animation.js.map +1 -1
- package/dist/utility/serialization/scene/batch.js +11 -4
- package/dist/utility/serialization/scene/batch.js.map +1 -1
- package/dist/utility/serialization/scene/camera.js +87 -254
- package/dist/utility/serialization/scene/camera.js.map +1 -1
- package/dist/utility/serialization/scene/cloth.js +25 -0
- package/dist/utility/serialization/scene/cloth.js.map +1 -0
- package/dist/utility/serialization/scene/common.js +14 -6
- package/dist/utility/serialization/scene/common.js.map +1 -1
- package/dist/utility/serialization/scene/foliage.js +821 -0
- package/dist/utility/serialization/scene/foliage.js.map +1 -0
- package/dist/utility/serialization/scene/hair.js +11 -4
- package/dist/utility/serialization/scene/hair.js.map +1 -1
- package/dist/utility/serialization/scene/light.js +115 -7
- package/dist/utility/serialization/scene/light.js.map +1 -1
- package/dist/utility/serialization/scene/material.js +388 -220
- package/dist/utility/serialization/scene/material.js.map +1 -1
- package/dist/utility/serialization/scene/mesh.js +69 -4
- package/dist/utility/serialization/scene/mesh.js.map +1 -1
- package/dist/utility/serialization/scene/node.js +140 -5
- package/dist/utility/serialization/scene/node.js.map +1 -1
- package/dist/utility/serialization/scene/node_physics.js +1318 -0
- package/dist/utility/serialization/scene/node_physics.js.map +1 -0
- package/dist/utility/serialization/scene/particle.js +11 -4
- package/dist/utility/serialization/scene/particle.js.map +1 -1
- package/dist/utility/serialization/scene/physics.js +120 -0
- package/dist/utility/serialization/scene/physics.js.map +1 -0
- package/dist/utility/serialization/scene/primitive.js +124 -10
- package/dist/utility/serialization/scene/primitive.js.map +1 -1
- package/dist/utility/serialization/scene/scene.js +1687 -51
- package/dist/utility/serialization/scene/scene.js.map +1 -1
- package/dist/utility/serialization/scene/sprite.js +11 -4
- package/dist/utility/serialization/scene/sprite.js.map +1 -1
- package/dist/utility/serialization/scene/terrain.js +163 -33
- package/dist/utility/serialization/scene/terrain.js.map +1 -1
- package/dist/utility/serialization/scene/text.js +11 -4
- package/dist/utility/serialization/scene/text.js.map +1 -1
- package/dist/utility/serialization/scene/water.js +1543 -264
- package/dist/utility/serialization/scene/water.js.map +1 -1
- package/dist/utility/serialization/types.js.map +1 -1
- package/dist/utility/shprojector.js +10 -22
- package/dist/utility/shprojector.js.map +1 -1
- package/dist/utility/textures/foam.js +170 -0
- package/dist/utility/textures/foam.js.map +1 -0
- package/dist/utility/textures/ggxlut.js +17 -43
- package/dist/utility/textures/ggxlut.js.map +1 -1
- package/dist/utility/textures/ltcdata.js +4 -4
- package/dist/utility/textures/ltcdata.js.map +1 -1
- package/dist/utility/textures/ltclut.js +16 -6
- package/dist/utility/textures/ltclut.js.map +1 -1
- package/dist/utility/unsupported.js +24 -0
- package/dist/utility/unsupported.js.map +1 -0
- package/dist/values.js +13 -1
- package/dist/values.js.map +1 -1
- package/package.json +25 -12
- package/src/asset/loaders/ktx2/basis/LICENSE +201 -0
- package/src/asset/loaders/ktx2/basis/basis_transcoder.js +2 -0
- package/src/asset/loaders/ktx2/basis/basis_transcoder.wasm +0 -0
- package/src/asset/meshoptimizer/LICENSE +21 -0
- package/dist/animation/joint_dynamics/convex_collider.js +0 -320
- package/dist/animation/joint_dynamics/convex_collider.js.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"skin.js","sources":["../../src/material/skin.ts"],"sourcesContent":["import type { BindGroup, PBFunctionScope } from '@zephyr3d/device';\r\nimport type { Clonable, Immutable } from '@zephyr3d/base';\r\nimport { Vector4 } from '@zephyr3d/base';\r\nimport { MeshMaterial, applyMaterialMixins } from './meshmaterial';\r\nimport { mixinLight } from './mixins/lit';\r\nimport { mixinVertexColor } from './mixins/vertexcolor';\r\nimport { mixinTextureProps } from './mixins/texture';\r\nimport { ShaderHelper } from './shader/helper';\r\nimport type { DrawContext } from '../render';\r\nimport { LIGHT_TYPE_POINT, MaterialVaryingFlags, RENDER_PASS_TYPE_LIGHT } from '../values';\r\n\r\n/**\r\n * HDR range packed into the SkinSSS side buffer when the render graph falls\r\n * back to an 8-bit format. The material divides the scatter irradiance by this\r\n * factor on write and {@link SkinSSS} multiplies it back after the blur.\r\n * @public\r\n */\r\nexport const SKIN_SSS_LDR_ENCODE_RANGE = 4;\r\n\r\n/**\r\n * Stylized realtime skin material.\r\n *\r\n * @remarks\r\n * This material is designed for the {@link SkinSSS} post effect. It renders a regular lit color\r\n * and, when `camera.skinSSS` is enabled, writes the *diffusible* part of that color - the stylized\r\n * diffuse ramp plus back-lit transmission, without specular - into the `SkinSSSTexture` MRT.\r\n *\r\n * The side buffer holds exactly the same term that is already in the lit color, untinted and\r\n * unscaled. {@link SkinSSS} subtracts it and adds back a channel-dependent diffused version, so\r\n * the redistribution is energy conserving by construction and disabling the effect leaves the\r\n * image unchanged. Scatter tint, strength and radius therefore live on the post effect, not here.\r\n *\r\n * Stylization is split from diffusion on purpose. {@link SkinMaterial.diffuseWrap},\r\n * {@link SkinMaterial.diffuseSoftness}, {@link SkinMaterial.shadowTint} and\r\n * {@link SkinMaterial.brightening} shape the direct lighting ramp; the post effect then diffuses\r\n * whatever ramp they produced. A stylized ramp stays stylized after scattering rather than being\r\n * averaged away.\r\n *\r\n * The optional `subsurfaceTexture` uses R as skin mask, G as local softness and B as thickness\r\n * for the back-lit transmission term (thin regions such as ears and nostrils glow when lit from\r\n * behind; enable it by setting {@link SkinMaterial.transmissionStrength}).\r\n *\r\n * @public\r\n */\r\nexport class SkinMaterial\r\n extends applyMaterialMixins(MeshMaterial, mixinLight, mixinVertexColor, mixinTextureProps('subsurface'))\r\n implements Clonable<SkinMaterial>\r\n{\r\n private static readonly FEATURE_VERTEX_NORMAL = this.defineFeature();\r\n private static readonly FEATURE_VERTEX_TANGENT = this.defineFeature();\r\n private _shininess: number;\r\n private _specularStrength: number;\r\n private _diffuseWrap: number;\r\n private _diffuseSoftness: number;\r\n private _scatterWrap: number;\r\n private _scatterStrength: number;\r\n private readonly _scatterColor: Vector4;\r\n private _transmissionStrength: number;\r\n private _transmissionPower: number;\r\n private readonly _shadowTint: Vector4;\r\n private _brightening: number;\r\n\r\n constructor() {\r\n super();\r\n this._shininess = 72;\r\n this._specularStrength = 1;\r\n this._diffuseWrap = 0.28;\r\n this._diffuseSoftness = 0.45;\r\n this._scatterWrap = 0.65;\r\n this._scatterStrength = 1.5;\r\n this._scatterColor = new Vector4(1, 0.42, 0.28, 1);\r\n this._transmissionStrength = 0;\r\n this._transmissionPower = 4;\r\n this._shadowTint = new Vector4(0, 0, 0, 1);\r\n this._brightening = 0;\r\n this.useFeature(SkinMaterial.FEATURE_VERTEX_NORMAL, true);\r\n }\r\n\r\n /** Marker used by the forward render graph to allocate the SkinSSS MRT. */\r\n get skinSSS() {\r\n return true;\r\n }\r\n\r\n clone() {\r\n const other = new SkinMaterial();\r\n other.copyFrom(this);\r\n return other;\r\n }\r\n\r\n copyFrom(other: this) {\r\n super.copyFrom(other);\r\n this.vertexNormal = other.vertexNormal;\r\n this.vertexTangent = other.vertexTangent;\r\n this.shininess = other.shininess;\r\n this.specularStrength = other.specularStrength;\r\n this.diffuseWrap = other.diffuseWrap;\r\n this.diffuseSoftness = other.diffuseSoftness;\r\n this.scatterWrap = other.scatterWrap;\r\n this.scatterStrength = other.scatterStrength;\r\n this.scatterColor = other.scatterColor;\r\n this.transmissionStrength = other.transmissionStrength;\r\n this.transmissionPower = other.transmissionPower;\r\n this.shadowTint = other.shadowTint;\r\n this.brightening = other.brightening;\r\n }\r\n\r\n /** true if vertex normal attribute presents */\r\n get vertexNormal() {\r\n return this.featureUsed<boolean>(SkinMaterial.FEATURE_VERTEX_NORMAL);\r\n }\r\n set vertexNormal(val) {\r\n this.useFeature(SkinMaterial.FEATURE_VERTEX_NORMAL, !!val);\r\n }\r\n\r\n /** true if vertex tangent attribute presents */\r\n get vertexTangent() {\r\n return this.featureUsed<boolean>(SkinMaterial.FEATURE_VERTEX_TANGENT);\r\n }\r\n set vertexTangent(val) {\r\n this.useFeature(SkinMaterial.FEATURE_VERTEX_TANGENT, !!val);\r\n }\r\n\r\n /** Blinn specular exponent. Higher values produce smaller highlights. */\r\n get shininess() {\r\n return this._shininess;\r\n }\r\n set shininess(val) {\r\n const next = Math.max(1, val ?? 1);\r\n if (next !== this._shininess) {\r\n this._shininess = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /** Direct specular strength. Keep this restrained for soft skin. */\r\n get specularStrength() {\r\n return this._specularStrength;\r\n }\r\n set specularStrength(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._specularStrength) {\r\n this._specularStrength = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /** Wrap amount for visible diffuse lighting. */\r\n get diffuseWrap() {\r\n return this._diffuseWrap;\r\n }\r\n set diffuseWrap(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._diffuseWrap) {\r\n this._diffuseWrap = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /** Blend from hard Lambert lighting to wrapped diffuse lighting. */\r\n get diffuseSoftness() {\r\n return this._diffuseSoftness;\r\n }\r\n set diffuseSoftness(val) {\r\n const next = Math.max(0, Math.min(1, val ?? 0));\r\n if (next !== this._diffuseSoftness) {\r\n this._diffuseSoftness = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /**\r\n * Wider wrap that used to shape the post-process scattering source.\r\n *\r\n * @deprecated No longer has any effect. The side buffer now carries the real\r\n * diffuse term rather than a hand-built difference that was nonzero only near\r\n * the terminator, so there is nothing for a second wrap to shape. Use\r\n * {@link SkinSSS.scatterRadius} and the profile's channel radii to control how\r\n * far light travels, and {@link SkinMaterial.diffuseWrap} to shape the ramp.\r\n */\r\n get scatterWrap() {\r\n return this._scatterWrap;\r\n }\r\n set scatterWrap(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._scatterWrap) {\r\n this._scatterWrap = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /**\r\n * Strength of the multiplier written into the SkinSSS side buffer.\r\n *\r\n * @deprecated No longer has any effect. Scaling the side buffer would break\r\n * the identity that makes the diffusion energy conserving - it must equal the\r\n * diffusible term already present in the lit color. Use\r\n * {@link SkinSSS.strength} for the overall amount and {@link SkinSSS.glow} for\r\n * an additive, non-conserving bleed on top.\r\n */\r\n get scatterStrength() {\r\n return this._scatterStrength;\r\n }\r\n set scatterStrength(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._scatterStrength) {\r\n this._scatterStrength = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /**\r\n * Strength of the back-lit transmission term. Requires a `subsurfaceTexture`\r\n * with thickness in the B channel; 0 (the default) disables transmission.\r\n */\r\n get transmissionStrength() {\r\n return this._transmissionStrength;\r\n }\r\n set transmissionStrength(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._transmissionStrength) {\r\n this._transmissionStrength = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /** Exponent of the back-lit transmission falloff. Higher values tighten the glow. */\r\n get transmissionPower() {\r\n return this._transmissionPower;\r\n }\r\n set transmissionPower(val) {\r\n const next = Math.max(1, val ?? 1);\r\n if (next !== this._transmissionPower) {\r\n this._transmissionPower = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /**\r\n * Warm tint for the blurred skin lighting contribution.\r\n *\r\n * @deprecated No longer has any effect; moved to {@link SkinSSS.scatterTint}.\r\n * Tinting here would tint the diffuse in the lit color too, which is what made\r\n * the old look read as a red haze over the whole face. On the post effect the\r\n * tint applies only to the light that actually moved, and per-channel scatter\r\n * radii from the profile already produce the red bleed on their own.\r\n */\r\n get scatterColor(): Immutable<Vector4> {\r\n return this._scatterColor;\r\n }\r\n set scatterColor(val: Immutable<Vector4>) {\r\n if (!val.equalsTo(this._scatterColor)) {\r\n this._scatterColor.set(val);\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /**\r\n * NPR-style shadow tint: the dark end of the diffuse ramp lifts toward this\r\n * color instead of black (black, the default, reproduces plain wrapped\r\n * lambert). A rosy/lavender tint gives the stylized beauty-shot shadow look.\r\n */\r\n get shadowTint(): Immutable<Vector4> {\r\n return this._shadowTint;\r\n }\r\n set shadowTint(val: Immutable<Vector4>) {\r\n if (!val.equalsTo(this._shadowTint)) {\r\n this._shadowTint.set(val);\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n /** Whitening gain applied to the whole diffuse response. 0 (the default) is neutral. */\r\n get brightening() {\r\n return this._brightening;\r\n }\r\n set brightening(val) {\r\n const next = Math.max(0, val ?? 0);\r\n if (next !== this._brightening) {\r\n this._brightening = next;\r\n this.uniformChanged();\r\n }\r\n }\r\n\r\n vertexShader(scope: PBFunctionScope) {\r\n super.vertexShader(scope);\r\n const pb = scope.$builder;\r\n scope.$l.oPos = ShaderHelper.resolveVertexPosition(scope);\r\n scope.$outputs.worldPos = pb.mul(ShaderHelper.getWorldMatrix(scope), pb.vec4(scope.oPos, 1)).xyz;\r\n ShaderHelper.setClipSpacePosition(\r\n scope,\r\n pb.mul(ShaderHelper.getViewProjectionMatrix(scope), pb.vec4(scope.$outputs.worldPos, 1))\r\n );\r\n if (this.vertexNormal) {\r\n scope.$l.oNorm = ShaderHelper.resolveVertexNormal(scope);\r\n scope.$outputs.wNorm = pb.mul(ShaderHelper.getNormalMatrix(scope), pb.vec4(scope.oNorm, 0)).xyz;\r\n if (this.vertexTangent) {\r\n scope.$l.oTangent = ShaderHelper.resolveVertexTangent(scope);\r\n scope.$outputs.wTangent = pb.mul(\r\n ShaderHelper.getNormalMatrix(scope),\r\n pb.vec4(scope.oTangent.xyz, 0)\r\n ).xyz;\r\n scope.$outputs.wBinormal = pb.mul(\r\n pb.cross(scope.$outputs.wNorm, scope.$outputs.wTangent),\r\n scope.oTangent.w\r\n );\r\n }\r\n }\r\n }\r\n\r\n fragmentShader(scope: PBFunctionScope) {\r\n super.fragmentShader(scope);\r\n const pb = scope.$builder;\r\n const that = this;\r\n if (this.needFragmentColorInput()) {\r\n if (this.drawContext.renderPass!.type === RENDER_PASS_TYPE_LIGHT) {\r\n scope.zSkinShininess = pb.float().uniform(2);\r\n scope.zSkinSpecularStrength = pb.float().uniform(2);\r\n scope.zSkinDiffuseWrap = pb.float().uniform(2);\r\n scope.zSkinDiffuseSoftness = pb.float().uniform(2);\r\n scope.zSkinShadowTint = pb.vec4().uniform(2);\r\n scope.zSkinBrightening = pb.float().uniform(2);\r\n // Encodes HDR scatter irradiance into the SkinSSS buffer range when the\r\n // render graph falls back to rgba8unorm (see getSSSLightingTextureFormat).\r\n scope.zSkinScatterEncodeScale = pb.float().uniform(2);\r\n if (this.subsurfaceTexture) {\r\n scope.zSkinTransmissionStrength = pb.float().uniform(2);\r\n scope.zSkinTransmissionPower = pb.float().uniform(2);\r\n }\r\n }\r\n scope.$l.albedo = this.calculateAlbedoColor(scope);\r\n if (this.vertexColor) {\r\n scope.albedo = pb.mul(scope.albedo, this.getVertexColor(scope));\r\n }\r\n if (this.drawContext.renderPass!.type === RENDER_PASS_TYPE_LIGHT) {\r\n const baseLightPass = !this.drawContext.lightBlending;\r\n // TBN[2] is the pre-normal-map geometric normal, needed for shadow\r\n // normal offset bias. Feeding the normal mapped shading normal instead\r\n // would displace the shadow lookup along pore detail.\r\n scope.$l.normalInfo = this.calculateNormalAndTBN(\r\n scope,\r\n scope.$inputs.worldPos,\r\n scope.$inputs.wNorm,\r\n scope.$inputs.wTangent,\r\n scope.$inputs.wBinormal\r\n );\r\n scope.$l.normal = scope.normalInfo.normal;\r\n scope.$l.viewVec = this.calculateViewVector(scope, scope.$inputs.worldPos);\r\n scope.$l.roughness = pb.sqrt(pb.div(2, pb.add(scope.zSkinShininess, 2)));\r\n scope.$l.skinMask = pb.float(1);\r\n scope.$l.skinSoftness = pb.float(0);\r\n scope.$l.skinThickness = pb.float(0);\r\n if (this.subsurfaceTexture) {\r\n scope.$l.subsurfaceTexel = this.sampleSubsurfaceTexture(scope);\r\n scope.skinMask = pb.clamp(scope.subsurfaceTexel.r, 0, 1);\r\n scope.skinSoftness = pb.clamp(scope.subsurfaceTexel.g, 0, 1);\r\n scope.skinThickness = pb.clamp(scope.subsurfaceTexel.b, 0, 1);\r\n }\r\n scope.$l.diffuseLighting = pb.vec3(0);\r\n scope.$l.transmissionLighting = pb.vec3(0);\r\n scope.$l.specularLighting = pb.vec3(0);\r\n scope.$l.NoV = pb.clamp(pb.dot(scope.normal, scope.viewVec), 0, 1);\r\n if (this.needCalculateEnvLight() && baseLightPass) {\r\n scope.$l.envDiffuse = this.getEnvLightIrradiance(scope, scope.normal);\r\n scope.diffuseLighting = pb.add(scope.diffuseLighting, scope.envDiffuse);\r\n scope.$l.reflectVec = this.calculateReflectionVector(scope, scope.normal, scope.viewVec);\r\n scope.$l.envFresnel = pb.add(0.028, pb.mul(0.972, pb.pow(pb.sub(1, scope.NoV), 5)));\r\n scope.specularLighting = pb.add(\r\n scope.specularLighting,\r\n pb.mul(\r\n this.getEnvLightRadiance(scope, scope.reflectVec, scope.roughness),\r\n scope.envFresnel,\r\n scope.zSkinSpecularStrength\r\n )\r\n );\r\n }\r\n this.forEachLight(scope, function (type, posRange, dirCutoff, colorIntensity, extra, shadow) {\r\n this.$l.diffuseScale = pb.float(1);\r\n this.$l.specularScale = pb.float(1);\r\n this.$l.sourceRadiusFactor = pb.float(0);\r\n this.$if(pb.equal(type, LIGHT_TYPE_POINT), function () {\r\n this.diffuseScale = extra.x;\r\n this.specularScale = extra.y;\r\n this.sourceRadiusFactor = pb.div(\r\n extra.z,\r\n pb.max(pb.distance(posRange.xyz, this.$inputs.worldPos), 0.0001)\r\n );\r\n });\r\n this.$l.lightAtten = that.calculateLightAttenuation(\r\n this,\r\n type,\r\n this.$inputs.worldPos,\r\n posRange,\r\n dirCutoff,\r\n extra\r\n );\r\n this.$l.lightDir = that.calculateLightDirection(\r\n this,\r\n type,\r\n this.$inputs.worldPos,\r\n posRange,\r\n dirCutoff\r\n );\r\n this.$l.rawNoL = pb.dot(this.normal, this.lightDir);\r\n this.$l.NoL = pb.clamp(this.rawNoL, 0, 1);\r\n this.$l.NoLWrap = pb.clamp(\r\n pb.div(pb.add(this.rawNoL, this.zSkinDiffuseWrap), pb.add(1, this.zSkinDiffuseWrap)),\r\n 0,\r\n 1\r\n );\r\n // calculateShadow() samples with implicit derivatives (dpdx); WGSL\r\n // requires the call to stay in uniform control flow, so never wrap\r\n // it in a dynamic branch such as NoLWrap > 0.\r\n //\r\n // Diffuse and specular share this term unmodified. An earlier version\r\n // faded it toward 1 around the terminator to hide shadow map acne\r\n // there, but that released the shadow in the wrong band (only ~9% at\r\n // NdotL = 0, by which point the acne is at its worst) and made cast\r\n // shadows dissolve wherever a surface turned away from the light.\r\n // Normal offset bias removes the acne at the source instead.\r\n this.$l.shadowTerm = shadow\r\n ? that.calculateShadow(\r\n this,\r\n this.$inputs.worldPos,\r\n scope.normalInfo.TBN[2],\r\n pb.max(this.NoL, 1e-5)\r\n )\r\n : pb.float(1);\r\n this.$l.lightColor = pb.mul(colorIntensity.rgb, colorIntensity.a, this.lightAtten);\r\n this.$l.diffuseLightColor = pb.mul(this.lightColor, this.shadowTerm);\r\n this.$l.halfVec = pb.normalize(pb.add(this.viewVec, this.lightDir));\r\n this.$l.NoH = pb.clamp(pb.dot(this.normal, this.halfVec), 0, 1);\r\n this.$l.LoH = pb.clamp(pb.dot(this.lightDir, this.halfVec), 0, 1);\r\n this.$l.pointShininess = pb.max(\r\n pb.div(this.zSkinShininess, pb.add(1, pb.mul(this.sourceRadiusFactor, 32))),\r\n 1\r\n );\r\n this.$l.softness = pb.clamp(\r\n pb.add(this.zSkinDiffuseSoftness, pb.mul(this.skinSoftness, 0.35)),\r\n 0,\r\n 1\r\n );\r\n this.$l.NoLVis = pb.mix(this.NoL, this.NoLWrap, this.softness);\r\n // NPR-style diffuse ramp: the dark end lifts toward the shadow tint\r\n // instead of black. A black tint reproduces plain wrapped lambert.\r\n this.$l.diffuseRamp = pb.mix(this.zSkinShadowTint.rgb, pb.vec3(1), this.NoLVis);\r\n this.diffuseLighting = pb.add(\r\n this.diffuseLighting,\r\n pb.mul(this.diffuseLightColor, this.diffuseRamp, this.diffuseScale, 1 / Math.PI)\r\n );\r\n if (that.subsurfaceTexture) {\r\n // Back-lit transmission: thin regions (B channel of the subsurface\r\n // texture) glow when the light faces the camera through the\r\n // surface.\r\n //\r\n // This deliberately uses the unshadowed lightColor. A back-lit\r\n // fragment is self-shadowed by definition - its own front face is\r\n // the occluder - so multiplying by the shadow term would cancel\r\n // exactly the case the term exists to model. The cost is that an\r\n // external caster does not block the glow, which a shadow map\r\n // cannot distinguish from self occlusion anyway.\r\n this.$l.transmission = pb.mul(\r\n pb.pow(\r\n pb.clamp(pb.dot(pb.neg(this.lightDir), this.viewVec), 0, 1),\r\n this.zSkinTransmissionPower\r\n ),\r\n this.skinThickness,\r\n this.zSkinTransmissionStrength\r\n );\r\n this.transmissionLighting = pb.add(\r\n this.transmissionLighting,\r\n pb.mul(this.lightColor, this.transmission, this.diffuseScale, 1 / Math.PI)\r\n );\r\n }\r\n // Normalized Blinn with Schlick Fresnel (skin F0 = 0.028). Specular\r\n // keeps the unfaded shadow term and hard NoL masking.\r\n this.$l.specNormalization = pb.div(pb.add(this.pointShininess, 8), 8 * Math.PI);\r\n this.$l.specFresnel = pb.add(0.028, pb.mul(0.972, pb.pow(pb.sub(1, this.LoH), 5)));\r\n this.$l.specular = pb.mul(\r\n this.lightColor,\r\n this.shadowTerm,\r\n pb.pow(this.NoH, this.pointShininess),\r\n this.specNormalization,\r\n this.specFresnel,\r\n this.zSkinSpecularStrength,\r\n this.specularScale,\r\n this.NoL\r\n );\r\n this.specularLighting = pb.add(this.specularLighting, this.specular);\r\n });\r\n // Whitening: lift the whole diffuse response (direct and ambient).\r\n scope.diffuseLighting = pb.mul(scope.diffuseLighting, pb.add(1, scope.zSkinBrightening));\r\n // Everything that scatters through the surface: the stylized diffuse\r\n // ramp plus back-lit transmission. Specular stays out - it reflects off\r\n // the oil layer and never enters the skin.\r\n scope.$l.diffusible = pb.mul(\r\n scope.albedo.rgb,\r\n pb.add(scope.diffuseLighting, scope.transmissionLighting)\r\n );\r\n scope.$l.litColor = pb.add(scope.diffusible, scope.specularLighting);\r\n // The SkinSSS side buffer carries exactly the diffusible term that is\r\n // also in litColor - untinted and unscaled. That identity is what lets\r\n // the post effect subtract it and add back a diffused version, which is\r\n // energy conserving by construction and leaves the image untouched when\r\n // the effect is disabled. Tinting or scaling here would break it; those\r\n // controls live on SkinSSS instead.\r\n //\r\n // Base and additive light passes both write their own contribution; the\r\n // additive blend (RGB one/one, alpha zero/one) accumulates RGB and keeps\r\n // the mask written by the base pass in alpha.\r\n scope.$l.skinSSS = pb.vec4(pb.mul(scope.diffusible, scope.zSkinScatterEncodeScale), scope.skinMask);\r\n if (\r\n this.drawContext.materialFlags &\r\n (MaterialVaryingFlags.SCENE_STORE_ROUGHNESS | MaterialVaryingFlags.SCENE_STORE_NORMAL)\r\n ) {\r\n scope.$l.outRoughness = pb.vec4(\r\n pb.mul(scope.albedo.rgb, pb.sub(1, scope.roughness), scope.zSkinSpecularStrength),\r\n pb.mul(scope.roughness, ShaderHelper.getCameraRoughnessFactor(scope))\r\n );\r\n this.outputFragmentColor(\r\n scope,\r\n scope.$inputs.worldPos,\r\n pb.vec4(scope.litColor, scope.albedo.a),\r\n scope.outRoughness,\r\n pb.vec4(pb.add(pb.mul(scope.normal, 0.5), pb.vec3(0.5)), 1),\r\n undefined,\r\n undefined,\r\n undefined,\r\n undefined,\r\n false,\r\n scope.skinSSS\r\n );\r\n } else {\r\n this.outputFragmentColor(\r\n scope,\r\n scope.$inputs.worldPos,\r\n pb.vec4(scope.litColor, scope.albedo.a),\r\n undefined,\r\n undefined,\r\n undefined,\r\n undefined,\r\n undefined,\r\n undefined,\r\n false,\r\n scope.skinSSS\r\n );\r\n }\r\n } else {\r\n this.outputFragmentColor(scope, scope.$inputs.worldPos, scope.albedo);\r\n }\r\n } else {\r\n this.outputFragmentColor(scope, scope.$inputs.worldPos, null);\r\n }\r\n }\r\n\r\n applyUniformValues(bindGroup: BindGroup, ctx: DrawContext, pass: number) {\r\n super.applyUniformValues(bindGroup, ctx, pass);\r\n if (this.needFragmentColor(ctx) && ctx.renderPass!.type === RENDER_PASS_TYPE_LIGHT) {\r\n bindGroup.setValue('zSkinShininess', this._shininess);\r\n bindGroup.setValue('zSkinSpecularStrength', this._specularStrength);\r\n bindGroup.setValue('zSkinDiffuseWrap', this._diffuseWrap);\r\n bindGroup.setValue('zSkinDiffuseSoftness', this._diffuseSoftness);\r\n bindGroup.setValue('zSkinShadowTint', this._shadowTint);\r\n bindGroup.setValue('zSkinBrightening', this._brightening);\r\n const ldrSkinSSS = ctx.SkinSSSTexture && ctx.SkinSSSTexture.format === 'rgba8unorm';\r\n bindGroup.setValue('zSkinScatterEncodeScale', ldrSkinSSS ? 1 / SKIN_SSS_LDR_ENCODE_RANGE : 1);\r\n if (this.subsurfaceTexture) {\r\n bindGroup.setValue('zSkinTransmissionStrength', this._transmissionStrength);\r\n bindGroup.setValue('zSkinTransmissionPower', this._transmissionPower);\r\n }\r\n }\r\n }\r\n}\r\n"],"names":["SKIN_SSS_LDR_ENCODE_RANGE","SkinMaterial","applyMaterialMixins","MeshMaterial","mixinLight","mixinVertexColor","mixinTextureProps","FEATURE_VERTEX_NORMAL","defineFeature","FEATURE_VERTEX_TANGENT","_shininess","_specularStrength","_diffuseWrap","_diffuseSoftness","_scatterWrap","_scatterStrength","_scatterColor","_transmissionStrength","_transmissionPower","_shadowTint","_brightening","Vector4","useFeature","skinSSS","clone","other","copyFrom","vertexNormal","vertexTangent","shininess","specularStrength","diffuseWrap","diffuseSoftness","scatterWrap","scatterStrength","scatterColor","transmissionStrength","transmissionPower","shadowTint","brightening","featureUsed","val","next","Math","max","uniformChanged","min","equalsTo","set","vertexShader","scope","pb","$builder","$l","oPos","ShaderHelper","resolveVertexPosition","$outputs","worldPos","mul","getWorldMatrix","vec4","xyz","setClipSpacePosition","getViewProjectionMatrix","oNorm","resolveVertexNormal","wNorm","getNormalMatrix","oTangent","resolveVertexTangent","wTangent","wBinormal","cross","w","fragmentShader","that","needFragmentColorInput","drawContext","renderPass","type","RENDER_PASS_TYPE_LIGHT","zSkinShininess","float","uniform","zSkinSpecularStrength","zSkinDiffuseWrap","zSkinDiffuseSoftness","zSkinShadowTint","zSkinBrightening","zSkinScatterEncodeScale","subsurfaceTexture","zSkinTransmissionStrength","zSkinTransmissionPower","albedo","calculateAlbedoColor","vertexColor","getVertexColor","baseLightPass","lightBlending","normalInfo","calculateNormalAndTBN","$inputs","normal","viewVec","calculateViewVector","roughness","sqrt","div","add","skinMask","skinSoftness","skinThickness","subsurfaceTexel","sampleSubsurfaceTexture","clamp","r","g","b","diffuseLighting","vec3","transmissionLighting","specularLighting","NoV","dot","needCalculateEnvLight","envDiffuse","getEnvLightIrradiance","reflectVec","calculateReflectionVector","envFresnel","pow","sub","getEnvLightRadiance","forEachLight","posRange","dirCutoff","colorIntensity","extra","shadow","diffuseScale","specularScale","sourceRadiusFactor","$if","equal","LIGHT_TYPE_POINT","x","y","z","distance","lightAtten","calculateLightAttenuation","lightDir","calculateLightDirection","rawNoL","NoL","NoLWrap","shadowTerm","calculateShadow","TBN","lightColor","rgb","a","diffuseLightColor","halfVec","normalize","NoH","LoH","pointShininess","softness","NoLVis","mix","diffuseRamp","PI","transmission","neg","specNormalization","specFresnel","specular","diffusible","litColor","materialFlags","MaterialVaryingFlags","SCENE_STORE_ROUGHNESS","SCENE_STORE_NORMAL","outRoughness","getCameraRoughnessFactor","outputFragmentColor","undefined","applyUniformValues","bindGroup","ctx","pass","needFragmentColor","setValue","ldrSkinSSS","SkinSSSTexture","format"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"skin.js","sources":["../../src/material/skin.ts"],"sourcesContent":["import type { BindGroup, PBFunctionScope, PBInsideFunctionScope, RenderStateSet } from '@zephyr3d/device';\nimport { Vector2, Vector3, type Clonable } from '@zephyr3d/base';\nimport { MeshMaterial, applyMaterialMixins } from './meshmaterial';\nimport { mixinLight } from './mixins/lit';\nimport { mixinVertexColor } from './mixins/vertexcolor';\nimport { mixinTextureProps } from './mixins/texture';\nimport { ShaderHelper } from './shader/helper';\nimport type { DrawContext } from '../render';\nimport {\n LIGHT_TYPE_POINT,\n MaterialVaryingFlags,\n RENDER_PASS_TYPE_DEPTH,\n RENDER_PASS_TYPE_LIGHT\n} from '../values';\nimport {\n skinDiffuseBRDF,\n skinDualLobeSpecular,\n skinDualSpecularRoughness,\n skinSpecularEnergyTerms,\n skinTransmission\n} from '../shaders/skin_brdf';\nimport { SSSProfile } from './sssprofile';\nimport { fetchSampler } from '../utility/misc';\n\n/**\n * HDR range that used to be packed into the PostSSS side buffer when the render\n * graph fell back to an 8-bit format.\n *\n * @deprecated The skin scattering source is now recovered from `SceneColor` via\n * the diffuse luminance stored in its alpha channel (matching UE5), so no side\n * buffer and no LDR encoding is involved. Kept for source compatibility; it has\n * no effect on rendering.\n *\n * @public\n */\nexport const SKIN_SSS_LDR_ENCODE_RANGE = 4;\n\n/**\n * Physically-based skin material aligned with UE5's SubsurfaceProfile shading model.\n *\n * @remarks\n * Uses a pre-integrated curvature-dependent diffuse BRDF and dual-lobe GGX specular\n * driven by subsurface profile parameters. The **diffuse** luminance is written to\n * `SceneColor.a` so the {@link PostSSS} post effect can recover the diffusible\n * fraction as `saturate(SceneColor.a / luma(SceneColor.rgb))` — the same spec/diff\n * separation UE5 performs in its SSS Setup and Recombine passes.\n *\n * The optional `subsurfaceTexture` uses R as the skin mask, which gates both the\n * screen-space diffusion and the dual specular lobe. Its other channels are\n * unused: transmission thickness is measured against the light's shadow map by\n * the transmission thickness pass rather than painted, and curvature is not part\n * of this path.\n *\n * @public\n */\nexport class SSSMaterial\n extends applyMaterialMixins(MeshMaterial, mixinLight, mixinVertexColor, mixinTextureProps('subsurface'))\n implements Clonable<SSSMaterial>\n{\n private static readonly FEATURE_VERTEX_NORMAL = this.defineFeature();\n private static readonly FEATURE_VERTEX_TANGENT = this.defineFeature();\n private _roughness: number;\n private _specularF0: number;\n private _transmissionStrength: number;\n private readonly _profile: SSSProfile;\n private readonly _subsurfaceProfileChanged: () => void;\n private readonly _lobeParams: Vector3;\n private readonly _profileTexelSize: Vector2;\n\n constructor() {\n super();\n this._subsurfaceProfileChanged = () => this.uniformChanged();\n // Created here and released in onDispose: the profile holds a row of a\n // 256-entry GPU table, and tying its life to the material's is what keeps\n // those rows from accumulating.\n this._profile = SSSProfile.createOwned();\n this._profile.addChangeListener(this._subsurfaceProfileChanged);\n this._lobeParams = new Vector3();\n this._profileTexelSize = new Vector2();\n this._roughness = 0.5;\n this._specularF0 = 0.04;\n this._transmissionStrength = 1;\n this.useFeature(SSSMaterial.FEATURE_VERTEX_NORMAL, true);\n }\n\n /** Releases the profile's table row along with the material. */\n protected onDispose() {\n super.onDispose();\n this._profile.removeChangeListener(this._subsurfaceProfileChanged);\n this._profile.dispose();\n }\n\n /**\n * Marker used by the forward render graph to enable the PostSSS post effect.\n *\n * @remarks\n * This no longer allocates a side buffer: the scattering source is recovered\n * from `SceneColor` and its diffuse-luminance alpha.\n */\n get postSSS() {\n return true;\n }\n\n /**\n * The profile driving this material's subsurface scattering.\n *\n * @remarks\n * Read-only and never null: the material creates one in its constructor and\n * owns it for life, so edit it in place rather than assigning a new one.\n *\n * ```ts\n * material.subsurfaceProfile.preset = 'jade';\n * material.subsurfaceProfile.meanFreePathDistance = 0.03;\n * ```\n *\n * Per-material ownership is what lets face, ears and lips scatter differently\n * in a single screen-space pass: the material writes its profile's id per pixel\n * and the diffusion looks the parameters up from there. Profiles are therefore\n * not shared - to transfer a look, use {@link SSSProfile.copyFrom}.\n *\n * @public\n */\n get subsurfaceProfile(): SSSProfile {\n return this._profile;\n }\n\n /**\n * Keeps the diffuse luminance written to `SceneColor.a` instead of letting the\n * opaque path overwrite it with 1. {@link PostSSS} needs it to separate the\n * diffusible energy from the specular it must leave untouched.\n */\n protected preservesOpaqueAlpha(ctx: DrawContext): boolean {\n return ctx.renderPass!.type === RENDER_PASS_TYPE_LIGHT;\n }\n\n /**\n * Keeps `SceneColor.a` additive across the multi-pass light loop.\n *\n * @remarks\n * The base implementation uses `zero/one` for alpha so that additive light\n * passes preserve whatever the base pass wrote. That is wrong here: the alpha\n * carries the diffuse luminance of the accumulated RGB, so it has to be summed\n * alongside it — otherwise `SceneColor.a / luma(SceneColor.rgb)` under-reports\n * the diffusible fraction as soon as a second light contributes, and the SSS\n * passes would scatter only the first light's diffuse energy.\n */\n protected updateRenderStates(pass: number, stateSet: RenderStateSet, ctx: DrawContext) {\n super.updateRenderStates(pass, stateSet, ctx);\n if (ctx.lightBlending && ctx.renderPass!.type === RENDER_PASS_TYPE_LIGHT) {\n const blendingState = stateSet.useBlendingState();\n if (blendingState.enabled) {\n blendingState.setBlendFuncAlpha('one', 'one');\n }\n }\n }\n\n clone() {\n const other = new SSSMaterial();\n other.copyFrom(this);\n return other;\n }\n\n copyFrom(other: this) {\n super.copyFrom(other);\n // The values, not the profile: a clone owns its own row of the table, so\n // that disposing either material cannot pull the parameters out from under\n // the other.\n this._profile.copyFrom(other._profile);\n this.vertexNormal = other.vertexNormal;\n this.vertexTangent = other.vertexTangent;\n this.roughness = other.roughness;\n this.specularF0 = other.specularF0;\n this.transmissionStrength = other.transmissionStrength;\n }\n\n get vertexNormal() {\n return this.featureUsed<boolean>(SSSMaterial.FEATURE_VERTEX_NORMAL);\n }\n set vertexNormal(val) {\n this.useFeature(SSSMaterial.FEATURE_VERTEX_NORMAL, !!val);\n }\n\n get vertexTangent() {\n return this.featureUsed<boolean>(SSSMaterial.FEATURE_VERTEX_TANGENT);\n }\n set vertexTangent(val) {\n this.useFeature(SSSMaterial.FEATURE_VERTEX_TANGENT, !!val);\n }\n\n /**\n * GGX base roughness the two specular lobes are derived from.\n *\n * @remarks\n * Defaults to UE5's material default of 0.5. The profile then tightens the\n * narrow lobe and broadens the wide one around this value, so it is the centre\n * of the dual-lobe highlight rather than the roughness of either lobe.\n */\n get roughness() {\n return this._roughness;\n }\n set roughness(val) {\n const next = Math.max(0.045, Math.min(1, val ?? 0.5));\n if (next !== this._roughness) {\n this._roughness = next;\n this.uniformChanged();\n }\n }\n\n /**\n * Fresnel reflectance at normal incidence.\n *\n * @remarks\n * Defaults to 0.04, what UE5's default `Specular` of 0.5 gives through\n * `F0 = 0.08 * Specular`; to port a UE5 material, use that conversion. This is\n * the only control over highlight strength, since a post-multiplier would skew\n * the grazing end of the Fresnel curve and bypass the energy terms, so the\n * specular would stop paying for itself out of the diffuse.\n *\n * The profile's IOR does not feed this: that drives transmission's refraction,\n * while the specular Fresnel stays on the dielectric mapping.\n */\n get specularF0() {\n return this._specularF0;\n }\n set specularF0(val) {\n const next = Math.max(0, Math.min(0.2, val ?? 0.04));\n if (next !== this._specularF0) {\n this._specularF0 = next;\n this.uniformChanged();\n }\n }\n\n /**\n * Overall multiplier on the back-lit transmission.\n *\n * @remarks\n * UE5 has no equivalent - its transmission is fully determined by the profile\n * and the measured thickness - so 1 is the faithful value and this exists only\n * to dial the effect back or push it further.\n *\n * Transmission additionally requires {@link PunctualLight.transmission} on at\n * least one shadow-casting light, since the thickness it needs is measured\n * against that light's shadow map. With no such light this has no effect.\n *\n * @public\n */\n get transmissionStrength() {\n return this._transmissionStrength;\n }\n set transmissionStrength(val) {\n const next = Math.max(0, val ?? 1);\n if (next !== this._transmissionStrength) {\n this._transmissionStrength = next;\n this.uniformChanged();\n }\n }\n\n vertexShader(scope: PBFunctionScope) {\n super.vertexShader(scope);\n const pb = scope.$builder;\n scope.$l.oPos = ShaderHelper.resolveVertexPosition(scope);\n scope.$outputs.worldPos = pb.mul(ShaderHelper.getWorldMatrix(scope), pb.vec4(scope.oPos, 1)).xyz;\n ShaderHelper.setClipSpacePosition(\n scope,\n pb.mul(ShaderHelper.getViewProjectionMatrix(scope), pb.vec4(scope.$outputs.worldPos, 1))\n );\n if (this.vertexNormal) {\n scope.$l.oNorm = ShaderHelper.resolveVertexNormal(scope);\n scope.$outputs.wNorm = pb.mul(ShaderHelper.getNormalMatrix(scope), pb.vec4(scope.oNorm, 0)).xyz;\n if (this.vertexTangent) {\n scope.$l.oTangent = ShaderHelper.resolveVertexTangent(scope);\n scope.$outputs.wTangent = pb.mul(\n ShaderHelper.getNormalMatrix(scope),\n pb.vec4(scope.oTangent.xyz, 0)\n ).xyz;\n scope.$outputs.wBinormal = pb.mul(\n pb.cross(scope.$outputs.wNorm, scope.$outputs.wTangent),\n scope.oTangent.w\n );\n }\n }\n }\n\n fragmentShader(scope: PBFunctionScope) {\n super.fragmentShader(scope);\n const pb = scope.$builder;\n const that = this;\n const lightPass = this.drawContext.renderPass!.type === RENDER_PASS_TYPE_LIGHT;\n // Declared outside `needFragmentColorInput` deliberately: that predicate is\n // false in the prepass for an ordinary opaque material, so a declaration\n // inside it would leave the uniform undefined and the prepass would write id\n // 0 for every skin pixel.\n const depthPassProfileId =\n this.drawContext.renderPass!.type === RENDER_PASS_TYPE_DEPTH && this.drawContext.sssProfileId;\n if (lightPass || depthPassProfileId) {\n scope.zSSSProfileId = pb.float().uniform(2);\n }\n if (this.needFragmentColorInput()) {\n if (lightPass) {\n scope.zSSSRoughness = pb.float().uniform(2);\n scope.zSSSSpecularF0 = pb.float().uniform(2);\n scope.zSSSLobeParams = pb.vec3().uniform(2);\n // Transmission is compiled in only when the thickness it needs exists.\n // The flag is part of the shader's cache key (render/lightpass.ts), and\n // it also guards against the per-light additive path, which has no\n // thickness texture and hands the BxDF a placeholder.\n if (this.drawContext.transmissionThickness) {\n scope.zSSSTransmissionStrength = pb.float().uniform(2);\n // rgba32f, so WebGPU will only accept a non-filtering sampler here;\n // the transmission profile is interpolated by hand for that reason.\n scope.zSSSProfileTex = pb.tex2D().sampleType('unfilterable-float').uniform(2);\n scope.zSSSProfileTexelSize = pb.vec2().uniform(2);\n }\n }\n scope.$l.albedo = this.calculateAlbedoColor(scope);\n if (this.vertexColor) {\n scope.albedo = pb.mul(scope.albedo, this.getVertexColor(scope));\n }\n if (this.drawContext.renderPass!.type === RENDER_PASS_TYPE_LIGHT) {\n const baseLightPass = !this.drawContext.lightBlending;\n scope.$l.normalInfo = this.calculateNormalAndTBN(\n scope,\n scope.$inputs.worldPos,\n scope.$inputs.wNorm,\n scope.$inputs.wTangent,\n scope.$inputs.wBinormal\n );\n scope.$l.normal = scope.normalInfo.normal;\n scope.$l.viewVec = this.calculateViewVector(scope, scope.$inputs.worldPos);\n scope.$l.roughness = scope.zSSSRoughness;\n scope.$l.skinMask = pb.float(1);\n if (this.subsurfaceTexture) {\n scope.$l.subsurfaceTexel = this.sampleSubsurfaceTexture(scope);\n scope.skinMask = pb.clamp(scope.subsurfaceTexel.r, 0, 1);\n }\n scope.$l.diffuseLighting = pb.vec3(0);\n scope.$l.transmissionLighting = pb.vec3(0);\n scope.$l.specularLighting = pb.vec3(0);\n scope.$l.envSpecular = pb.vec3(0);\n scope.$l.NoV = pb.clamp(pb.dot(scope.normal, scope.viewVec), 0.0001, 1);\n // The lobe roughnesses depend only on the material and profile, so they\n // are resolved once rather than per light. The skin mask stands in for\n // UE5's per-pixel subsurface opacity, which is what fades the dual lobe\n // out where the surface stops being skin.\n scope.$l.lobeRoughness = skinDualSpecularRoughness(\n scope,\n scope.roughness,\n scope.skinMask,\n scope.zSSSLobeParams.x,\n scope.zSSSLobeParams.y\n );\n // Multiple-scattering compensation. UE5 takes the average lobe roughness\n // here rather than computing a term per lobe, and applies the result to\n // both the direct and the ambient contribution.\n scope.$l.avgLobeRoughness = pb.mix(\n scope.lobeRoughness.x,\n scope.lobeRoughness.y,\n scope.zSSSLobeParams.z\n );\n scope.$l.energyTerms = skinSpecularEnergyTerms(\n scope,\n scope.avgLobeRoughness,\n scope.NoV,\n scope.zSSSSpecularF0\n );\n // x scales specular back up to unit albedo; 1 - y is the energy left for\n // the diffuse underneath.\n scope.$l.energyConservation = scope.energyTerms.x;\n scope.$l.energyPreservation = pb.sub(1, scope.energyTerms.y);\n // --- Environment lighting ---\n if (this.needCalculateEnvLight() && baseLightPass) {\n scope.$l.envDiffuse = this.getEnvLightIrradiance(scope, scope.normal);\n scope.diffuseLighting = pb.add(scope.diffuseLighting, scope.envDiffuse);\n scope.$l.reflectVec = this.calculateReflectionVector(scope, scope.normal, scope.viewVec);\n // UE5's ReflectionEnvironment:\n //\n // EnergyTerms = ComputeGGXSpecEnergyTerms(GBuffer.Roughness, NoV, SpecularColor)\n // Color.rgb = GatherRadiance(R, GBuffer.Roughness) * EnergyTerms.E\n //\n // Two consequences. The roughness is the raw **material** value, since\n // UE5 applies the dual lobe only in the direct BxDF. And the weight is\n // the directional albedo `E` - the split-sum DFG with multiple-scattering\n // folded in, not a bare Fresnel - which already carries the multi-scatter\n // gain, so it must not also be multiplied by the direct path's `W`.\n scope.$l.envEnergyTerms = skinSpecularEnergyTerms(\n scope,\n scope.roughness,\n scope.NoV,\n scope.zSSSSpecularF0\n );\n scope.envSpecular = pb.mul(\n this.getEnvLightRadiance(scope, scope.reflectVec, scope.roughness),\n scope.envEnergyTerms.y\n );\n }\n this.forEachLight(\n scope,\n function (type, posRange, dirCutoff, colorIntensity, extra, shadow, thickness) {\n this.$l.diffuseScale = pb.float(1);\n this.$l.specularScale = pb.float(1);\n this.$l.sourceRadiusFactor = pb.float(0);\n this.$if(pb.equal(type, LIGHT_TYPE_POINT), function () {\n this.diffuseScale = extra.x;\n this.specularScale = extra.y;\n this.sourceRadiusFactor = pb.div(\n extra.z,\n pb.max(pb.distance(posRange.xyz, this.$inputs.worldPos), 0.0001)\n );\n });\n this.$l.lightAtten = that.calculateLightAttenuation(\n this,\n type,\n this.$inputs.worldPos,\n posRange,\n dirCutoff,\n extra\n );\n this.$l.lightDir = that.calculateLightDirection(\n this,\n type,\n this.$inputs.worldPos,\n posRange,\n dirCutoff\n );\n this.$l.rawNdotL = pb.dot(this.normal, this.lightDir);\n this.$l.NoL = pb.clamp(this.rawNdotL, 0, 1);\n this.$l.VdotL = pb.dot(this.viewVec, this.lightDir);\n // Shadow: pre-integrated BRDF handles NdotL internally, so pass a\n // fixed bias to keep normal-offset stable at the terminator.\n this.$l.shadowTerm = shadow\n ? that.calculateShadow(this, this.$inputs.worldPos, scope.normalInfo.TBN[2], pb.float(0.5))\n : pb.float(1);\n this.$l.lightColor = pb.mul(colorIntensity.rgb, colorIntensity.a, this.lightAtten);\n this.$l.halfVec = pb.normalize(pb.add(this.viewVec, this.lightDir));\n this.$l.NoH = pb.clamp(pb.dot(this.normal, this.halfVec), 0, 1);\n this.$l.VoH = pb.clamp(pb.dot(this.viewVec, this.halfVec), 0, 1);\n // Burley diffuse with the NoL cosine, as UE5's SubsurfaceProfileBxDF\n // evaluates it. The soft terminator is the screen-space diffusion's job;\n // bending this term to fake it double-counts the effect.\n this.$l.skinDiff = skinDiffuseBRDF(this, this.NoV, this.NoL, this.VoH, this.roughness);\n this.diffuseLighting = pb.add(\n this.diffuseLighting,\n pb.mul(this.lightColor, this.shadowTerm, this.skinDiff, this.NoL, this.diffuseScale)\n );\n // Back-lit transmission, after UE5's SubsurfaceProfileBxDF. UE5\n // attenuates by the *transmission* shadow, which is the encoded\n // optical depth itself - so the same value both indexes the profile\n // and scales it, which is why `thickness` appears twice.\n //\n // No surface shadow and no NoL: the light arrives from behind, so the\n // camera-facing surface is shadowed and turned away from it by\n // construction. Applying either would zero out exactly the pixels\n // this term exists for.\n if (that.drawContext.transmissionThickness) {\n this.$l.transmission = skinTransmission(\n this,\n this.zSSSProfileTex,\n this.zSSSProfileTexelSize,\n this.zSSSProfileId,\n thickness,\n this.normal,\n this.viewVec,\n this.lightDir\n );\n this.transmissionLighting = pb.add(\n this.transmissionLighting,\n pb.mul(\n this.lightColor,\n this.transmission,\n thickness,\n this.zSSSTransmissionStrength,\n this.diffuseScale\n )\n );\n }\n // Dual-lobe GGX specular, with the NoL cosine UE5 applies alongside it.\n this.$l.spec = skinDualLobeSpecular(\n this,\n this.NoH,\n this.NoV,\n this.NoL,\n this.VoH,\n this.lobeRoughness,\n this.zSSSLobeParams.z,\n this.zSSSSpecularF0\n );\n this.specularLighting = pb.add(\n this.specularLighting,\n pb.mul(this.lightColor, this.shadowTerm, this.spec, this.NoL, this.specularScale)\n );\n }\n );\n // --- Assemble ---\n //\n // UE5 applies the energy terms to the accumulated lighting rather than per\n // light: the diffuse loses what the specular layer above it reflected, and\n // the specular gains back the energy single-scattering GGX dropped. The\n // transmission is left alone, since it enters from behind the surface and\n // never passes through that specular layer.\n //\n // The environment specular stays outside that multiply: it was already\n // weighted by the directional albedo `E` when gathered, which carries the\n // multiple-scattering gain, so applying `W` on top would count it twice.\n // UE5 keeps the same split.\n //\n // The albedo multiply has to cover the transmission as well, because the\n // baked profile carries only the falloff shape - UE5 supplies the base\n // colour in its recombine pass instead, and this engine supplies it here.\n //\n // The transmission then rides into `diffLum` below and so is diffused\n // along with the rest. That is deliberate: UE5 passes it as the\n // `ScatterableLight` argument of `LightAccumulator_AddSplit`, the same\n // slot the diffuse uses.\n scope.$l.diffusible = pb.mul(\n scope.albedo.rgb,\n pb.add(pb.mul(scope.diffuseLighting, scope.energyPreservation), scope.transmissionLighting)\n );\n scope.specularLighting = pb.add(\n pb.mul(scope.specularLighting, scope.energyConservation),\n scope.envSpecular\n );\n scope.$l.litColor = pb.add(scope.diffusible, scope.specularLighting);\n // SceneColor.a = diffuse luminance, UE5's spec/diff separation mechanism:\n // the SSS passes recover the diffusible fraction as\n // `saturate(SceneColor.a / luma(SceneColor.rgb))`, so the alpha must carry\n // the *diffuse* luminance, not the total.\n scope.$l.diffLum = pb.dot(scope.diffusible, pb.vec3(0.2126, 0.7152, 0.0722));\n // Surface data for the SSS passes: rgb = world normal, a = subsurface\n // opacity.\n //\n // SceneColor.a cannot serve as the mask: every opaque material writes 1\n // there, so gating on it would make the diffusion treat the background and\n // the eyes as skin.\n //\n // The normal rides along so the diffusion can weight taps by how far the\n // surface has turned away. Carrying it here rather than reading SceneNormal\n // makes scattering independent of whether that optional MRT is enabled.\n //\n // The alpha is UE5's Opacity input unmodified - a continuous 0..1 mask\n // where 0 is no scattering and 1 is full. The profile id travels\n // separately, out of the depth prepass, since one channel cannot carry a\n // table row and a weight at once.\n scope.$l.postSSSMask = pb.vec4(pb.add(pb.mul(scope.normal, 0.5), pb.vec3(0.5)), scope.skinMask);\n if (\n this.drawContext.materialFlags &\n (MaterialVaryingFlags.SCENE_STORE_ROUGHNESS | MaterialVaryingFlags.SCENE_STORE_NORMAL)\n ) {\n scope.$l.outRoughness = pb.vec4(\n pb.mul(scope.albedo.rgb, pb.sub(1, scope.roughness)),\n pb.mul(scope.roughness, ShaderHelper.getCameraRoughnessFactor(scope))\n );\n this.outputFragmentColor(\n scope,\n scope.$inputs.worldPos,\n pb.vec4(scope.litColor, scope.diffLum),\n scope.outRoughness,\n pb.vec4(pb.add(pb.mul(scope.normal, 0.5), pb.vec3(0.5)), 1),\n undefined,\n undefined,\n undefined,\n undefined,\n false,\n scope.skinSSSMask\n );\n } else {\n this.outputFragmentColor(\n scope,\n scope.$inputs.worldPos,\n pb.vec4(scope.litColor, scope.diffLum),\n undefined,\n undefined,\n undefined,\n undefined,\n undefined,\n undefined,\n false,\n scope.skinSSSMask\n );\n }\n } else {\n this.outputFragmentColor(scope, scope.$inputs.worldPos, scope.albedo);\n }\n } else {\n this.outputFragmentColor(scope, scope.$inputs.worldPos, null);\n }\n }\n\n /**\n * The profile id the depth prepass writes for this material.\n *\n * @remarks\n * Overrides {@link MeshMaterial.getDepthPassProfileId}. The uniform is declared\n * in {@link SSSMaterial.fragmentShader} for the prepass as well as the light\n * pass, and bound below.\n */\n protected getDepthPassProfileId(scope: PBInsideFunctionScope) {\n return scope.zSSSProfileId;\n }\n\n applyUniformValues(bindGroup: BindGroup, ctx: DrawContext, pass: number) {\n super.applyUniformValues(bindGroup, ctx, pass);\n const lightPass = ctx.renderPass!.type === RENDER_PASS_TYPE_LIGHT;\n const depthPassProfileId = ctx.renderPass!.type === RENDER_PASS_TYPE_DEPTH && ctx.sssProfileId;\n // Not gated on needFragmentColor: the prepass declares this uniform for\n // every skin material, including the opaque ones that predicate excludes.\n if (lightPass || depthPassProfileId) {\n bindGroup.setValue('zSSSProfileId', this._profile.encodedId);\n }\n if (!this.needFragmentColor(ctx) || !lightPass) {\n return;\n }\n bindGroup.setValue('zSSSRoughness', this._roughness);\n bindGroup.setValue('zSSSSpecularF0', this._specularF0);\n const profile = this._profile;\n bindGroup.setValue(\n 'zSSSLobeParams',\n this._lobeParams.setXYZ(profile.roughness0, profile.roughness1, profile.lobeMix)\n );\n if (ctx.transmissionThickness) {\n bindGroup.setValue('zSSSTransmissionStrength', this._transmissionStrength);\n const table = SSSProfile.getTable(ctx.device);\n if (table) {\n bindGroup.setTexture('zSSSProfileTex', table, fetchSampler('clamp_nearest_nomip'));\n this._profileTexelSize.setXY(1 / SSSProfile.tableColumns, 1 / SSSProfile.tableRows);\n bindGroup.setValue('zSSSProfileTexelSize', this._profileTexelSize);\n }\n }\n }\n}\n"],"names":["SKIN_SSS_LDR_ENCODE_RANGE","SSSMaterial","applyMaterialMixins","MeshMaterial","mixinLight","mixinVertexColor","mixinTextureProps","FEATURE_VERTEX_NORMAL","defineFeature","FEATURE_VERTEX_TANGENT","_roughness","_specularF0","_transmissionStrength","_profile","_subsurfaceProfileChanged","_lobeParams","_profileTexelSize","uniformChanged","SSSProfile","createOwned","addChangeListener","Vector3","Vector2","useFeature","onDispose","removeChangeListener","dispose","postSSS","subsurfaceProfile","preservesOpaqueAlpha","ctx","renderPass","type","RENDER_PASS_TYPE_LIGHT","pass","stateSet","updateRenderStates","lightBlending","blendingState","useBlendingState","enabled","setBlendFuncAlpha","clone","other","copyFrom","vertexNormal","vertexTangent","roughness","specularF0","transmissionStrength","featureUsed","val","next","Math","max","min","vertexShader","scope","pb","$builder","$l","oPos","ShaderHelper","resolveVertexPosition","$outputs","worldPos","mul","getWorldMatrix","vec4","xyz","setClipSpacePosition","getViewProjectionMatrix","oNorm","resolveVertexNormal","wNorm","getNormalMatrix","oTangent","resolveVertexTangent","wTangent","wBinormal","cross","w","fragmentShader","that","lightPass","drawContext","depthPassProfileId","RENDER_PASS_TYPE_DEPTH","sssProfileId","zSSSProfileId","float","uniform","needFragmentColorInput","zSSSRoughness","zSSSSpecularF0","zSSSLobeParams","vec3","transmissionThickness","zSSSTransmissionStrength","zSSSProfileTex","tex2D","sampleType","zSSSProfileTexelSize","vec2","albedo","calculateAlbedoColor","vertexColor","getVertexColor","baseLightPass","normalInfo","calculateNormalAndTBN","$inputs","normal","viewVec","calculateViewVector","skinMask","subsurfaceTexture","subsurfaceTexel","sampleSubsurfaceTexture","clamp","r","diffuseLighting","transmissionLighting","specularLighting","envSpecular","NoV","dot","lobeRoughness","skinDualSpecularRoughness","x","y","avgLobeRoughness","mix","z","energyTerms","skinSpecularEnergyTerms","energyConservation","energyPreservation","sub","needCalculateEnvLight","envDiffuse","getEnvLightIrradiance","add","reflectVec","calculateReflectionVector","envEnergyTerms","getEnvLightRadiance","forEachLight","posRange","dirCutoff","colorIntensity","extra","shadow","thickness","diffuseScale","specularScale","sourceRadiusFactor","$if","equal","LIGHT_TYPE_POINT","div","distance","lightAtten","calculateLightAttenuation","lightDir","calculateLightDirection","rawNdotL","NoL","VdotL","shadowTerm","calculateShadow","TBN","lightColor","rgb","a","halfVec","normalize","NoH","VoH","skinDiff","skinDiffuseBRDF","transmission","skinTransmission","spec","skinDualLobeSpecular","diffusible","litColor","diffLum","postSSSMask","materialFlags","MaterialVaryingFlags","SCENE_STORE_ROUGHNESS","SCENE_STORE_NORMAL","outRoughness","getCameraRoughnessFactor","outputFragmentColor","undefined","skinSSSMask","getDepthPassProfileId","applyUniformValues","bindGroup","setValue","encodedId","needFragmentColor","profile","setXYZ","roughness0","roughness1","lobeMix","table","getTable","device","setTexture","fetchSampler","setXY","tableColumns","tableRows"],"mappings":"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"}
|