Cómo funciona la renderización de juegos en 3D: luces y sombras

La implementación de la gran mayoría de los efectos visuales en los juegos modernos depende del uso juicioso de la iluminación y las sombras. Sin ellos, los juegos serían aburridos y sin vida. En la cuarta parte del análisis de la representación de juegos 3D, nos centraremos en lo que está sucediendo en el mundo 3D junto con el procesamiento de vértices y el mapeo de texturas. Nuevamente necesitaremos muchas matemáticas, así como una sólida comprensión de los conceptos básicos de la óptica.

Parte 1: procesamiento de vértices

Parte 2: rasterización y trazado de rayos

Parte 3: texturizado y filtrado de texturas

Recordar el pasado


Anteriormente, examinamos los aspectos clave de mover y procesar objetos en escenas, su conversión del espacio tridimensional a una cuadrícula plana de píxeles, así como las formas de superponer texturas en estos objetos. Durante muchos años, tales operaciones han sido una parte esencial del proceso de renderizado, y podemos ver esto volviendo en 1993 y lanzando Doom de id Software.


Según los estándares modernos, el uso de luces y sombras en este juego era muy primitivo: las fuentes de luz no se tenían en cuenta, a cada superficie basada en sus vértices se le daba un valor de color general o el valor de la luz ambiental . Todos los signos de sombras se crearon gracias al uso astuto de las texturas y la elección del color del entorno.

No había sombras, porque no eran tarea de los programadores: la PC de esa época era un procesador de 66 MHz (es decir, 0.066 GHz), un disco duro de 40 MB y una tarjeta gráfica de 512 kilobytes con capacidades 3D mínimas. Avance rápido 23: en el famoso reinicio de la serie, vemos una historia completamente diferente.


Se utilizaron muchas tecnologías para renderizar este marco , cuenta con etapas tales como oclusión ambiental del espacio de pantalla, mapeo de profundidad previa al paso, filtros de desenfoque bokeh, operadores de corrección de tono, etc. El cálculo de la iluminación y el sombreado de cada superficie se realiza de forma dinámica: cambian constantemente según las condiciones ambientales y las acciones del jugador.

Dado que cualquier operación de renderizado 3D requiere matemáticas (¡un montón de cálculos!), Es mejor que comencemos con lo que sucede detrás de escena de cualquier juego moderno.

Iluminación matemática


Para implementar todo correctamente, necesitamos simular con precisión el comportamiento de la luz al interactuar con varias superficies. Es curioso que por primera vez este problema comenzó a resolverse en el siglo XVIII por un hombre llamado Johann Heinrich Lambert.

En 1760, un científico suizo lanzó un libro llamado Photometria . En él, describió las reglas fundamentales del comportamiento de la luz; El más notable de ellos fue el siguiente: la superficie emite luz (por reflexión o como fuente de luz) de tal manera que el brillo de la luz emitida varía según el coseno del ángulo entre la superficie normal y el observador.


Esta simple regla sentó las bases para la llamada iluminación difusa . Este es un modelo matemático utilizado para calcular el color de una superficie en función de sus propiedades físicas (por ejemplo, su color y grado de reflexión de la luz) y la ubicación de la fuente de luz.

En el renderizado 3D, esto requiere mucha información, lo cual es más fácil de imaginar en forma de tal esquema:


Vemos muchas flechas en la imagen, estos son vectores , y se requieren los siguientes vectores para calcular el color:

  • 3 vectores para la posición del vértice, la fuente de luz y la cámara mirando la escena
  • 2 vectores para las direcciones de la fuente de luz y la cámara desde el punto de vista del vértice
  • 1 vector normal
  • 1 medio vector (siempre está en el medio entre los vectores de dirección de la iluminación y la cámara)

Se calculan en la etapa de procesamiento de los vértices del proceso de renderizado, y la ecuación que los une a todos (llamada modelo Lambert) tiene la forma:


Es decir, el color del vértice bajo iluminación difusa se calcula multiplicando el color de la superficie, el color de la fuente de luz y el producto escalar de los vectores normales del vértice y la dirección de la luz con los coeficientes de iluminación de atenuación y proyección. Esta operación se realiza para cada fuente de luz en la escena, de ahí el símbolo de suma al comienzo de la ecuación.

Los vectores en esta ecuación (y todo lo que vemos a continuación) están normalizados (como se muestra en los iconos sobre cada vector). El vector normalizado conserva su dirección original, y su longitud disminuye a un valor unitario (es decir, igual a 1 unidad de medida).

Los valores de color de la superficie y la fuente de luz son números RGBA estándar (rojo, verde, azul y transparencia alfa). Pueden ser enteros (por ejemplo, INT8 para cada canal de color), pero casi siempre son números de coma flotante (por ejemplo, FP32). El coeficiente de atenuación determina cómo disminuye el nivel de iluminación cuando se aleja de la fuente, y se calcula mediante otra ecuación:


Los términos A C , A L y A Q son coeficientes diferentes (constante, lineal, cuadrático) que describen cómo la distancia afecta el nivel de iluminación. Todos ellos son configurados por programadores al crear un motor de renderizado. En cada API gráfica, esto se implementa a su manera, pero los coeficientes se introducen al codificar el tipo de fuente de luz.

Antes de considerar el último coeficiente (reflector), vale la pena señalar que en la representación 3D hay esencialmente tres tipos de fuentes de luz: punto, direccional y foco.


Las fuentes puntuales emiten luz de manera uniforme en todas las direcciones, y las fuentes direccionales emiten luz en una sola dirección (desde el punto de vista de las matemáticas, esta es solo una fuente puntual, remota a una distancia infinita). Los focos son fuentes direccionales complejas ya que emiten luz en forma de cono. La forma en que la luz varía en el cuerpo del cono determina el tamaño de las partes interna y externa del cono.

Y sí, para el coeficiente del reflector, hay otra ecuación:


El valor del coeficiente del proyector es 1 (es decir, la fuente no es un proyector) o 0 (si el vértice está fuera de la dirección del cono), o algún valor calculado entre los dos. Los ángulos φ (phi) y θ (theta) especifican las dimensiones de la parte interna / externa del cono del foco.

Se usan dos vectores: L dcs y L dir (inverso a la dirección de la cámara y la dirección del foco) para determinar si el cono del vértice se está tocando.

Ahora debemos recordar que todo esto es necesario para calcular el valor de la iluminación difusa, y todas estas operaciones deben realizarse para cadala fuente de iluminación en la escena, o al menos para cada fuente que el programador quería considerar. Muchas de estas ecuaciones se ejecutan mediante API gráficas, pero también se pueden hacer manualmente si los codificadores necesitan más control sobre la imagen.

Sin embargo, en el mundo real, de hecho, hay un número infinito de fuentes de luz: cada superficie refleja la iluminación, por lo que todas afectan la iluminación general de la escena. Incluso por la noche hay iluminación de fondo, ya sean estrellas y planetas o luz dispersa en la atmósfera.

Para simular esto, se calcula otro valor de iluminación: iluminación ambiental .


Esta ecuación es más simple que para la iluminación difusa porque no se requieren direcciones. Aquí, se realiza una simple multiplicación de varios coeficientes:

  • C SA - color de iluminación de superficie
  • C GA : resalte el color de la escena 3D global
  • C LA - color de iluminación de todas las fuentes de luz en la escena

Vale la pena señalar que la atenuación y los coeficientes del proyector se utilizan nuevamente, así como la suma de todas las fuentes de luz.

Por lo tanto, tenemos iluminación de fondo y tomamos en cuenta la iluminación difusa de las fuentes de luz de varias superficies del mundo 3D. Pero el modelo Lambert funciona solo para materiales que reflejan la iluminación de su superficie en todas las direcciones; los objetos hechos de vidrio o metal crean otro tipo de reflejo llamado especular ; ¡Naturalmente, también hay una ecuación para él!


Las partes individuales de esta fórmula ya deberían serle familiares: tenemos dos valores del color del espejo (uno para la superficie - C S , el otro para la luz - C LS ), así como los factores habituales de atenuación e inundación.

Dado que la reflexión especular está muy enfocada y dirigida, se utilizan dos vectores para determinar el brillo de la iluminación especular: el vértice normal y el semi-vector. El coeficiente p se llama el poder de la reflexión especular , este es un número que determina el brillo de la reflexión dependiendo de las propiedades del material de la superficie. A medida que aumenta p, el efecto espejo se vuelve más brillante, pero más enfocado y más pequeño.

El último elemento a considerar es el más simple porque es solo un número. Se llama iluminación emisiva , y se aplica a objetos que son una fuente directa de iluminación, es decir, a una llama, una linterna o al Sol.

Esto significa que ahora tenemos un número y tres conjuntos de ecuaciones para calcular el color del vértice de la superficie, teniendo en cuenta la iluminación de fondo (ambiente), así como la interacción entre diferentes fuentes de luz y las propiedades del material de la superficie (difuso y especular). Los programadores pueden elegir solo uno o combinar los cuatro simplemente doblándolos.


Visualmente, la combinación se ve así:


Las ecuaciones consideradas por nosotros se aplican mediante API gráficas (por ejemplo, Direct3D y OpenGL) utilizando sus funciones estándar, pero para cada tipo de iluminación existen algoritmos alternativos. Por ejemplo, la iluminación difusa se puede implementar utilizando el modelo Oren-Nayyar , que es más adecuado para superficies muy rugosas que el modelo Lambert.

La ecuación de reflexión de espejo puede reemplazarse por modelos que tengan en cuenta el hecho de que las superficies muy lisas como el vidrio o el metal todavía son rugosas, pero a nivel microscópico. Dichos modelos, llamados algoritmos de micro facetas , a costa de la complejidad matemática, proporcionan imágenes más realistas.

Independientemente del modelo que se utilice, todos mejoran enormemente al aumentar la frecuencia de su aplicación en la escena 3D.

Vértice o cálculos píxel por píxel


Cuando examinamos el procesamiento de vértices y la rasterización , vimos que los resultados de todos los cálculos de iluminación difíciles realizados para cada vértice deberían interpolarse sobre la superficie entre los vértices. Esto se debe a que las propiedades asociadas con el material de la superficie se almacenan dentro de los vértices; cuando el mundo 3D se comprime en una cuadrícula de píxeles 2D, los píxeles permanecen solo donde estaba el vértice.


El resto de los píxeles necesitan transmitir información sobre el color de los vértices para que los colores se mezclen correctamente en la superficie. En 1971, Henri Gouraud , entonces un estudiante graduado en la Universidad de Utah, propuso un método ahora llamado Gouraud Shading .

Su método fue computacionalmente rápido y durante muchos años se convirtió en el estándar de facto , pero también tuvo problemas. No podía interpolar correctamente la iluminación del espejo, y si el objeto estaba compuesto por un pequeño número de primitivas, la mezcla entre las primitivas parecía errónea.

En 1973, Bui Tyong Fong, quien también trabajó en la Universidad de Utah, propuso una solución a este problema. En su artículo de investigación, Fong demostró una técnica para interpolar las normales de vértices en superficies rasterizadas. Esto significaba que los modelos de reflexión especular y dispersa funcionarían correctamente para cada píxel, y podemos ver esto claramente en los gráficos por computadora en línea de David Eck y el tutorial WebGL.

Las esferas de carbono que se muestran a continuación están coloreadas con el mismo modelo de iluminación, pero para los cálculos zurdos se realizan verticalmente, seguidos del sombreado de Gouraud para interpolarlos en toda la superficie. Para la esfera de la derecha, los cálculos se realizan píxel por píxel, y la diferencia es obvia.


Las imágenes fijas no transmiten todas las mejoras que trajo el sombreado sobre Phong , pero puede ejecutar de forma independiente la demostración en línea de Ek y ver la animación.

Sin embargo, Fong no se detuvo allí, y un par de años después publicó otro artículo de investigación en el que mostró cómo se pueden realizar cálculos separados para la reflexión ambiental, difusa y especular con una ecuación simple:


¡Aquí tenemos que entenderlo seriamente! Los valores indicados por la letra k son las constantes de reflexión para las reflexiones ambientales, difusas y especulares. Cada uno de ellos es una fracción del tipo correspondiente de luz reflejada de la magnitud de la luz incidente; Valores de C que vimos en las ecuaciones anteriores (valores de color del material de la superficie para cada tipo de iluminación).

El vector R es el vector de "reflexión perfecta": la dirección en la que la luz reflejada se movería si la superficie fuera perfectamente lisa; Se calcula utilizando la superficie normal y el vector de luz incidente. El vector C es el vector de dirección de la cámara; y R y C están normalizados.

Finalmente, existe la última constante en la ecuación: el valor de α determina el grado de brillo de la superficie. Cuanto más liso sea el material (es decir, cuanto más se parezca al vidrio o al metal), mayor será el número.

Esta ecuación generalmente se llama modelo de reflexión de Phong . En el momento de su investigación, dicha propuesta era radical, porque requería recursos informáticos serios. Jim Blinn creó una versión simplificada del modelo , reemplazando la parte de la fórmula de R y C a H y N (vector de media distancia y superficie normal). El valor de R debe calcularse para cada fuente de luz y para cada píxel en el cuadro, yH es suficiente para calcular una vez para cada fuente y para toda la escena.

El modelo de reflexión Blinn-Fong es hoy el sistema de iluminación estándar y se usa por defecto en Direct3D, OpenGL, Vulkan, etc.

Hay muchos otros modelos matemáticos, especialmente ahora que las GPU pueden procesar píxeles en sombreadores largos y complejos; juntas, tales fórmulas se denominan funciones de distribución de transmisión / reflectancia bidireccional (BRDF / BTFD); son la base para colorear cada píxel en el monitor cuando jugamos juegos 3D modernos.

Sin embargo, hasta ahora hemos considerado solo superficies que reflejan la luz: los materiales translúcidos transmiten luz, mientras que los rayos de luz se refractan. Y algunas superficies. por ejemplo, el agua refleja y transmite luz en diferentes grados.

Llevamos la iluminación a un nuevo nivel


Echemos un vistazo al juego 2018 Ubisoft Assassin's Creed: Odyssey , en el que el jugador a menudo navega en el agua, tanto en ríos poco profundos como en aguas profundas.


Madera pintada, metal, cuerdas, tela y agua: todo esto refleja y refracta la luz mediante un montón de cálculos.

Para obtener la representación más realista del agua y mantener una velocidad suficiente del juego, los programadores de Ubisoft utilizaron una serie de trucos. La superficie del agua está iluminada por el trío familiar de luz ambiental, difusa y especular, pero se complementan con características interesantes.

El primero de ellos se usa a menudo para generar las propiedades reflectantes del agua: estos son reflejos de espacio de pantalla (SSR). Esta técnica representa la escena, pero los colores de los píxeles dependen de la profundidad de cada píxel, es decir. desde su distancia a la cámara. La profundidad se almacena en el denominado búfer de profundidad. Luego, el marco se renderiza nuevamente con toda la iluminación y texturas habituales, pero la escena se guarda como textura de renderizado y no como un búfer listo que se transmite al monitor.

Después de eso, se realiza la marcha de rayos . Para hacer esto, se emiten rayos desde la cámara y se establecen distancias a lo largo del curso del haz. El código verifica la profundidad del haz en relación con los píxeles en el búfer de profundidad. Si tienen el mismo valor, el código verifica el píxel normal para ver si está dirigido a la cámara, y si es así, el motor busca el píxel correspondiente a partir de la textura de renderizado. Luego, otro conjunto de instrucciones invierte la posición del píxel para que se refleje correctamente en la escena.


La orden SSR utilizada en el motor Frostbite de EA.

Además, la luz se dispersa durante el movimiento dentro de los materiales, y para materiales como el agua o el cuero, se utiliza otro truco llamado dispersión por debajo de la superficie (SSS). No lo explicaremos en detalle, pero puede leer cómo se usa para crear resultados tan sorprendentes en la presentación de Nvidia 2014 .


Demostración de FaceWorks 2013 de Nvidia ( enlace )

Volvamos al agua de Assassin's Creed: la implementación de SSS apenas se nota aquí, y debido a consideraciones de velocidad, no se usa tan activamente. En juegos anteriores de la serie AC, Ubisoft usaba SSS falsos , pero en el último juego su uso es más complicado, pero aún no tan grande como vimos en la demostración de Nvidia.

Para cambiar los valores de iluminación en la superficie del agua, se realizan procedimientos adicionales que simulan correctamente los efectos de la profundidad debido a un cambio en la transparencia dependiendo de la distancia a la costa. Y cuando la cámara mira el agua cerca de la costa, se utilizan aún más algoritmos para tener en cuenta la cáustica y la refracción.

Los resultados son impresionantes:


Assassin's Creed: Odyssey: representa el agua en todo su esplendor.

Observamos el agua, pero ¿qué pasa con el movimiento de la luz en el aire? Las partículas de polvo, la humedad y otros elementos también conducen a la dispersión de la luz. Como resultado, los rayos de luz reciben volumen y no permanecen solo como un conjunto de rayos directos.

El tema de la iluminación volumétrica se puede extender a una docena de artículos, por lo que hablaremos sobre cómo el juego Rise of the Tomb Raider lo aborda . En el video a continuación, solo hay una fuente principal de iluminación: el sol brilla a través de la abertura del edificio.


Para crear un volumen de luz, el motor del juego toma la pirámide de visibilidad de la cámara (ver más abajo) y la divide exponencialmente en 64 partes. Luego, cada segmento se rasteriza en cuadrículas con un tamaño de 160 x 94 elementos, y todos estos datos se guardan en una textura de representación tridimensional del formato FP32. Como las texturas suelen ser bidimensionales, los "píxeles" del volumen de la pirámide se denominan vóxeles .


Para un bloque de vóxel de 4 x 4 x 4, los sombreadores computacionales determinan qué fuentes de luz activas afectan este volumen y luego escriben esta información en otra textura de representación tridimensional. Luego, para estimar la "densidad" total de luz dentro del bloque de vóxel, se utiliza una fórmula compleja llamada función de dispersión de Hengy-Greenstein .

Luego, el motor realiza varios sombreadores más para refinar los datos, después de lo cual se realiza la marcha de rayos a lo largo de las rebanadas de la pirámide con la acumulación de valores de densidad de luz. ¡Eidos-Montréal afirma que en Xbox One todas estas operaciones toman aproximadamente 0.8 milisegundos!

Aunque esta técnica no se usa en todos los juegos, los jugadores esperan ver una cobertura volumétrica en casi todos los juegos 3D populares lanzados hoy, especialmente en juegos de disparos en primera persona y juegos de acción y aventura.


La iluminación volumétrica utilizada en la secuela de Rise of the Tomb Raider de 2018.

Inicialmente, esta técnica de iluminación se llamaba "rayos divinos" o, como se los llama en términos científicos, "rayos crepusculares" . Uno de los primeros juegos en los que se utilizó fue el primer Crysis de Crytek, lanzado en 2007.

Sin embargo, esta no era la verdadera iluminación volumétrica: el proceso incluía la representación inicial de la escena en forma de un búfer de profundidad, que se usaba como una máscara, otro búfer en el que los colores de los píxeles se volvían más oscuros cuanto más se acercaban a la cámara.

Este búfer de máscara se muestreó varias veces, y el sombreador tomó muestras y las mezcló difuminando. El resultado de esta operación se mezcló con la escena terminada:


El progreso de las tarjetas gráficas en los últimos 12 años ha sido tremendo. Las GPU más potentes en el momento del lanzamiento de Crysis fueron las Nvidia GeForce 8800 Ultra . La GPU moderna más rápida: la GeForce RTX 2080 Ti tiene más de 30 veces más potencia informática, 14 veces más memoria y 6 veces más ancho de banda.

Con toda esta potencia informática, los juegos modernos pueden proporcionar una precisión gráfica y una velocidad general mucho mayores, a pesar de la mayor complejidad del renderizado.


"Divine Rays" en The Division 2 de Ubisoft

Pero, de hecho, este efecto demuestra que, a pesar de la importancia de una iluminación correcta para la precisión visual, la ausencia de luz es aún más importante .

Esencia de la sombra


Comencemos una nueva sección del artículo con el juego Shadow of the Tomb Raider . En la imagen a continuación, todas las opciones de gráficos relacionadas con las sombras están deshabilitadas; a la derecha están incluidos. La diferencia es enorme, ¿verdad?


Dado que las sombras se forman naturalmente en el mundo real, los juegos en los que se implementan incorrectamente nunca se verán bien. Nuestros cerebros están acostumbrados a usar sombras como soporte visual para crear una sensación de profundidad relativa, ubicación y movimiento. Pero hacerlo en un juego 3D es sorprendentemente difícil, o al menos difícil hacerlo bien.

