Unified GSplat Picking Support#8421
Merged
Merged
Conversation
Contributor
There was a problem hiding this comment.
Pull request overview
Adds GPU picking support for Gaussian Splats in unified rendering by introducing a shared ID allocation path and wiring those IDs through the work buffer into the pick pass, so Picker can return GSplatComponent alongside MeshInstance.
Changes:
- Introduces centralized
PickerIdgenerator and migratesMeshInstance/GSplatComponentto use it. - Adds optional
pcIdwork-buffer stream (GSplatParams.id) and shaders to write/read that ID for pick rendering. - Extends picker render pass + examples to support unified gsplat picking and maintains a legacy picking example.
Reviewed changes
Copilot reviewed 21 out of 25 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
| src/scene/shader-lib/wgsl/chunks/gsplat/vert/gsplat.js | Passes per-splat/component pick ID through a flat varying during pick pass. |
| src/scene/shader-lib/wgsl/chunks/gsplat/frag/gsplatCopyToWorkbuffer.js | Writes uId into the pcId stream when enabled. |
| src/scene/shader-lib/wgsl/chunks/gsplat/frag/gsplat.js | Encodes vPickId into pick output for unified gsplat pick pass. |
| src/scene/shader-lib/wgsl/chunks/common/frag/pick.js | Adds encodePickOutput(id) and makes meshInstanceId optional via PICK_CUSTOM_ID. |
| src/scene/shader-lib/glsl/chunks/gsplat/vert/gsplat.js | GLSL equivalent: passes flat vPickId during pick pass. |
| src/scene/shader-lib/glsl/chunks/gsplat/frag/gsplatCopyToWorkbuffer.js | GLSL equivalent: writes uId into pcId stream. |
| src/scene/shader-lib/glsl/chunks/gsplat/frag/gsplat.js | GLSL equivalent: encodes vPickId during pick pass when unified ID enabled. |
| src/scene/shader-lib/glsl/chunks/common/frag/pick.js | GLSL equivalent: adds encodePickOutput(id) and PICK_CUSTOM_ID gating. |
| src/scene/picker-id.js | Adds centralized picker ID allocator. |
| src/scene/mesh-instance.js | Migrates mesh instance IDs to PickerId.get(). |
| src/scene/gsplat-unified/gsplat-work-buffer.js | Enables GSPLAT_ID define when pcId stream exists so copy shader writes IDs. |
| src/scene/gsplat-unified/gsplat-work-buffer-render-pass.js | Sets uId per placement when rendering into the work buffer. |
| src/scene/gsplat-unified/gsplat-renderer.js | Enables unified-ID shader defines (GSPLAT_UNIFIED_ID, PICK_CUSTOM_ID) when pcId exists. |
| src/scene/gsplat-unified/gsplat-placement.js | Adds placement id and propagates it through placement creation / inheritance. |
| src/scene/gsplat-unified/gsplat-params.js | Adds GSplatParams.id to append pcId stream (R32U) to the work buffer format. |
| src/scene/gsplat-unified/gsplat-info.js | Carries placement ID into render info for shader uniform setup. |
| src/framework/graphics/render-pass-picker.js | Extends picker pass to map placement IDs to GSplatComponent. |
| src/framework/graphics/picker.js | Updates picker documentation/types to return `MeshInstance |
| src/framework/components/gsplat/component.js | Allocates a stable component pick ID and passes it into unified placement creation. |
| examples/thumbnails/gaussian-splatting_picking_small.webp | Adds updated thumbnail for unified picking example. |
| examples/thumbnails/gaussian-splatting_picking_large.webp | Adds updated thumbnail for unified picking example. |
| examples/thumbnails/gaussian-splatting-legacy_picking_small.webp | Adds thumbnail for legacy picking example. |
| examples/thumbnails/gaussian-splatting-legacy_picking_large.webp | Adds thumbnail for legacy picking example. |
| examples/src/examples/gaussian-splatting/picking.example.mjs | Updates example to enable unified mode + scene.gsplat.id and handle GSplatComponent results. |
| examples/src/examples/gaussian-splatting-legacy/picking.example.mjs | Adds a separate legacy (non-unified) gsplat picking example. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| } | ||
|
|
||
| // Enable gsplat ID for unified picking | ||
| app.scene.gsplat.id = true; |
Contributor
There was a problem hiding this comment.
Oh, I hadn't noticed this property before. Couple of things:
- I still feel like configuration props for rendering gsplats should live on the
GSplatComponentSystem. idsuggests to me it's an actual ID (e.g. a GUID or number). So naming feels weird. Something likeenableIdswould be better IMHO.
Contributor
Author
There was a problem hiding this comment.
- perhaps.
- will do, great point.
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.
Summary
PickerIdclass for consistent ID allocation across pickable objectsPickerclass to returnGSplatComponentfor unified gsplats alongsideMeshInstancefor other objectsChanges
Centralized ID Generation
PickerIdclass (src/scene/picker-id.js) with staticget()method for allocating unique IDsMeshInstancenow usesPickerId.get()instead of internal counterGSplatComponentallocates its own ID at construction, passed to placementGSplat Unified Picking
GSplatParams.idproperty enables per-component ID storage in the work bufferpcIdstream (R32U format) is added to the work buffer formatPicker Updates
Picker.getSelection()andgetSelectionAsync()now return(MeshInstance | GSplatComponent)[]Examples
gaussian-splatting/picking.example.mjsto demonstrate unified pickinggaussian-splatting-legacy/picking.example.mjsfor non-unified picking referencePublic API Changes
New:
GSplatParams.idOnce enabled, cannot be disabled. The ID stream persists for the lifetime of the app.
Updated:
Picker.getSelectionAsync()/Picker.getSelection()Return type changed from
MeshInstance[]to(MeshInstance | GSplatComponent)[]: