Finalmente encontré una solución, en realidad algunas soluciones diferentes. Yo no averiguar la causa real del artefacto de un gráfico de programación perspectiva - pero he encontrado algunas soluciones.
Como dije anteriormente en mi pregunta, parecía que el artefacto solo estaba ocurriendo en los volúmenes de sombra calculados previamente de la geometría estática engendrada por el mundo (que es básicamente geometría que el motor sabe que nunca se moverá, por lo que calcula de antemano -time los volúmenes de sombra y otras cosas con un comando ingresado en la consola llamado "dmap"). No entendí por qué solo estaba en las sombras de la geometría estática del engendro del mundo y no en ninguno de los modelos ASE o LWO.
Ahora, lo que noté fue que en realidad hay una gran cantidad de parámetros que se pueden usar con el comando dmap, uno de estos parámetros se llama "shadowOpt", que debe representar el nivel de optimización de la sombra. Este parámetro establece una enumeración; parece haber algunos niveles diferentes de optimización de sombra:
typedef enum {
SO_NONE, // 0 // NOTE: I haven't tried this one yet - should test this one.
SO_MERGE_SURFACES, // 1 // NOTE: this was the original default one - it causes some artifacts - the ones I have been trying to fix.
SO_CULL_OCCLUDED, // 2 // NOTE: this one works the best - takes a bit longer - but it has alot of unnecessary print statements that could probably be removed.
SO_CLIP_OCCLUDERS, // 3 // NOTE: I haven't tried this one yet - but it is not used anywhere.
SO_CLIP_SILS, // 4 // NOTE: I haven't tried this one yet - should test this one.
SO_SIL_OPTIMIZE // 5 // NOTE: this one doesn't seem to work well at all - and it takes an extrememly long amount of time - was probably an expirimental version.
} shadowOptLevel_t;
He tenido éxito con la opción 2: "SO_CULL_OCCLUDED". Soluciona todos los artefactos, tarda un poco más en ejecutarse, pero creo que gran parte de este tiempo se gasta imprimiendo grandes cantidades de información en la consola; estas impresiones probablemente podrían reducirse o eliminarse.
Uno de los lugares que me dio algunas pistas fue el comentario aquí en tr_stencilshadow.cpp:
// if we are running from dmap, perform the (very) expensive shadow optimizations
// to remove internal sil edges and optimize the caps
if ( callOptimizer ) {
Ahora, el problema con solo hacer esta optimización de sombra "extra" durante "dmap" es que si alguna de estas luces se mueve alguna vez (lo cual siempre es posible dependiendo del tipo de proyecto que esté haciendo), entonces volverá por defecto a proceso de creación de volumen de sombra en tiempo real "no optimizado" (para la luz movida) y los artefactos reaparecerán para esa luz. Entonces, la única forma de garantizar que estos artefactos no aparezcan es ejecutar siempre el costoso proceso de optimización para estas sombras estáticas de engendros mundiales. De hecho, es muy costoso, por lo que este sería un último recurso absoluto si no puede encontrar una solución gráfica adecuada. (si lo hace, asegúrese de publicar su solución aquí).
Recomendaría a cualquiera que cree mapas grandes para el motor Vanilla Doom 3, y que use geometría engendrada por el mundo, que creen un cvar que puedan cambiar dependiendo de sus necesidades para la creación en tiempo real de los volúmenes de sombra optimizados. Llamé a mi cvar r_useExpensiveShadowOptimizations, que parece ser un oxímoron. Por ejemplo:
// if we are running from dmap, perform the (very) expensive shadow optimizations
// to remove internal sil edges and optimize the caps
if ( callOptimizer || r_useExpensiveShadowOptimizations.GetBool() ) {
También recomiendo que, dependiendo del tamaño de sus mapas (y suponiendo que las luces no se muevan), aumente el nivel de optimización del volumen de sombra estática con el parámetro "shadowOpt" para dmap.
Entonces, básicamente, todas las cosas que necesita para tener un mapa grande y no tener artefactos de sombra están ahí para usted, solo tiene que decidir cuáles necesitará usar. Hacerlo en tiempo real es extremadamente costoso y solo debe hacerse como último recurso si no puede encontrar una solución gráfica adecuada. Hacerlo en DMAP tiene mucho sentido ya que resuelve el problema y solo toma unos segundos más para que el mapa se compile.