Stratos: Punto de Encuentro de Desarrolladores

¡Bienvenido a Stratos!

Acceder

Foros





Foco de luz en 2d usando OpenGL

Iniciado por javiel, 30 de Marzo de 2007, 04:09:16 PM

« anterior - próximo »

javiel

La verdad que no se si esto facilita usar opengl, pero bueno

Lo que estoy intentando hacer es en un mapa cualquier poder poner un poco de luz para que se vea sólo una parte del mapa y la otra parte quede oscura. Pongo una imagen para que veais mas claro lo que quiero hacer



La cosa es que cuando te muevas por el mapa la luz irá cambiando. No se si tengo que iluminar la escena con OpenGL, no se si tendría que hacer una especie de máscara, la verdad que no tengo ni idea de como plantearme el problema. Además el juego va en isométrico y no se si cambia bastante de lo que he puesto.

Otra cosa es que además del mapa tengo los paneles del juego, donde estás los puntos y más datos. No se si la luz afectaría también a esta parte

La verdad que tengo muchas dudas. ¿alguien me podría orientar mas o menos para saber por donde tengo que buscar información?

gracias
uper-Tirititran: el superhéroe gaditano (http://www.super-tirititran.com)

killrazor

El problema de la luz es que la luz en opengl funciona por vertices. Tal como lo tienes, parece que la iluminacion seria de la imagen que tienes como mapa de TILES. Que siginifica eso? Que cambiando la luz podras iluminar todo mas  o menos pero todo. Y lo veras todo mas claro o mas oscuro.

Mi solucion es una imagen negra con un circulo en el centro y usar blending para la semitransparencia y la transparencia.

Fran

Yo eso no lo plantearía como luz, sino como mezcla de texturas o como lightmap con alpha blending

javiel

gracias por vuestras respuestas.

Lo del tema del poner el círculo negro, es una posiblidad pero no se si hay soluciones mejores

Lo del tema que comenta fran ¿podías ortientarme un poco mejor sobre tus dos propuestas? Un poco más de información si no te importa para poder estudiarlas

muchas gracias
uper-Tirititran: el superhéroe gaditano (http://www.super-tirititran.com)

tamat

usa glEnable( GL_BLEND ) y glBlendFunc. Creo que con eso te bastaría.
Por un stratos menos tenso

Fran

Si. Imagino q estarás haciendolo con poligonos 2D, haciendo mapeado de texturas. Pues se trata de q te hagas una textura negra con un circulo blanco en el centro, hagas un enable blending, pongas un alpha de 0.5 p.e. y mapees esa textura como textura 1 (de texturas ARB) con GL_ALPHA,GL_ONE_MINUS_SRC_ALPHA en glBlendFunc sobre la otra. No lo he probado en 2D pero imagino q funcionará igual q en 3D

marcode

Pues igual daría mejor efecto una luz normal, aunque ilumine polígonos planos. por ejemplo los personajes y objetos podrían "tomar" más luz, pareciendo que les incide directamente por igual, al contrario que el suelo, que a medida que se aleja se oscurece.

El lightmap tal y como se muestra en la imagen anterior da sensación de iluminación falsa, como si se mirase a través de un filtro.

Yo probaría con luces "reales" a ver cómo queda.
size=9]afortunadamente siempre ha habido alguien dispuesto a reinventar la rueda, de lo contrario seguiríamos usando un disco de piedra con un agujero.[/size]

marcode

Yo probaría con luces "reales" a ver cómo queda, aunque ilumine polígonos planos. por ejemplo los personajes y objetos podrían "tomar" más luz, pareciendo que les incide directamente por igual, al contrario que el suelo, que a medida que se aleja se oscurece.

Modificando las normales de cada vértice del sprite serían posibles ese, y otros efectos realistas. Incluso apuntando las normales hacia el exterior se podría conseguir sensación de sombreado en la zona opuesta a la luz.

El lightmap tal y como se muestra en la imagen anterior no da sensación de iluminación, es como si se mirase a través de un filtro.
size=9]afortunadamente siempre ha habido alguien dispuesto a reinventar la rueda, de lo contrario seguiríamos usando un disco de piedra con un agujero.[/size]

TrOnTxU

Yo tb creo que deberias probar con luces antes de meter la "mascara".
Si tienes miedo de iluminar el GUI o otras cosas acuerdate de dibujarlas despues de desactivar las luces, esto seria:

glEnable(GL_LIGHTING);
... // dibujar los tiles
glDisable(GL_LIGHTING);
... // dibujar la GUI


Creo que GL_LIGHTING està bien escrito, sino pegale un ojo a la documentación del OpenGl.

Un saludo

PS: mi recomendación seria que aun con un fondo formado por tiles los personajes deberian estar en 3dimensiones, ya que quedaria mejor la iluminación. Pero no me hagas demasiado caso ;P es solo una opinión.
Vicent: Linked-In  ***  ¡¡Ya tengo blog!!

Fran

Si quieres conseguir exactamente el efecto q has puesto, la manera más sencilla es la que te he puesto. Aunque lo otro tb funcionaría, pero CREO q el efecto no sería tan de marcar el terreno. Más que nada xq la malla de tríangulos que tendrías que hacer sería bastante tupida para conseguir ese efecto

javiel

sigo con las pruebas. De principio con las luces no estoy haciendo nada, aunque quiero probar a ver que tal.

Las pruebas las estoy haciendo con la máscara, pero no me salen como yo quiero realmente, aunque como yo quiero no se si se puede hacer ;-)

He puesto la máscara. Tengo la imagen y luego otra con fondo negro y círculo en blanco. Y sale esto:



He estado haciendo pruebas y la única forma ha sido poniendo el BLEND así:

glBlendFunc(GL_DST_COLOR,GL_ZERO);

Los BLEND de las otras imágenes (las de debajo) los tengo así:

glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

La cosa es que de principio esto lo podría hacer perfectamente con un PNG con un círculo transparente en medio, o sea, que tampoco es que halla avanzado demasiado.

La cuestión es que la imagen con el fondo negro es muy grande y si la moviese pues tendría que se 2 veces más grande que la pantalla para que cubriese todo. Imaginemos que quiero hacer algo como 007 cuando sale al principio de la película con el circulo buscándolo. Si tengo un círculo como este, para poder moverlo por pantalla cómodamente:



Me saldría algo así:



Y yo quisiera que saliera algo así:



No se si esto es posible, ya que la imagen negra no es tan grande, a ver que opináis

¿es posible?
uper-Tirititran: el superhéroe gaditano (http://www.super-tirititran.com)

Fran

Para empezar lo de abajo no tienes q hacerlo con ninguna glBlendFunc. Es lo de arriba (el PNG negro con el circulo blanco ) el q tienes q renderizar con GL_ALPHA (y perdón) GL_ONE para el fondo. GL_ALPHA se le aplica al agujero, y GL_ONE como 2º parámetro quiere decir q lo del fondo te lo deje como está:

glBlendFunc(GL_SRC_ALPHA,GL_DST_ONE)

Para seguir, entiendo que tienes q tener un PNG de grande como la cámara, nada más. Y saberlo poner frente a ella para q esté centrado en ella sin tener q ser tan grande como describes. Por cierto. No tienes xq guardarlo. Hay formas de montar texturas en memoria y dibujar sobre ellas. Yo te podría decir como se hace en Java.

javiel

he hecho lo que me has dicho Fran usando

glBlendFunc(GL_SRC_ALPHA,GL_ONE)

pq GL_DST_ONE no existe

pero me sale lo siguiente:



haciendolo como te dije antes me sale bien, pero como te digo es lo mismo que poner una imagen negra con el circulo transparente

No se que hacer, o si se puede hacer

Por otro lado estoy interesado en lo que comentas de poder crear texturas. Si me puedes poner el código en JAVA y a ver si lo entiendo para pasar a c++ o si tiene (o alguien tiene) algún site donde lo explique en c++ mejor

muchas gracias
uper-Tirititran: el superhéroe gaditano (http://www.super-tirititran.com)

senior wapo

Haz esto:

1. Para que te llene toda la pantalla el efecto:
Opcional: Pon el modo de direccionamiento de texturas en "clamp to edge" (googlea GL_CLAMP y GL_CLAMP_TO_EDGE). Eso hará que si pones coordenadas que se salen del tamaño de la textura te use para esos pixels los de los extremos (deja el borde negro que tienes en la imagen no hagas que el circulo toque los limites de la textura).
Luego dibujas un quad que ocupe toda la pantalla ajustando las coordenadas de textura al tamaño de la pantalla y posición deseada de la luz.

Si esto te parece complicado, hazlo como ahora pero dibuja quads negros en las 8 casillas que quedan alrededor

2. Metele un paso de blur a la máscara en un programa de dibujo, los bordes del foco tan recortados queda feo.

3. Para que la zona oscura no sea negra sino el fondo muy oscurecido. Prueba este blend al dibujar la máscara:


glDisable(GL_LIGHTING);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glColor4f( 1.0f, 1.0f, 1.0f, 0.4f ); // Mete 40% transparencia al color

--- dibuja aqui el foco ---

glEnable(GL_LIGHTING);


Si no has tocado nada, el color plano se multiplica con el de la textura en cada pixel, por eso pones un color con el valor máximo en rojo, verde y azul pero menor en el alpha del pixel.

Nota: La imagen de la textura ha de ser un circulo blanco sobre fondo negro, como la que has puesto arriba.

Un saludo.

Fran

Lo q te estoy diciendo de GL_SRC_ALPHA,GL_ONE (No recuerdo pero yo creo que es GL_DST_ONE) es con el alpha activado con glColor4f claro está). El GL_ONE_MINUS_SRC_ALPHA consigue otro efecto y edito, tb te puede valer.




glBlendFunc(GL_SRC_ALPHA, GL_ONE);
glColor4f( 1.0f, 1.0f, 1.0f, alpha ); // Mete 40% transparencia al color

-- dibujar el foco como lo dibujes (triangulos, quad,...)







Stratos es un servicio gratuito, cuyos costes se cubren en parte con la publicidad.
Por favor, desactiva el bloqueador de anuncios en esta web para ayudar a que siga adelante.
Muchísimas gracias.