Pregunta

Por defecto parece que los objetos se dibujan de adelante hacia atrás. Estoy dibujando un objeto 2-D UI y me gustaría crearlo de atrás hacia adelante. Por ejemplo, podría crear un cuadrado blanco primero y luego crear un cuadrado negro ligeramente más pequeño encima, creando así un panel negro con un borde blanco. Esta publicación tuvo un debate y describió este orden como & " Algoritmo del pintor " pero en última instancia, el ejemplo que dieron simplemente renderizó los objetos en orden inverso para obtener el efecto deseado. Me imagino de atrás hacia adelante (los primeros objetos van hacia atrás, los objetos posteriores se dibujan en la parte superior) La representación se puede lograr a través de alguna transformación (gOrtho?)?

También mencionaré que no estoy interesado en una solución que use una biblioteca de contenedor como GLUT.

También descubrí que el comportamiento predeterminado en Mac con Cocoa NSOpenGLView parece retroceder al frente, donde, como en Windows, no puedo obtener este comportamiento. El código de instalación en Windows que estoy usando es este:

glViewport (0, 0, wd, ht);
glMatrixMode(GL_PROJECTION);           
glLoadIdentity();                      
glOrtho (0.0f, wd, ht, 0.0f, -1.0f, 1.0f);
glMatrixMode(GL_MODELVIEW);             
glLoadIdentity();                       
¿Fue útil?

Solución

La siguiente llamada desactivará las pruebas de profundidad y hará que los objetos se dibujen en el orden creado. De hecho, esto hará que los objetos retrocedan al frente.

glDepthFunc(GL_NEVER);      // Ignore depth values (Z) to cause drawing bottom to top

Asegúrese de no llamar a esto:

glEnable (GL_DEPTH_TEST);   // Enables Depth Testing

Otros consejos

Para su pregunta específica, no, no hay una forma estandarizada de especificar el orden de profundidad en OpenGL. Algunas implementaciones pueden realizar pedidos de profundidad de adelante hacia atrás de forma predeterminada porque generalmente es más rápido, pero eso no está garantizado (como descubrió).

Pero realmente no veo cómo te ayudará en tu situación. Si dibuja un cuadrado negro delante de un cuadrado blanco, el cuadrado negro debe dibujarse delante del cuadrado blanco, independientemente del orden en que se dibujen, siempre que tenga habilitado el almacenamiento en búfer de profundidad. Si en realidad son coplanarios, ninguno de los dos está realmente frente al otro y cualquier algoritmo de clasificación de profundidad sería impredecible.

El tutorial en el que publicó un enlace solo habló sobre él porque la clasificación en profundidad ES relevante cuando usa transparencia. Pero no me parece que eso sea lo que buscas.

Pero si realmente tiene que hacerlo de esa manera, debe hacerlo usted mismo. Primero envíe su cuadrado blanco a la tubería de renderizado, fuerce el renderizado y luego envíe su cuadrado negro. Si lo hace de esa manera, y deshabilita el almacenamiento en búfer de profundidad, entonces los cuadrados pueden ser coplanares y se le garantizará que el cuadrado negro se dibuja sobre el cuadrado blanco.

El orden de dibujo es difícil. No hay una solución fácil. El alogoritmo del pintor (ordenar objetos por su distancia en relación con la vista de su cámara) es el más sencillo, pero como ha descubierto, no resuelve todos los casos.

Sugeriría una combinación del algoritmo y las capas del pintor. Construye capas para elementos específicos en su programa. Entonces tienes una capa de fondo, capas de objetos, capas de efectos especiales y una capa GUI.

Use el algoritmo del pintor en los elementos de cada capa. En algunas capas especiales (como su capa GUI), no ordene con el algoritmo del pintor, sino por su orden de llamada. Primero llama a ese cuadrado blanco para que se dibuje primero.

Dibuje los elementos que desea colocar detrás de los elementos que desea colocar al frente. Es decir, en realidad cambie el valor z (suponiendo que z sea perpendicular al plano de la pantalla). No tiene que cambiarlo mucho para que los elementos se dibujen uno frente al otro. Y si solo cambia el valor z ligeramente, no debería notar un gran desplazamiento desde su posición deseada. Incluso podría ser realmente elegante y calcular la posición x, y correcta en función de la posición z modificada, para que el elemento aparezca donde se supone que debe estar.

Tus cosas se dibujarán en el orden exacto en el que llamas a las funciones glBegin / glEnd. Puedes obtener un buffer de profundidad usando el z-buffer, y si tus objetos 2d tienen valores z diferentes, puedes obtener el efecto que deseas de esa manera. La única forma en que está viendo el comportamiento que describe en la Mac es si el programa está dibujando cosas en orden inverso al manual o usando el búfer z para lograr esto. De lo contrario, OpenGL no tiene ninguna funcionalidad automáticamente como usted describe.

Como señaló AlanKley, la forma de hacerlo es deshabilitar el búfer de profundidad. El algoritmo del pintor es realmente una técnica de conversión de escaneo 2D utilizada para representar polígonos en el orden correcto cuando no tiene algo como un búfer z. Pero no lo aplicarías a los polígonos 3D. Por lo general, los transformaría y los proyectaría (manejando las intersecciones con otros polígonos) y luego ordenaría la lista resultante de polígonos proyectados en 2D por su coordenada z proyectada, luego los dibujaría en orden z inverso.

Siempre he pensado en el algoritmo del pintor como una técnica alternativa para la eliminación de superficies ocultas cuando no puedes (o no quieres) usar un z-buffer.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top