Comencemos con el pato. Aquí se está moviendo por el campo, y los rayos del sol la alcanzan y están bloqueados correctamente.


Una de las primeras formas de implementar la sombra en la escena fue agregar una sombra "puntual" debajo del modelo. Esto es completamente poco realista, porque la forma de la sombra no coincide con la forma del objeto que proyecta la sombra; Sin embargo, este enfoque es rápido y fácil de crear.

Los primeros juegos en 3D, por ejemplo, el primer Tomb Raider de 1996, utilizaron este método porque el hardware de esa época, por ejemplo, Sega Saturn y Sony PlayStation, no podían proporcionar nada mejor. Este método pintó un conjunto simple de primitivas justo encima de la superficie sobre la que se mueve el modelo, y luego las sombreó; También se utilizó el dibujo en la parte inferior de una textura simple.


Otro de los primeros métodos fue proyectar sombras . En este caso, la primitiva que emitía una sombra se proyectaba sobre un plano que contenía el piso. Parte de los cálculos matemáticos necesarios para esto fue creado por Jim Blinn a finales de los 80. Según los estándares modernos, este es un proceso simple y funciona mejor para objetos estáticos simples.


Pero gracias a la optimización, la proyección de sombras proporcionó la creación de los primeros ejemplos dignos de sombras dinámicas, por ejemplo, en el juego de 1999 Kingpin: Life of Crime de Interplay. Como vemos en la imagen a continuación, solo los personajes animados (¡incluso las ratas!) Tienen sombras, pero esto es mejor que simples puntos.


Los problemas más serios con este enfoque son: (a) la opacidad perfecta de la sombra, y (b) el método de proyección emite la sombra en una superficie plana (por ejemplo, en el suelo).

Estos problemas se pueden resolver aplicando una fracción de transparencia al colorear la primitiva proyectada y realizar varias proyecciones para cada personaje, pero las capacidades de hardware de PC de finales de los 90 no pudieron hacer frente a la representación adicional.

Tecnología moderna para crear sombras.


Una forma más precisa de implementar sombras se propuso mucho antes, ya en 1977. Mientras trabajaba en la Universidad de Austin (Texas), Franklin Crowe escribió un artículo de investigación en el que propuso varias técnicas utilizando volúmenes de sombra.

En términos generales, se pueden describir de la siguiente manera: el proceso determina qué primitivas se dirigen hacia la fuente de luz; sus costillas se estiran hasta un avión. Si bien esto es muy similar a proyectar sombras, la diferencia importante es que el volumen creado de sombras se usa para verificar si el píxel está dentro / fuera del volumen. Gracias a esta información, se pueden emitir sombras en todas las superficies, no solo en el suelo.

Esta técnica fue mejorada en 1991 por Tim Heidmann, quien trabajó enGráficos de silicio . Mark Kilgard se involucró en su desarrollo posterior en 1999 , y el método que consideraremos fue creado en 2000 por John Carmack de id Software (aunque el método de Carmack fue abierto independientemente dos años antes por Bilodo y Songa de Creative Labs; esto llevó a que Carmack se vio obligado a cambiar su código para evitar problemas legales).

Este enfoque requiere la representación de múltiples cuadros (llamada representación multipass , un proceso muy costoso a principios de los 90 que se usa en todas partes hoy en día) y un concepto llamado búfer de plantilla .

A diferencia de los buffers y profundidades de cuadros, no es creado por la escena 3D en sí misma: este buffer es una matriz de valores iguales en todas las dimensiones (es decir, resolución en x e y ) en forma de ráster. Los valores almacenados en él se utilizan para indicarle al motor de representación qué hacer con cada píxel en el búfer de cuadros.

El ejemplo más simple de usar este búfer es usarlo como una máscara:


El método con el volumen de sombras se realiza aproximadamente así:

  • Representamos la escena en el búfer de cuadro, pero solo usamos la iluminación ambiental (también incluimos todos los valores de emisión si el pixel contiene una fuente de luz)
  • , , ( (back-face culling)). (, ) . (.. «») - .
  • , (front-face culling) -, .
  • , , -.

