Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

ringsplat

Equirectangular 360 panorama → 3D Gaussian Splat, end-to-end on Apple Silicon (MPS).

A thin pipeline around Apple's ml-sharp that:

  1. Crops a horizontal ring of perspective faces from an equirectangular image,
  2. Runs SHARP per-face — each in a fresh subprocess, so MPS GPU memory is returned to the OS between faces (the trick that sidesteps the IOGPUDeviceShmem allocation failure you hit on naive multi-face setups),
  3. Rotates each face's splats into a shared world frame (yaw on Y),
  4. Optionally applies a Voronoi yaw clip to drop face-to-face overlap,
  5. Concatenates everything into a single .ply.

No DA360 alignment, no SH rotation, no fancy refinement — just enough to get a viewable 360 splat from a single panorama with a stock M-series Mac.

Why

Existing 360 → splat tools (e.g. SPAG4d) assume CUDA. On Apple Silicon they either fail to install or hit MPS shared-memory exhaustion the moment SHARP loads while DA360 is still resident — even after empty_cache. ringsplat keeps the per-face inference fully isolated as a child process, so the allocator state is never carried across faces.

Requirements

  • macOS on Apple Silicon (M1/M2/M3/M4) with Metal — also works on Linux/CUDA.
  • Python ≥ 3.11.
  • Apple ml-sharp installed separately. The sharp CLI must be invocable (e.g. ~/ml-sharp/venv/bin/sharp).
# install ml-sharp (one-time)
git clone https://github.com/apple/ml-sharp.git
cd ml-sharp
python3.11 -m venv venv
source venv/bin/activate
pip install -r requirements.txt
sharp --help    # confirm

Install

git clone https://github.com/DECK6/ringsplat.git
cd ringsplat
python3.11 -m venv .venv
source .venv/bin/activate
pip install -e .

Usage

ringsplat \
  --input  panorama_2to1.png \
  --output scene.ply \
  --side-count 6 \
  --face-size 512 \
  --fov-deg 60 \
  --device mps \
  --scale-align --anchor-percentile 99 \
  --radius-cutoff 99.5 \
  --clip-yaw \
  --legacy-pointcloud \
  --sharp-bin /path/to/ml-sharp/venv/bin/sharp

The flags above are the recommended starting point. side-count=6 × fov=60° exactly tiles 360° with zero overlap — SHARP's default 30 mm focal assumption is ~63°, so 60° fits cleanly inside each face and adjacent faces meet without ghosting. The alignment trio (scale-align + anchor-percentile 99

  • radius-cutoff 99.5) keeps the merged splat round when seen from above.
Flag Default Notes
--side-count 8 4 / 6 / 8 horizontal faces — 6 recommended
--face-size 512 per-face square resolution
--fov-deg 360/side_count * 1.2 use 60 with side-count 6 for zero-overlap tiling under SHARP's 30 mm focal
--device mps mps / cuda / cpu
--scale-align off rescale faces to share an anchor radius
--anchor-percentile 50 50 = median; 99 = outer envelope
--radius-cutoff off drop splats past this radius percentile (e.g. 99.5)
--clip-yaw off hard Voronoi yaw clip on overlap
--legacy-pointcloud off add r/g/b/a + nx/ny/nz so non-GS viewers (TouchDesigner Point File In, MeshLab) show color
--workdir ./work_sharp360 face crops + per-face plys
--keep-work off don't delete --workdir after run

--sharp-bin can also come from RINGSPLAT_SHARP_BIN env var, or any sharp on PATH.

Output

A single binary little-endian .ply with the SHARP vertex properties:

x, y, z, f_dc_0, f_dc_1, f_dc_2, opacity, scale_0..2, rot_0..3

Drop it into any 3DGS viewer (e.g. SuperSplat, gsplat, TouchDesigner with a GLSL renderer).

Performance (Apple M4 Pro, 16-core GPU)

side_count face_size total time
4 512 ~50 s
6 512 ~95 s (recommended)
8 512 ~120 s

About 80% of the wall time is SHARP itself; the rest is subprocess startup + crop/merge.

Limitations

  • Horizontal ring only — top/bottom (zenith/nadir) is not covered. Add pitch ±60° faces in a future version if you need full sphere coverage.
  • No inter-face depth alignment — each face is metric per SHARP's own estimate. Visible parallax mismatch can appear on close objects in overlap regions; raise --side-count or enable --clip-yaw to mitigate.
  • DC-only color (SHARP outputs f_dc_*, no f_rest_*), so view-dependent shading is flat — yaw rotation is therefore lossless.
  • Quaternion rotation is composed correctly for the rotation channel, but SH rotation is not applied (irrelevant while ml-sharp ships SH degree 0).

License

MIT (this repo). ml-sharp is governed by Apple's own license — installing and running it is your responsibility.

About

Equirectangular 360 panorama → 3D Gaussian Splat, end-to-end on Apple Silicon (MPS)

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages