feat(gsplat): apply render-stage modify hooks in the hybrid renderer#8822
Merged
Conversation
The render-stage material customization (app.scene.gsplat.material's gsplatModifyVS chunk: modifySplatCenter / modifySplatRotationScale / modifySplatColor, plus defines and uniforms) now also applies to the hybrid (GPU-sorted) renderer, matching the quad renderer. Previously these hooks were ignored in the hybrid path because projection happens in the projector compute pass rather than the vertex shader. - Inject the modify hooks into the projector compute (compute-gsplat-project-common applies center + rotation/scale before computeSplatCov; compute-gsplat-projector applies color after getColor), reusing the existing gsplatModifyVS chunk. - The projector reflects user-declared uniforms/textures from the modify chunk into its own bind group (via compute WGSL reflection) and forwards material params and defines, rebuilding the compute variants only when the chunk/defines change. - Add the no-op gsplatModifyVS chunk to the compute local renderer (which shares projectSplatCommon) so it keeps compiling. - Add Material#definesKey: a cached, lazily-rebuilt content key for material defines (invalidated by setDefine / copy), used to detect customization changes cheaply without scanning the defines map every frame.
Contributor
There was a problem hiding this comment.
Pull request overview
Extends the hybrid (GPU-sorted) gsplat renderer's projector compute to honor the same render-stage gsplatModifyVS hooks (modifySplatCenter, modifySplatRotationScale, modifySplatColor) that the quad renderer already uses from app.scene.gsplat.material. Previously these were ignored on the hybrid path because projection happens in a compute pass. Variants are rebuilt only when the user chunk / defines actually change, leveraging a new cached Material#definesKey.
Changes:
- WGSL projector compute chunks include
gsplatModifyVS/gsplatHelpersVSand call the modify hooks at the equivalent points togsplatCorner/gsplatVS(with the same(w,x,y,z)↔(x,y,z,w)quaternion swap). GSplatProjectorreads the user's WGSL modify chunk and defines from the render material, merges them into the compute (skipping projector-internal defines), forwards material parameters, and adds a debug-only warning when reflected user resource names collide with projector bindings.- New
Material#definesKeygetter — cached, lazily-rebuilt content key fordefines, invalidated bysetDefineandcopy, used by the projector to cheaply detect define changes.
Reviewed changes
Copilot reviewed 7 out of 7 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
src/scene/shader-lib/wgsl/chunks/gsplat/compute-gsplat-project-common.js |
Calls modifySplatCenter then modifySplatRotationScale before computeSplatCov, with the yzwx/wxyz quaternion swap to match the quad path. |
src/scene/shader-lib/wgsl/chunks/gsplat/compute-gsplat-projector.js |
Includes gsplatHelpersVS/gsplatModifyVS and applies modifySplatColor (post AA compensation) on both pick and non-pick branches. |
src/scene/shader-lib/wgsl/chunks/gsplat/compute-gsplat-local-tile-count.js |
Adds default gsplatModifyVS include so the local-tile-count compute (sharing projectSplatCommon) keeps compiling. |
src/scene/gsplat-unified/gsplat-compute-local-renderer.js |
Wires the no-op default modify chunk into the local compute renderer's includes. |
src/scene/gsplat-unified/gsplat-projector.js |
Adds _updateMaterial change-detection, injects user modify chunk/defines/parameters into projector compute, and a debug-only collision check against reserved bindings/uniforms. |
src/scene/gsplat-unified/gsplat-manager.js |
Forwards gsplat.material to the projector dispatch params. |
src/scene/materials/material.js |
Adds _definesKey cache + lazy definesKey getter, invalidated by setDefine and copy; doc note discourages direct mutation. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Render-stage material customization — the
gsplatModifyVSchunk (modifySplatCenter/modifySplatRotationScale/modifySplatColor) plus defines and uniforms set onapp.scene.gsplat.material— now applies to the hybrid (GPU-sorted) renderer, matching the quad renderer. Previously these hooks were silently ignored in the hybrid path because projection happens in the projector compute pass rather than the vertex shader. Builds on the compute WGSL reflection from #8821 (which handles the user-declared uniforms/textures).Changes:
compute-gsplat-project-commonappliesmodifySplatCenterandmodifySplatRotationScalebeforecomputeSplatCov(mirroringgsplatCorner's quaternion handling);compute-gsplat-projectorappliesmodifySplatColoraftergetColor. Reuses the existinggsplatModifyVSchunk +gsplatHelpersVS.gsplatModifyVSchunk and defines, reflects its declared uniforms/textures into the projector's own bind group, and forwards material parameters. Compute variants are rebuilt only when the chunk/defines change (not per frame). A debug-only check (once per compile) reports user resource names that collide with projector-internal bindings.gsplatModifyVS(it sharesprojectSplatCommon), so it keeps compiling.Material#definesKey— a cached, lazily-rebuilt content key for material defines, invalidated bysetDefine/copy. Lets change-detection avoid scanning the defines map every frame (mirrorsShaderChunkMap.key); generally reusable.API Changes:
Material#definesKey(getter,@ignore). No breaking changes.Notes:
copyMaterialSettings). The geometry/color modification is fully handled in the projector compute and baked into the projection cache, and the engine-side fragment inputs (alphaClip, colorRamp, fog, overdraw) are already synced. The only thing such a copy would add is fragment-shader customization (overridinggsplatPS, or fragment-only defines/params), which is not a supported gsplat customization point today (the only exposed render-stage hook isgsplatModifyVS). If gsplat fragment-shader customization is ever introduced, the hybrid renderer would need acopyMaterialSettings-equivalent at that point.