Saltar al contenido
  1. Inicio
  2. Publicaciones
  3. 3D Gaussian Splatting: renderizado en tiempo …
Inteligencia Artificial 10 min de lectura 09 Nov 2026

3D Gaussian Splatting: renderizado en tiempo real

Explicamos 3D Gaussian Splatting, el método de Inria que reemplaza la red de NeRF por millones de gaussianas 3D y un rasterizador en GPU para ver escenas fotografiadas en tiempo real, con sus resultados y sus límites.

3D Gaussian Splatting: renderizado en tiempo real

El paper

3D Gaussian Splatting for Real-Time Radiance Field Rendering

Autores
Bernhard Kerbl, Georgios Kopanas, Thomas Leimkühler, George Drettakis
Organización
Inria
Año
2023
Licencia
Copyright del editor
Ver la ficha del paper

Respuesta corta: qué logra 3D Gaussian Splatting

3D Gaussian Splatting representa una escena con millones de gaussianas 3D y las dibuja con un rasterizador en GPU. En el dataset Mip-NeRF360 renderiza a 134 fps frente a 0.06 de Mip-NeRF360, con calidad parecida (PSNR 27.21 frente a 27.69) y 41m33s de entrenamiento contra 48 horas (Kerbl et al., 2023).

Motivación: por qué 3D Gaussian Splatting busca otra forma de renderizar campos de radiancia

La síntesis de nuevas vistas (novel-view synthesis) parte de varias fotos de una escena y genera la imagen que vería una cámara en una posición que nadie fotografió. Desde NeRF, la forma dominante de hacerlo es un campo de radiancia (radiance field): una función continua que dice qué color y qué densidad hay en cada punto del espacio.

Para dibujar una imagen con NeRF se lanza un rayo por cada píxel y se consulta esa función en muchos puntos del rayo. Ese muestreo, llamado ray-marching, es caro y mete ruido. El método con mejor calidad cuando salió el paper, Mip-NeRF360, "requires up to 48 hours of training time", según los autores.

Los métodos rápidos, como InstantNGP (que guarda rasgos en una tabla hash) y Plenoxels (que usa una rejilla de vóxeles sin red neuronal), bajan el entrenamiento a minutos. El costo es la calidad, y su renderizado se queda en tiempos interactivos de 10 a 15 cuadros por segundo según la escena. Según los autores, para escenas completas y abiertas ningún método lograba tiempo real a 1080p.

Bernhard Kerbl, Georgios Kopanas, Thomas Leimkühler y George Drettakis (Inria, Université Côte d'Azur y Max-Planck-Institut für Informatik) publicaron en 2023, en ACM Transactions on Graphics, una alternativa. En lugar de una función continua, representan la escena con millones de gaussianas 3D explícitas y las dibujan con un rasterizador, como en un videojuego. La pregunta del paper es si así se conserva la calidad de Mip-NeRF360 sin pagar sus horas de entrenamiento ni sus segundos por cuadro.

Cómo funciona 3D Gaussian Splatting, paso a paso

La entrada son fotos de una escena estática y las cámaras calibradas con Structure-from-Motion (SfM), el proceso que estima desde dónde se tomó cada foto. SfM produce, de paso, una nube de puntos dispersa. 3D Gaussian Splatting crea una gaussiana 3D en cada uno de esos puntos. En el caso sintético de Blender también funciona con un inicio aleatorio.

La primitiva: una gaussiana 3D

Cada gaussiana tiene una posición (media $\mu$), una matriz de covarianza $\Sigma$ que define su forma de elipsoide, una opacidad $\alpha$ y unos coeficientes de armónicos esféricos (spherical harmonics, SH) que dan su color según desde dónde la mires. Su valor en el espacio es $G(x) = e^{-\frac{1}{2}(x)^T\Sigma^{-1}(x)}$, la campana de siempre en tres dimensiones. Para dibujarla, se proyecta a la pantalla con $\Sigma' = J W \Sigma W^T J^T$, donde $W$ es la transformación de la cámara y $J$ el jacobiano de la proyección. El resultado es una mancha elíptica en el plano, un splat.

Cómo se pinta un píxel

Los autores parten de una observación: NeRF y el renderizado por puntos usan el mismo modelo de formación de imagen. El color de un píxel se arma mezclando, de adelante hacia atrás, los splats que lo cubren. Es la ecuación (3) del paper:

$$C = \sum_{i \in \mathcal{N}} c_i \alpha_i \prod_{j=1}^{i-1} (1 - \alpha_j)$$

  • $C$: el color final del píxel.
  • $\mathcal{N}$: el conjunto ordenado de gaussianas que cubren el píxel, de la más cercana a la más lejana.
  • $c_i$: el color de la gaussiana $i$ visto desde esa cámara, calculado con sus armónicos esféricos.
  • $\alpha_i$: la gaussiana proyectada en la pantalla evaluada en el píxel, multiplicada por la opacidad aprendida.
  • $\prod_{j=1}^{i-1} (1 - \alpha_j)$: la transmitancia, la fracción de luz que dejan pasar las gaussianas de enfrente.

La intuición: si una gaussiana cercana es opaca, la transmitancia cae a casi cero y las de atrás ya no aportan. Si es transparente, deja ver lo que hay detrás. La diferencia con NeRF no es la fórmula, es el algoritmo: aquí no hay que buscar muestras al azar a lo largo del rayo, porque las gaussianas ya están en la lista.

Una covarianza que el gradiente no puede romper

Una covarianza solo tiene sentido físico si es semidefinida positiva. El descenso de gradiente no respeta esa condición por sí solo, así que los autores no optimizan $\Sigma$ directo. La escriben como un elipsoide, ecuación (6):

$$\Sigma = R S S^T R^T$$

  • $S$: matriz diagonal de escala, guardada como un vector 3D $s$ (el tamaño del elipsoide en cada eje).
  • $R$: matriz de rotación, guardada como un cuaternión $q$ que se normaliza en cada paso.

La intuición: cualquier $s$ y cualquier $q$ dan una covarianza válida. Si una escala se hace muy pequeña, la gaussiana se aplana como un disco y sirve para representar superficies; si las tres son iguales, es una esfera. Los autores derivan todos los gradientes a mano (apéndice A) para no pagar el costo de la diferenciación automática.

Qué se optimiza y con qué pérdida

En cada iteración se renderiza una vista de entrenamiento, se compara con la foto real y se ajustan posiciones, covarianzas, opacidades y colores con Adam. La pérdida es la ecuación (7):

$$\mathcal{L} = (1 - \lambda)\mathcal{L}_1 + \lambda\mathcal{L}_{\text{D-SSIM}}$$

  • $\mathcal{L}_1$: el error absoluto promedio píxel por píxel.
  • $\mathcal{L}_{\text{D-SSIM}}$: un término basado en SSIM, que mide la similitud estructural (bordes, texturas) y no solo el color de cada píxel.
  • $\lambda$: el peso entre los dos; los autores usan 0.2 en todas sus pruebas.

La intuición: con $\lambda$ en cero solo importa el color exacto; al subirlo, la optimización cuida más que la textura se vea igual.

Control adaptativo de densidad

La nube de SfM es escasa, así que hay que crear gaussianas. Cada 100 iteraciones, 3D Gaussian Splatting revisa las que tienen un gradiente de posición en pantalla grande (mayor a 0.0002). Si la gaussiana es pequeña, la clona: falta geometría. Si es grande, la divide en dos y reduce su escala por un factor de 1.6: una sola mancha cubre demasiado. Además elimina las casi transparentes y, cada 3000 iteraciones, pone las opacidades cerca de cero para limpiar manchas flotantes.

El rasterizador por mosaicos

La rapidez viene del rasterizador. Divide la pantalla en mosaicos (tiles) de 16×16 píxeles y descarta las gaussianas fuera de la cámara. A cada copia de gaussiana por mosaico le asigna una llave de hasta 64 bits: los 32 bits bajos guardan la profundidad y los altos el número de mosaico. Un solo radix sort en la GPU ordena todo a la vez. Luego cada mosaico mezcla sus gaussianas de adelante hacia atrás y se detiene cuando el píxel se satura. A diferencia de trabajos previos, no limita cuántas gaussianas reciben gradiente.

Ejemplo visual: velocidad y calidad de 3D Gaussian Splatting

La primera pregunta es la velocidad. La Tabla 1 del paper reporta los cuadros por segundo (FPS) al renderizar las escenas del dataset Mip-NeRF360. Las dos barras azules son 3D Gaussian Splatting tras 7K y 30K iteraciones de entrenamiento. Mip-NeRF360 aparece casi en cero: 0.06 cuadros por segundo.

Velocidad de renderizado en el dataset Mip-NeRF360 (cuadros por segundo, más es mejor). Fuente: Kerbl et al. (2023), Tabla 1.

La segunda pregunta es si esa velocidad cuesta calidad. La gráfica compara el PSNR (peak signal-to-noise ratio, en decibeles: más alto es más parecido a la foto real) en los tres datasets reales. Contra Mip-NeRF360, 3D Gaussian Splatting pierde un poco en su dataset, gana en Tanks&Temples y empata en Deep Blending.

Calidad de imagen (PSNR, más es mejor) en vistas de prueba. Los valores de Mip-NeRF360 en su propio dataset son los publicados por sus autores. Fuente: Kerbl et al. (2023), Tabla 1.

Resultados de 3D Gaussian Splatting frente a Mip-NeRF360, InstantNGP y Plenoxels

Los autores evaluaron 13 escenas reales: todas las del dataset Mip-NeRF360, dos de Tanks&Temples y dos de Deep Blending. Separaron una de cada 8 fotos para prueba, como propone Mip-NeRF360. Usaron los mismos hiperparámetros en todo y midieron en una GPU A6000, excepto Mip-NeRF360. Los números de los otros métodos salen de correr el código de sus autores, salvo las métricas de Mip-NeRF360 en su propio dataset, copiadas de su paper.

Calidad y tiempo en las escenas reales

En el dataset Mip-NeRF360, 3D Gaussian Splatting con 30K iteraciones obtiene SSIM de 0.815, PSNR de 27.21 y LPIPS de 0.214. Mip-NeRF360 reporta 0.792, 27.69 y 0.237. Es decir, gana en SSIM y LPIPS (donde menos es mejor) y queda abajo en PSNR. La diferencia está en el costo: 41m33s de entrenamiento y 134 FPS frente a 48h y 0.06 FPS.

Ese tiempo de 48h de Mip-NeRF360 es una equivalencia: lo entrenaron en un nodo de 4 GPU A100 durante 12 horas. En Tanks&Temples, 3D Gaussian Splatting alcanza PSNR de 23.14 frente a 22.22 de Mip-NeRF360, en 26m54s. En Deep Blending, 29.41 frente a 29.40, en 36m2s.

Contra los métodos rápidos, la versión de 7K iteraciones es la comparación justa. En el dataset Mip-NeRF360 entrena en 6m25s y logra PSNR de 25.60 a 160 FPS. InstantNGP Big tarda 7m30s, logra 25.59 y renderiza a 9.43 FPS. Plenoxels tarda 25m49s, logra 23.08 y va a 6.79 FPS. Según los autores, con más entrenamiento 3D Gaussian Splatting llega a la calidad de Mip-NeRF360, algo que los otros métodos rápidos no logran.

Escenas sintéticas y tamaño del modelo

En el dataset sintético de Blender, 3D Gaussian Splatting arranca con 100K gaussianas aleatorias, sin SfM. Su PSNR promedio es 33.32, frente a 33.30 de Point-NeRF, 33.18 de InstantNGP Base y 33.09 de Mip-NeRF. Las escenas entrenadas se renderizan de 180 a 300 FPS.

La memoria es el costo visible: el modelo de 30K iteraciones ocupa 734MB en el dataset Mip-NeRF360, frente a 48MB de InstantNGP Big y 8.6MB de Mip-NeRF360.

Qué aporta cada pieza

La Tabla 3 quita un componente a la vez en tres escenas (Truck, Garden y Bicycle). Con el método completo el PSNR promedio tras 30K iteraciones es 26.05. Iniciar con puntos aleatorios lo baja a 20.42, quitar la división de gaussianas a 23.90 y usar gaussianas isotrópicas (esferas) a 25.23. El caso extremo es limitar a 10 las gaussianas que reciben gradiente por píxel, como hacían métodos previos: el promedio cae a 19.19 y en Truck se pierden 11dB.

Ablaciones: PSNR promedio de tres escenas al quitar cada componente. Fuente: Kerbl et al. (2023), Tabla 3.

Limitaciones de 3D Gaussian Splatting: qué no prueba el paper

  • Artefactos donde faltan fotos. Los autores reconocen manchas alargadas, gaussianas "splotchy" y saltos visuales (popping) cuando se crean gaussianas grandes, sobre todo en zonas poco observadas. No aplican regularización, y para escenas muy grandes, como las urbanas, dicen que hay que bajar la tasa de aprendizaje.
  • Mucha memoria. El pico de memoria de GPU al entrenar escenas grandes puede pasar de 20 GB en su prototipo. Para renderizar hay que cargar el modelo completo (cientos de MB) más de 30 a 500 MB del rasterizador. NeRF guarda la escena en mucho menos espacio.
  • Comparaciones con matices. En el dataset de Mip-NeRF360, el PSNR de Mip-NeRF360 sigue arriba. Sus métricas en ese dataset son copiadas y su hardware es otro (A100). La Tabla 1 mide FPS a la resolución nativa de cada dataset, sin desglosar resoluciones, así que la promesa de tiempo real a 1080p del resumen no se puede revisar fila por fila.
  • Alcance. Solo trata escenas estáticas, todos los números son de los propios autores y las ablaciones usan tres escenas.

Qué significa para ti: cómo aprovechar 3D Gaussian Splatting hoy

Si trabajas con visión por computadora, reconstrucción 3D o contenido para web y realidad virtual, 3D Gaussian Splatting es una opción práctica para pasar de fotos a una escena navegable en tiempo real. Los autores publicaron su código y sus datos en la página del proyecto (repo-sam.inria.fr/fungraph/3d-gaussian-splatting). Está escrito en Python con PyTorch, más kernels de CUDA para el rasterizador, así que necesitas una GPU NVIDIA.

El flujo es parecido al de NeRF: tomas fotos alrededor de la escena, calibras las cámaras con una herramienta de SfM y entrenas. La diferencia está en el resultado: no es una red neuronal, es una lista de gaussianas con posición, forma, opacidad y color. Eso se puede guardar, recortar y renderizar sin consultar un modelo.

Las dos ideas centrales caben en pocas líneas de NumPy. Este código arma una covarianza válida a partir de una escala y un cuaternión (ecuación 6) y mezcla dos gaussianas ordenadas para obtener el color de un píxel (ecuación 3):

import numpy as np


def covarianza(escala, q):
    """Sigma = R S S^T R^T a partir de un vector de escala y un cuaternión (ecuación 6)."""
    w, x, y, z = q / np.linalg.norm(q)          # se normaliza para tener una rotación válida
    R = np.array([
        [1 - 2 * (y * y + z * z), 2 * (x * y - w * z), 2 * (x * z + w * y)],
        [2 * (x * y + w * z), 1 - 2 * (x * x + z * z), 2 * (y * z - w * x)],
        [2 * (x * z - w * y), 2 * (y * z + w * x), 1 - 2 * (x * x + y * y)],
    ])
    S = np.diag(escala)
    return R @ S @ S.T @ R.T


def mezcla_alfa(colores, alfas):
    """Color de un píxel con gaussianas ya ordenadas de adelante hacia atrás (ecuación 3)."""
    C, T = np.zeros(3), 1.0                     # T: luz que todavía pasa
    for c, a in zip(colores, alfas):
        C += T * a * c
        T *= 1 - a
        if T < 1e-4:                            # el píxel ya se saturó: se deja de mezclar
            break
    return C


Sigma = covarianza(np.array([0.5, 0.05, 0.05]), np.array([0.92, 0.0, 0.38, 0.0]))
print(np.linalg.eigvalsh(Sigma))                # siempre >= 0: covarianza válida
print(mezcla_alfa([np.array([1.0, 0.2, 0.2]), np.array([0.2, 0.2, 1.0])], [0.6, 0.9]))

Los valores propios de la covarianza son las escalas al cuadrado, así que nunca son negativos, sin importar qué haga el optimizador. El color del píxel mezcla la gaussiana roja de enfrente con la azul de atrás según cuánta luz deja pasar la primera.

Lo que no cambia: si tu restricción es espacio en disco o una GPU con poca memoria, un método tipo NeRF o InstantNGP sigue siendo más ligero. Y si tu escena se mueve, este paper no lo cubre.

Referencias

Bernhard Kerbl, Georgios Kopanas, Thomas Leimkühler, George Drettakis. 3D Gaussian Splatting for Real-Time Radiance Field Rendering. ACM Transactions on Graphics 2023, 2023. https://doi.org/10.1145/3592433

Preguntas frecuentes

¿3D Gaussian Splatting usa una red neuronal?

No. La escena es una lista explícita de gaussianas 3D con posición, forma, opacidad y color, y se dibuja con un rasterizador en GPU. Se entrena con descenso de gradiente, pero no hay una red que consultar al renderizar.

¿En qué se diferencia 3D Gaussian Splatting de NeRF?

Comparten el mismo modelo de mezcla de colores, pero NeRF guarda la escena en una función continua y la consulta con muestras a lo largo de cada rayo. Gaussian Splatting guarda gaussianas explícitas y solo las ordena y mezcla, lo que lo hace mucho más rápido a cambio de usar más memoria.

¿Qué necesito para entrenar una escena con Gaussian Splatting?

Fotos de una escena estática, cámaras calibradas con Structure-from-Motion y una GPU NVIDIA, porque el rasterizador está escrito en CUDA. Los autores publicaron el código en Python con PyTorch.

¿3D Gaussian Splatting sirve para escenas en movimiento?

El paper no lo cubre: trabaja con fotos de una escena estática. Tampoco evalúa escenas urbanas muy grandes, donde los autores dicen que hay que ajustar la tasa de aprendizaje.

¿Por qué los modelos de Gaussian Splatting pesan tanto?

Porque guardan millones de gaussianas, cada una con su posición, covarianza, opacidad y coeficientes de color. Los autores reconocen que su consumo de memoria es mucho mayor que el de los métodos tipo NeRF y que hay margen para comprimirlo.