¿Tiene sentido implementar la lógica para omitir la representación de objetos fuera de la ventana gráfica o no debería importarme y dejar que Framework lo haga?
fuente
¿Tiene sentido implementar la lógica para omitir la representación de objetos fuera de la ventana gráfica o no debería importarme y dejar que Framework lo haga?
El sacrificio es una optimización del rendimiento. Por lo tanto, no tiene sentido hacerlo solo por el simple hecho de hacerlo. Tienes que tener una razón.
La GPU (no el Marco XNA) elimina triángulos y píxeles a una velocidad increíblemente rápida. Cada triángulo que envíe debe transformarse (a través de su sombreador de vértices). Luego se eliminan los que aterrizan fuera de la pantalla. Luego llena los triángulos restantes, eliminando píxeles que están fuera de la pantalla. Los píxeles restantes se dibujan en el búfer posterior (a través de su sombreador de píxeles).
(Cuando digo "entonces", en realidad hace todo esto en una tubería paralela masiva).
Por lo tanto, es muy raro e inusual que tenga que seleccionar triángulos individuales. Para alcanzar los límites de vértice, debes dibujar una cantidad absurdamente grande de triángulos. Para alcanzar los límites de velocidad de relleno, búsqueda de texturas o sombreado de píxeles, generalmente debe tener una alta complejidad de profundidad (en cuyo caso la eliminación de ventana gráfica / frustum no ayudará).
Por lo tanto, generalmente hay poco o ningún costo para tener geometría fuera de la pantalla.
El costo, particularmente en el contexto del dibujo de "objetos" (generalmente objetos 3D), es en realidad enviar esos objetos a la GPU en primer lugar . Envíe demasiados objetos y alcanzará su límite de lote (obtendrá unos pocos miles * lotes por cuadro).
Recomiendo leer esta respuesta y esta plataforma de diapositivas vinculada para obtener una descripción detallada de los lotes.
Debido a esto, si implementa el sacrificio de frustum, puede reducir el número de lotes que envía a la GPU. Si tiene un lote limitado, esto puede llevarlo por debajo del límite.
Ahora, su pregunta es sobre 2D XNA, por lo que presumiblemente está utilizando SpriteBatch
. Esto es un poco diferente.
No es un error que se llame "Sprite Batch ". Lo que está haciendo es tomar los sprites que dibujas y hacer lo mejor posible para enviar esos sprites a la GPU en la menor cantidad de lotes posible al agruparlos.
Pero SpriteBatch se verá obligado a iniciar un nuevo lote si:
Por lo tanto, el sacrificio es una optimización adecuada si se encuentra con la primera. Si está enviando una cantidad tan grande de sprites que termina con demasiados lotes (probablemente también esté utilizando ancho de banda, pero estoy bastante seguro de que primero alcanzará el límite de lote). En general, esto solo sucederá si tienes un mundo realmente enorme, por lo que, en este caso, puedes salirte con la tuya con un sacrificio muy simple, rápido pero impreciso.
Ahora: si está dibujando con suficientes intercambios de textura para superar el límite de lote, y muchos de ellos están realmente fuera de la pantalla y eliminarlos lo colocaría por debajo del límite de lote. Entonces sí, el sacrificio es una optimización que funcionará.
Sin embargo , una mejor optimización a seguir en este caso es usar atlas de textura (también conocido como: hojas de sprites). Esto le permite reducir el número de intercambios de texturas y, por lo tanto, lotes, independientemente de lo que esté en la pantalla o no. (Esta es la razón principal por la que puede especificar un rectángulo de origen para sus sprites).
(Como siempre: este es un consejo sobre la optimización del rendimiento. Por lo tanto, debe medir y comprender el rendimiento de su propio juego y los límites que está alcanzando, antes de gastar esfuerzo en agregar optimizaciones).
De acuerdo con una publicación en los foros de MSDN, el marco XNA no elimina el sacrificio:
http://xboxforums.create.msdn.com/forums/p/22763/121897.aspx
Esta publicación continúa diciendo que si tienes muchos objetos en tu escena, valdría la pena rodar los tuyos.
fuente
He estado desarrollando motores de terreno de vóxeles procesales durante unos años en XNA. En la mayoría de los cuadros, los motores están transformando literalmente cientos de miles de quads. En mi perfil, descubrí que el frustum y la eliminación de oclusiones aumentan el rendimiento.
El perfil XNA HiDef (no Reach) tiene una clase OcclusionQuery que se utiliza para realizar el sacrificio de oclusión. La eliminación de oclusión elimina esos quads de una ventana gráfica que otros quads ocultan a la vista.
Algo más que debe considerar es encabezar tanto la generación como el teselado por separado.
Entonces, sí, cuando se acerque a una gran cantidad de cuadrículas en cada cuadro que se está transformando, debe pensar detenidamente en cómo puede aplicar las técnicas de selección y enhebrado para mantener la velocidad de cuadros, reduciendo el tráfico a los sombreadores de gpu.
fuente