Capitolo 8 — Formati di esportazione


Cosa mostra l'immagine (2 991 gaussiane, SH grado 3, bouquet sintetico Blender come set di test IP-clean): Le indicazioni di dimensione sotto ogni scheda di formato vengono calcolate in tempo reale dal conteggio attuale delle gaussiane e dall'overhead del formato — non sono hard-coded. Da 2 991 gaussiane (SH grado 3) nascono così 742 KB di PLY, 74 KB di SPZ (fattore ~10× più piccolo grazie alla quantizzazione), 708 KB di glTF (con l'estensione KHR_gaussian_splatting, quindi quasi equivalente al PLY), 96 KB di .splat (formato compresso a 24 byte per gaussiana). Orbit Video mostra "~Zero KB", perché la dimensione è nota solo dopo la codifica MP4. Web Viewer (133 KB) raggruppa un file HTML autonomo con viewer WebGL incorporato e dati splat compressi — più grande del puro .splat per l'overhead del viewer. La cronologia delle esportazioni a destra elenca l'esportazione PLY già completata ("training_20260527T211321Z.ply, 743 KB, 23:13") con pillola di formato e azione "Mostra nel Finder".
Un training completato fornisce una nuvola gaussiana — una collezione di alcune centinaia di migliaia fino a milioni di distribuzioni gaussiane 3D, che insieme ricostruiscono la scena. RadianceKit conosce dieci modi per scrivere questa nuvola su disco. Sei di essi sono formati di dati 3D puri (PLY, Compressed PLY, SPZ, SOG, glTF, .splat), uno raggruppa la nuvola insieme a un viewer HTML pronto (Web Viewer), uno renderizza un file MP4 da una traiettoria di fotocamera in orbita (Orbit Video), e due non esportano contenuti gaussiani ma soltanto il risultato SfM (pose della fotocamera e nuvola di punti grossolana) per il riutilizzo in altre pipeline di training (transforms.json + COLMAP Workspace).
Quale formato sia quello giusto quando dipende dall'obiettivo. Per l'archiviazione dei dati completi senza perdita di qualità si prende PLY. Per viewer web sulla propria pagina di solito bastano .splat o il Web Viewer integrato. Quando il file deve essere minimo, vale la pena SPZ o SOG. Per il riutilizzo del risultato SfM in Nerfstudio, Postshot o Brush, transforms.json e il COLMAP Workspace sono i percorsi giusti.
Tutte le funzioni di esportazione si trovano nel menu "Export" così come nella Modalità principiante all'ultimo passaggio del wizard. La maggior parte dei formati è pienamente conforme al sandbox e funziona nella versione App Store. Solo SOG richiede un binario esterno (cwebp), che non è necessariamente presente nella build App Store — per i dettagli vedi E4.
E1 — PLY (.ply)
DOVE
Barra dei menu → Export → 3D Formats → Export PLY… (⌘E). Modalità principiante: passaggio wizard Export → scheda formato "PLY". Dimensione: tipicamente 100 % (valore di riferimento). Compatibile con: SuperSplat, PolyCam, tutti i viewer 3DGS.
TECNICO
PLY è il formato di archiviazione canonico per 3D Gaussian Splatting. RadianceKit scrive un file binario little-endian con il layout di proprietà 3DGS standardizzato: per gaussiana posizione a tre componenti, tre normali sempre impostate a zero, tre coefficienti SH DC (f_dc_0..2) per il colore RGB di base, seguiti da fino a 45 ulteriori coefficienti SH (f_rest_0..44) nell'arrangiamento trasposto channel-major definito dal paper Kerbl 2023 (prima tutti i coefficienti del canale R, poi tutti i G, poi tutti i B), seguiti da opacità logit (valori grezzi pre-sigmoid), tre scale in log-space e una rotazione quaternionica wxyz. Il grado SH massimo esportato viene limitato al minimo tra il desiderio dell'utente e il grado effettivamente appreso; il default è 3 (45 coefficienti rest). Prima della scrittura, la dimensione del payload viene calcolata in interi a 64 bit per intercettare overflow su nuvole estremamente grandi. Il file viene scritto in modo atomico, il che su grandi nuvole occupa brevemente il doppio spazio su disco.
E2 — Compressed PLY (.ply)
DOVE
Barra dei menu → Export → 3D Formats → Export Compressed PLY…. Modalità principiante: scheda formato "Compressed PLY". Dimensione: circa 10–20 % rispetto a PLY (compressione 5–10 volte). Compatibile con: SuperSplat, motore PlayCanvas, viewer basati su web.
TECNICO
La variante PlayCanvas del formato PLY con quantizzazione chunked. Le gaussiane sono raggruppate in chunk da 256. Per chunk vengono memorizzati separatamente nell'header i bound min/max per posizione, scala e colore; le singole gaussiane riferiscono i loro valori relativi a questi bound e vengono compresse a 32 bit ciascuna: posizione e scala con packing 11-10-11 bit, rotazione come quaternione "smallest-three" 2-10-10-10 bit, colore come RGBA 8-8-8-8. I coefficienti SH superiori vengono quantizzati con soli 8 bit per componente (shCoeffCount * 3 uchar per gaussiana). Il formato stesso è ancora PLY con header ASCII e quindi in linea di principio validabile con strumenti PLY, ma le proprietà dei vertici sono dichiarate come campi uint. Il grado SH è di default 0 (nessun coefficiente rest), per massimizzare la compressione — gradi SH più alti possono essere selezionati esplicitamente.
E3 — SPZ (.spz)
DOVE
Barra dei menu → Export → 3D Formats → Export SPZ…. Modalità principiante: scheda formato "SPZ". Dimensione: circa 10 % rispetto a PLY (90 % più piccolo). Compatibile con: Niantic Scaniverse, Niantic Spatial Fields, MetalSplatter.
TECNICO
Il formato SPZ v2 di Niantic. Le posizioni vengono impacchettate come fixed-point a 24 bit (questo dà una risoluzione di circa 0,25 mm), le scale come quantizzazione a 8 bit nel log-space, le rotazioni come smallest-three a 8 bit (in v2 vengono memorizzati solo xyz, w viene derivato dal decoder dalla norma del quaternione), le opacità come valori sigmoidizzati a 8 bit. Il SH DC viene memorizzato con una formula di packing specifica SPZ (dc_raw * 0.15 * 255 + 0.5 * 255), le bande SH superiori con 5 bit (banda 1) rispettivamente 4 bit (banda 2-3) per coefficiente. L'intero blob binario impacchettato viene poi compresso con gzip standard (RFC 1952), il che dà un formato container gzipped con i magic byte 1f 8b. RadianceKit invoca per questo il gzip di sistema, perché l'API zlib integrata di Apple genera un framing Apple proprietario che non sarebbe compatibile con i reader SPZ in Spatial Fields o MetalSplatter. Il gzip di sistema rimane invocabile anche all'interno del sandbox macOS.
E4 — SOG (.sog)
DOVE
Barra dei menu → Export → 3D Formats → Export SOG…. Modalità principiante: scheda formato "SOG". Dimensione: circa 5–6 % rispetto a PLY (compressione 15–20 volte — l'opzione più piccola). Compatibile con: motore PlayCanvas, editor SuperSplat.
TECNICO
"Spatially Ordered Gaussians" — un formato PlayCanvas che memorizza la nuvola GPU-ready in più immagini WebP lossless. Prima tutte le gaussiane vengono ordinate spazialmente tramite codice Morton 3D (Z-order a 30 bit, 10 bit per asse), il che dà alle immagini una successiva cache locality nel renderer. Poi le posizioni vengono quantizzate con trasformazione logaritmica simmetrica (per un migliore range dinamico) a valori a 16 bit e divise in due immagini RGBA (means_l.webp per gli 8 bit inferiori, means_u.webp per i superiori). Le rotazioni vengono codificate come smallest-three con 3×8 bit più modalità a 2 bit in un'immagine RGBA (la modalità finisce in alpha come 252 + largest). Le scale e il SH DC vengono quantizzati ciascuno con un codebook a 256 voci (distribuito basato su percentile su tutti i valori), gli indici finiscono in scales.webp e sh0.webp. Le cinque immagini più un meta.json con codebook e bound vengono impacchettate in un file ZIP (encoder personalizzato, perché il sandbox blocca lo zip di sistema) e salvate con l'estensione .sog.
Attenzione sandbox: SOG è l'unica opzione di formato che richiede un binario esterno. Lo stadio di encoder WebP invoca cwebp da /usr/local/bin/cwebp o /opt/homebrew/bin/cwebp. Se non viene trovato alcun binario cwebp, il codice ricade su una codifica PNG grezza — ma: il fallback PNG non funziona in SuperSplat. Nella versione App Store valuta la disponibilità in base alla variante di build; nella variante sviluppatore cwebp deve essere installato tramite Homebrew (brew install webp).
E5 — glTF (.glb)
DOVE
Barra dei menu → Export → 3D Formats → Export glTF…. Modalità principiante: scheda formato "glTF". Dimensione: paragonabile a PLY. Compatibile con: viewer glTF con l'estensione KHR_gaussian_splatting (bozza standard Khronos).
TECNICO
Scrive un file binario .glb autosufficiente (nessun allegato file bin separato) secondo la specifica dell'estensione KHR_gaussian_splatting. Le posizioni vengono memorizzate come dati vertice glTF POSITION regolari (float3), tutti gli altri attributi (rotazione come float4, scala come float3, opacità come float, coefficienti SH come float3 × shCoeffCount) si trovano in attributi vertice aggiuntivi e vengono referenziati tramite l'estensione. Importante: glTF utilizza un sistema di coordinate Y-up destrorso, COLMAP/3DGS lavora Y-down/Z-forward. Quindi l'esportatore applica una rotazione di 180 gradi attorno all'asse X — le posizioni vengono riscritte con (x, -y, -z), i quaternioni vengono adattati a (w, x, -y, -z). Questo dà una rappresentazione geometricamente corretta e congrua (non specchiata) nei viewer glTF. I chunk JSON e binari vengono allineati a 4 byte come richiesto dallo standard GLB.
E6 — Splat (.splat)
DOVE
Barra dei menu → Export → 3D Formats → Export .splat…. Modalità principiante: scheda formato ".splat". Dimensione: esattamente 32 byte per gaussiana. Compatibile con: gsplat.js, viewer basati su web (riferimento antimatter15), la maggior parte delle demo 3DGS nel browser.
TECNICO
Il formato .splat di antimatter15 — 32 byte per gaussiana, nessun header, nessuna indirezione. Layout per voce: 3 × float32 posizione (coordinate mondo), 3 × float32 scala (trasformata exp dal log-space del buffer interno), 4 × uint8 colore RGBA (coefficiente SH DC scalato con SH_C0 = 0.282... e limitato a [0,255]), 4 × uint8 quaternione (w,x,y,z, normalizzato e codificato come 128 + 128*q nell'intervallo byte). Viene memorizzato solo SH DC — le bande SH superiori vengono scartate. Questo rende il formato estremamente compatto, ma costa le variazioni di colore dipendenti dalla vista che si verificano in riflessi o highlight speculari. L'ordine di scrittura è esattamente l'ordine di indice della nuvola (nessun ordinamento spaziale), i viewer web come gsplat.js renderizzano partendo da questo presupposto.

flowers-01.html autonomo aperto direttamente dal Finder con doppio clic nel browser predefinito — il programma WebGL2 incorporato renderizza la nuvola gaussiana immediatamente, senza rete o server. I marker neri attorno al bouquet sono le fotocamere di training, opzionalmente visualizzabili. Il drag del mouse ruota, lo scroll fa lo zoom.E7 — Web Viewer (.html)
DOVE
Barra dei menu → Export → Media → Export Web Viewer…. Modalità principiante: scheda formato "Web Viewer". Dimensione: dati splat codificati base64 (≈ 4/3 di overhead) + circa 5 KB di shell HTML/JS. Compatibile con: qualsiasi browser moderno con WebGL2 (tutti i desktop, iOS 15+, Android 5+).
TECNICO
Raggruppa la nuvola gaussiana insieme a un renderer WebGL2 scritto completamente inline in un singolo file .html. Non ci sono dipendenze CDN, nessun WASM, nessun secondo file. La nuvola viene prima codificata internamente come binario .splat (stessa logica a 32 byte di E6), poi incorporata in base64, poi decodificata nel browser con atob. Il renderer integrato esegue il proprio ordinamento WebGL2, il controllo orbit del mouse e l'ordinamento CPU per frame; tutto il codice JS (shader, matematica, loop) è visibile nell'HTML di output. La convenzione degli assi al confine memoria-renderer è esattamente la stessa di E5: posizione (x, -y, -z), quaternione (w, x, -y, -z). Opzionalmente può essere visualizzato un overlay di branding (switch del tier gratuito). Poiché tutto è inline, il file funziona anche direttamente dal protocollo file:// — nessun server web locale necessario per i test.

E8 — Orbit Video (.mp4/.mov)
DOVE
Barra dei menu → Viewport → Record Turntable Video OPPURE Barra dei menu → Export → Media → Export Orbit Video…. Modalità principiante: scheda formato "Orbit Video" con cursore di durata 3–30 s. Dimensione: dipende da durata, risoluzione, bitrate. Compatibile con: tutte le piattaforme (H.264 e HEVC sono standard Apple).
TECNICO
Renderizza la nuvola gaussiana lungo una traiettoria di fotocamera in orbita parametrica e codifica ogni frame tramite AVAssetWriter in un file MP4 o MOV. La configurazione dell'orbita controlla velocità di rotazione (giri), distanza, elevazione, FOV, durata e fattore ease-in/out. Per frame, la matrice di adattamento mondo (calcolata dal renderer per ruotare le coordinate interne nel mondo orbit Y-up) viene moltiplicata con la fotocamera, poi viene applicata la riflessione Y specifica di MetalSplatter. Il target di rendering offscreen viene tirato tramite IOSurface a un CVPixelBuffer per l'encoder. L'encoder supporta H.264 e HEVC, bitrate configurabile e risoluzione da 480p a 8K. Prima del primo frame, il renderer attende 200 ms affinché l'ordinamento iniziale degli splat sia completato. Questa esportazione è GPU-bound — a 8K e milioni di gaussiane il tempo di rendering per frame è di diversi secondi, quindi sono possibili tempi totali di rendering di 10–30 minuti per 6 s di video.
E9 — SfM Transforms (transforms.json)
DOVE
Barra dei menu → Export → Photogrammetry → Export SfM (transforms.json)…. Dimensione: tipicamente 1–10 KB (solo pose + intrinseci, nessuna immagine, nessuna gaussiana). Compatibile con: nerfstudio, Brush, gsplat, OpenSplat, Meshroom, tutti i trainer 3DGS feed-forward moderni.
TECNICO
Scrive il formato transforms.json di nerfstudio con una lista di pose della fotocamera più intrinseci condivisi. Per fotocamera, la view matrix (RadianceKit interno: world-to-camera in convenzione COLMAP) viene invertita, poi i vettori base Y e Z locali alla fotocamera vengono specchiati per convertire alla convenzione nerfstudio (stile OpenGL, fotocamera guarda lungo -Z, +Y è in alto). La matrice 4×4 finale finisce come nested array row-major di double nel campo transform_matrix di ogni frame. Gli intrinseci vengono memorizzati al livello superiore (lunghezza focale x/y, punto principale x/y, larghezza/altezza dell'immagine, camera_model = "OPENCV", più i coefficienti di distorsione k1, k2, p1, p2) — a meno che l'esportatore non riconosca più set di intrinseci diversi, allora vengono scritti per frame. I percorsi delle immagini vengono scritti come images/<filename> relativi al file JSON; l'utente deve creare una cartella images/ sibling con le foto di training.
E10 — COLMAP Workspace (sparse/0/)
DOVE
Barra dei menu → Export → Photogrammetry → Export SfM (COLMAP Workspace)…. Dimensione: tre file binari insieme tipicamente 4–8 MB — points3D.bin domina (una riga per punto 3D della nuvola sparsa), images.bin e cameras.bin sono ciascuno ben sotto i 100 KB. Compatibile con: COLMAP stesso, Nerfstudio, Postshot, Meshroom, tutti gli strumenti che si aspettano una directory sparse/ COLMAP.
TECNICO
Scrive il layout sparse/0/ standard di COLMAP con tre file binari: cameras.bin, images.bin, points3D.bin. Il riferimento del formato è la documentazione ufficiale di COLMAP. cameras.bin contiene la lista degli intrinseci deduplicata (le fotocamere con intrinseci identici + dimensione dell'immagine vengono riassunte in una singola voce); il modello di fotocamera utilizzato è OPENCV (modello 4), con fx/fy/cx/cy più i quattro coefficienti di distorsione k1/k2/p1/p2. images.bin elenca per immagine la posa come quaternione wxyz più la traslazione, seguita dall'ID della fotocamera e dal nome del file; non vengono memorizzate corrispondenze 2D-3D. points3D.bin contiene la nuvola di punti SfM con posizione, colore (RGB 0-255) e valori predefiniti per riproiezione e lunghezza dei track. Tutto viene scritto in little-endian. La re-importazione in RadianceKit funziona tramite il menu File → "Import COLMAP/Metashape Workspace…" (vedi Q3 nel capitolo Backend SfM).
Quale formato quando?
| Obiettivo | Formato |
|---|---|
| Viewer web sulla propria pagina | E7 Web Viewer (.html) |
Viewer web con gsplat.js | E6 Splat (.splat) |
| Riutilizzo pipeline in Postshot / Nerfstudio | E9 transforms.json + E10 COLMAP Workspace |
| Modifica SuperSplat | E1 PLY o E2 Compressed PLY |
| Niantic Scaniverse / Spatial Fields | E3 SPZ |
| Massima compressione | E4 SOG (cwebp richiesto) |
| Video marketing/social | E8 Orbit Video |
Confronto rapido
| Formato | Estensione | Sandbox | Dimensione (1M gauss) | Uso migliore |
|---|---|---|---|---|
| E1 PLY | .ply | sì | ~250 MB | Archivio, massima compatibilità |
| E2 Compressed PLY | .ply | sì | ~40 MB | Web + SuperSplat |
| E3 SPZ | .spz | sì (gzip-spawn) | ~40 MB | Niantic + Mobile |
| E4 SOG | .sog | condizionato (cwebp) | ~20 MB | Massima compressione |
| E5 glTF | .glb | sì | ~250 MB | Pipeline Khronos |
| E6 Splat | .splat | sì | ~32 MB | Viewer web gsplat.js |
| E7 Web Viewer | .html | sì | ~45 MB | File browser standalone |
| E8 Orbit Video | .mp4/.mov | sì | variabile | Social/marketing |
| E9 SfM Transforms | .json | sì | ~5 KB | Trasferimento pose |
| E10 COLMAP Workspace | Directory | sì | ~4–8 MB | Trasferimento pose binario |
La colonna dimensione è un'indicazione approssimativa per 1 mln di gaussiane con grado SH 3. I valori reali variano a seconda della comprimibilità della scena; il grado SH 0 riduce PLY/glTF di un fattore 4.