Estos búferes de plantilla y volúmenes de sombra (comúnmente llamados sombras de plantilla) se usaron en el juego Doom 3 id Software de 2004 :


¿Te das cuenta de que la superficie sobre la que camina el personaje todavía es visible a través de la sombra? Esta es la primera ventaja sobre la proyección de sombras. Además, este enfoque le permite tener en cuenta la distancia desde la fuente de luz (como resultado, se obtienen sombras más débiles) y proyectar sombras sobre cualquier superficie (incluido el propio personaje).

Pero esta técnica tiene serios inconvenientes, el más notable de los cuales es que los bordes de la sombra dependen completamente del número de primitivas utilizadas para crear el objeto que proyecta la sombra. Además, el multipassing está asociado con muchas operaciones de lectura / escritura en la memoria local, por lo que el uso de sombras de plantilla es bastante costoso en términos de rendimiento.

Además, hay un límite en el número de volúmenes de sombra, que se puede verificar utilizando el búfer de plantilla, porque todas las API gráficas asignan un número bastante pequeño de bits (generalmente solo 8). Sin embargo, debido al costo computacional de las sombras de plantilla, este problema generalmente no surge.

Hay otro problema: las sombras mismas están lejos de ser realistas. ¿Por qué? Debido a que todas las fuentes de luz (lámparas, llamas abiertas, linternas y el Sol) no son puntos únicos en el espacio, es decir emiten luz de alguna área. Incluso en el caso más simple que se muestra a continuación, las sombras reales rara vez tienen bordes bien definidos.


La región más oscura de las sombras se llama sombra completa (umbra); la penumbra siempre es una sombra más clara, y el borde entre los dos a menudo está borroso (porque generalmente hay muchas fuentes de luz). Es difícil modelar esto con búferes de plantilla y volúmenes, ya que las sombras creadas se almacenan en una forma incorrecta para que puedan procesarse. ¡El mapeo de sombras viene al rescate !

El procedimiento básico fue desarrollado en 1978 por Lance Williams . Es bastante simple:

  • Para cada fuente de luz, renderizamos la escena desde el punto de vista de esta fuente, creando una textura especial de las profundidades (es decir, sin color, iluminación, textura, etc.). La resolución de este búfer no tiene que ser igual al tamaño del cuadro terminado, pero cuanto mayor sea, mejor.
  • , ( x,y z) , .
  • : , .

Obviamente, este es otro procedimiento de varias pasadas, pero el último paso se puede realizar utilizando sombreadores de píxeles para que la verificación de profundidad y los cálculos de iluminación posteriores se combinen en una sola pasada. Y dado que todo el proceso de creación de sombras no depende de la cantidad de primitivas utilizadas, es mucho más rápido que usar el búfer de plantilla y el volumen de sombras.

Desafortunadamente, la técnica básica descrita anteriormente genera todo tipo de artefactos visuales (por ejemplo, alias de perspectiva , "acné en la sombra" , "peter panning"), la mayoría de los cuales están relacionados con la resolución y el tamaño de bits de la textura de profundidad. Todas las GPU y las API de gráficos tienen limitaciones similares a las texturas, por lo que se ha creado un conjunto completo de técnicas adicionales para resolver estos problemas.

Una de las ventajas de usar texturas para obtener información de profundidad es que las GPU pueden muestrearlas y filtrarlas muy rápidamente y de muchas maneras diferentes. En 2005, Nvidia demostró un método de muestreo de textura que podría resolver algunos de los problemas visuales causados ​​por el sombreado estándar. Además, proporcionó un cierto grado de suavidad de los bordes de las sombras; Esta técnica se llama filtrado porcentual más cercano .


Casi al mismo tiempo, Futuremark demostró el uso de mapas de sombras en cascada (CSM) en 3DMark06 . Esta es una técnica en la que para cada fuente de luz se crean varias texturas de profundidad con diferentes resoluciones. Las texturas de alta resolución se usan cerca de la fuente y más abajo, a una distancia de la fuente. El resultado son transiciones de sombras más suaves en la escena sin distorsión.

Donnelly y Loritzen mejoraron esta técnica en 2006 en su procedimiento de mapeo de sombras de varianza (VSM), así como Intel en 2010 en su algoritmo de distribución de muestras (SDSM).


