Add masks support to all Gaussian render methods#480
Open
swahtz wants to merge 5 commits intoopenvdb:mainfrom
Open
Add masks support to all Gaussian render methods#480swahtz wants to merge 5 commits intoopenvdb:mainfrom
masks support to all Gaussian render methods#480swahtz wants to merge 5 commits intoopenvdb:mainfrom
Conversation
Signed-off-by: Jonathan Swartz <jonathan@jswartz.info>
- Introduced two new functions: `_pixel_mask_to_tile_mask` for converting per-pixel boolean masks to per-tile masks, and `_apply_pixel_mask` for applying these masks to rendered features and alphas. - Updated `GaussianSplat3d` methods to utilize the new masking functionality, allowing for optional per-pixel boolean masks during rendering. - Enhanced unit tests to validate the new pixel mask behavior, ensuring correct integration with existing rendering processes. Signed-off-by: Jonathan Swartz <jonathan@jswartz.info>
Contributor
There was a problem hiding this comment.
Pull request overview
This PR adds comprehensive masks and backgrounds support to all Gaussian splatting render methods, enabling per-pixel masking for dense renders and per-tile masking for sparse/jagged renders. Previously, only render_images_from_world supported these parameters.
Changes:
- Extended all render APIs (dense, sparse, jagged) to accept optional
masksandbackgroundsparameters - Implemented a two-stage masking approach for dense methods: conservative per-tile masking for early-out optimization, followed by precise per-pixel masking
- Added comprehensive test coverage verifying correct rendering behavior and gradient flow with masks
Reviewed changes
Copilot reviewed 14 out of 14 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
tests/unit/test_gaussian_splat_3d.py |
Added 13 new tests covering all render paths with masks: dense (pixel masks), sparse (tile masks), and jagged (tile masks) |
src/python/GaussianSplatBinding.cpp |
Added masks parameter bindings to 8 render methods (dense, sparse, jagged) |
src/fvdb/detail/ops/gsplat/GaussianRasterizeForward.h |
Added masks parameter to sparse forward dispatch signature |
src/fvdb/detail/ops/gsplat/GaussianRasterizeForward.cu |
Threaded masks through sparse forward dispatch implementations (CUDA, CPU, PrivateUse1) |
src/fvdb/detail/ops/gsplat/GaussianRasterizeBackward.h |
Added masks parameter to both dense and sparse backward dispatch signatures |
src/fvdb/detail/ops/gsplat/GaussianRasterizeBackward.cu |
Threaded masks through all backward dispatch implementations |
src/fvdb/detail/autograd/GaussianRasterizeSparse.h |
Added masks parameter to sparse rasterize autograd forward signature |
src/fvdb/detail/autograd/GaussianRasterizeSparse.cpp |
Implemented save/restore for optional masks and backgrounds in sparse autograd |
src/fvdb/detail/autograd/GaussianRasterize.h |
Added masks parameter to dense rasterize autograd forward signature |
src/fvdb/detail/autograd/GaussianRasterize.cpp |
Implemented save/restore for optional masks and backgrounds in dense autograd |
src/fvdb/GaussianSplat3d.h |
Added masks parameter to all public render methods and internal implementation methods |
src/fvdb/GaussianSplat3d.cpp |
Threaded masks through all render implementations; removed unused renderImpl method |
fvdb/gaussian_splatting.py |
Added helper functions for mask conversion and application; updated all render methods to support per-pixel masks (dense) or per-tile masks (sparse) |
fvdb/__init__.py |
Added masks parameter to gaussian_render_jagged wrapper |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Signed-off-by: Jonathan Swartz <jonathan@jswartz.info>
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.
Add
masksandbackgroundssupport to all Gaussian splatting render methodsCloses #469
Summary
Plumb
masksandbackgroundsthrough all render paths. Themasks(per-tile[C, tileH, tileW]bool) andbackgrounds(per-camera color) optional parameters were only supported on a subset of render methods. This PR adds them to all dense, sparse, and jagged render functions across the full stack: CUDA dispatch, autograd, C++ API, Python bindings, and Python wrappers.Expose a per-pixel mask API on dense render methods. Users now pass a per-pixel boolean mask of shape
[C, H, W]to the 5 dense render methods (render_images,render_depths,render_images_and_depths,render_images_from_world,render_from_projected_gaussians). Internally, the Python wrapper derives a conservative per-tile mask viaF.max_pool2d(a tile is rendered if any of its pixels are unmasked) and passes it to the C++ kernel for the existing tile-level early-out optimization. After rendering, a differentiable per-pixel mask is applied to the output so masked pixels receive the background color and zero alpha, with correct gradient flow.Add comprehensive tests. A new
TestGaussianRenderMaskstest class covers all render paths: all-ones mask matches unmasked output, all-zeros mask produces background, backward pass with masks produces nonzero gradients, and all-zeros mask produces zero gradients. Tests cover dense (per-pixel masks), sparse (per-tile masks), and jagged (per-tile masks) paths.Test plan
Verifies:
render_imageswith all-ones pixel mask matches no-mask outputrender_imageswith all-zeros pixel mask produces backgroundrender_imagesbackward with masks produces nonzero gradientsrender_imageswith all-zeros mask produces zero gradientsrender_depthswith all-zeros pixel mask produces backgroundrender_images_and_depthswith all-zeros pixel mask produces backgroundrender_from_projected_gaussianswith all-ones and all-zeros pixel maskssparse_render_imageswith tile masks and backgroundssparse_render_imagesbackward with tile maskssparse_render_depthswith tile masks and backgroundssparse_render_images_and_depthswith tile masks and backgroundsgaussian_render_jaggedwith all-ones and all-zeros tile masks