Uso de SDSM en Shadow of the Tomb Raider

Para mejorar la imagen, los desarrolladores de juegos a menudo usan todo un arsenal de técnicas de sombreado, pero el principal sigue siendo el mapeo de sombras. Sin embargo, solo se puede aplicar a un pequeño número de fuentes de luz activas, porque si intenta modelarlo para cada superficie que refleje o emita luz, la velocidad de fotogramas disminuirá catastróficamente.

Afortunadamente, hay una técnica conveniente que funciona con cualquier objeto. Da la impresión de una disminución en el brillo de la iluminación que llega al objeto (debido al hecho de que él u otros objetos bloquean un poco la luz). Esta característica se llama oclusión ambiental.y ella tiene muchas versiones. Algunos de ellos están especialmente diseñados por fabricantes de hardware, por ejemplo, AMD creó HDAO ( oclusión ambiental de alta definición ) y Nvidia tiene HBAO + ( oclusión ambiental basada en el horizonte ).

Cualquiera que sea la versión utilizada, se aplica después de que la escena se renderiza por completo, por lo tanto, se clasifica como un efecto de procesamiento posterior . De hecho, para cada píxel se calcula cuánto lo vemos en la escena (más sobre esto aquí y aquí ) comparando el valor de la profundidad del píxel con los píxeles que lo rodean en el punto correspondiente en el búfer de profundidad (que, de nuevo, se almacena como una textura).

Muestrear el búfer de profundidad y luego calcular el color final del píxel juega un papel importante para garantizar la calidad de la oclusión ambiental; Como en el caso del sombreado, todas las versiones de oclusión ambiental para su correcto funcionamiento requieren que el programador configure y ajuste cuidadosamente el código según la situación.


Shadow of the Tomb Raider sin AO (izquierda) y con HBAO + (derecha)

Sin embargo, cuando se implementa correctamente, este efecto visual deja una profunda impresión. En la imagen de arriba, preste atención a las manos, piñas y plátanos de la persona, así como a la hierba y la vegetación circundantes. Los cambios de color de píxeles HBAO + son bastante menores, pero todos los objetos ahora se ven mejor integrados en el entorno (a la izquierda parece que una persona está colgando del suelo).

Si selecciona cualquiera de los últimos juegos discutidos en este artículo, entonces la lista de técnicas de renderizado utilizadas en ellos al procesar luces y sombras será la longitud del artículo en sí. Y aunque no todos los juegos 3D nuevos cuentan con todas estas tecnologías, los motores de juegos universales como Unreal le permiten habilitarlos opcionalmente, y los kits de herramientas (por ejemplo, las compañías de Nvidia) proporcionan un código listo para ser insertado en el juego. Esto demuestra que no son métodos ultramodernos altamente especializados, que alguna vez fueron propiedad de los mejores programadores, ahora están disponibles para cualquiera.

No podemos completar este artículo sobre iluminación y sombras sin mencionar el trazado de rayos. Ya hemos hablado sobre este proceso en esta serie de artículos, pero el nivel actual de desarrollo tecnológicorequiere soportar una baja tasa de cuadros y un desembolso de efectivo serio.

Sin embargo, la tecnología es compatible con las consolas de próxima generación Microsoft y Sony, lo que significa que en los próximos años, su uso se convertirá en otra herramienta estándar para los desarrolladores de todo el mundo que buscan mejorar la calidad visual de los juegos. Solo mira lo que Remedy logró en su último juego de Control :


¡Hemos recorrido un largo camino desde sombras falsas en texturas e iluminación ambiental simple!

Eso no es todo


En el artículo, tratamos de hablar sobre los cálculos matemáticos fundamentales y las técnicas utilizadas en los juegos 3D, que los hacen lo más realistas posible. También examinamos las tecnologías subyacentes al modelado de la interacción de la luz con objetos y materiales. Pero todo esto fue solo la punta del iceberg.

Por ejemplo, omitimos temas como iluminación que ahorra energía, destello de lente, floración, renderizado altamente dinámico, transferencia de radiación, corrección de tono, niebla, aberración cromática, mapeo de fotones, cáusticos, radiosidad: esta lista continúa. Un breve estudio requeriría 3-4 artículos más.

All Articles