Diciembre 02, 2015, 09:52:38 PM Ultima modificación: Diciembre 03, 2015, 12:57:36 AM por NiuWeb
Hola, estoy haciendo unos cuantos efectos kawaii a mi juego, y entre ellos dibujo una sombra. Al principio tenía algo sencillo, así:
[gml]
//draw Event
draw_sprite_ext(sWall,0,x+4,y+4,c_black,0.6);
draw_self();
[/gml]

Y este código iba de maravilla, se veía algo así:


PEEEEERO como soy bien cool :') decidí agregarle algo más. Unos triángulos en sus esquinas para rellenar los espacios que quedaban, y escribí mi código así:
[gml]
  draw_set_alpha(0.6);
  draw_set_colour(c_black);
  draw_triangle(x+32,y,x+32,y+5,x+37,y+5,false);
  draw_triangle(x,y+32,x+5,y+32,x+5,y+37,false);
  draw_set_alpha(1);
  draw_self();
[/gml]

Bueno, de a uno en uno se ven bien, algo así:


Pero el lio viene cuando agrego varias instancias seguidas, los triángulos (creo que también el sprite) como que se mezclan haciéndolo más opaco y poco estético:

(No sé que tan bien se vea el error)
Mi pregunta es, cómo evitar que estos efectos de dibujo se mezclen, y en vez de eso, se unan con la misma transparencia para evitar que se vean partes más oscuras  ??? :-[
A ver si me expliqué bien...xD :D :D XD XD :-[
alaberga regué el café.

BA:STFW&RTFM

Los empalmes ocurren porque se está dibujando más de una vez lo mismo en en mismo lugar (obvio) y además, con un alfa menor a 1 (pero mayor a 0). Creo que una solución consistiría en llevar un control de las zonas donde se ha dibujado, para no volver a dibujar un triángulo ahí, solución que no me convence del todo. Tampoco veo (no estoy seguro) que usar blend modes + surfaces sea buena solución, porque el código necesario para dibujar algo simple aumentaría, y además, creo que independientemente del modo blend que se use, dibujar dos veces algo con una opacidad intermedia causaría empalmes de todas maneras (no lo puedo asegurar, necesitaría hacer pruebas).

Mi solución:
Usar un simple sprite que ya contenga la forma final deseada. Es decir, una celda azul como la segunda imagen que colocaste.

Resultado:


Quienes hayan usado algo así (cubo con perspectiva), seguramente se han topado con el error de que los cubos se ven desordenados o empalmados (según se los haya colocado en la habitación o creado mediante código). Una solución a este problema es dibujar los cubos siguiendo cierto orden determinado, para que no se vea que el borde de un cubo se empalma con otro de manera rara. Lo que yo hice para evitar este problema fue que cada cubo pregunte si a su izquierda o arriba hay otro cubo (que podría causar el empalme no deseado) si es así, modificar las profundidades de los dos cubos involucrados, de manera que el cubo de arriba (o de la izquierda) cambie su profundidad a una mayor, y así evitar los traslapes.

Seguramente a alguien se le ocurre otra solución. Lo que más quise evitar fue el dibujo recurrente de triángulos.

#2 Diciembre 02, 2015, 11:12:40 PM Ultima modificación: Diciembre 02, 2015, 11:16:44 PM por NiuWeb
Precisamente lo que quise evitar al escribir código para la sombra es modificar el sprite, ya que tengo muchos datos que están relacionados con su tamaño, y tendría que, básicamente reescribir el 50% de mi código, porque también hay muchos códigos de dibujo en su sprite, y necesito poder ocultar/mostrar la sombra sin modificar sprites ya que la sub-imagen es muy importante, y dibuja dos subimágenes al tiempo y blah, blah, blah...
En fin, necesito poder mezclar estas funciones de dibujo sin modificar el sprite. Supongo que esperaré hasta que algún ángel me salve :D
[spoiler]Yo invoco a los dioses Clamud, Guacusio, penumbra, entre otros y pido me brinden su sabiduría!!!![/spoiler]
PD: Lo del sprite fue lo primero que pensé, pero por algo creé el tema :D :-[
alaberga regué el café.

BA:STFW&RTFM

if !place_meeting(x+1,y,obj_wall)
and !place_meeting(x,y+1,obj_wall)
{
     draw_sprite_ext(sWall,0,x+4,y+4,c_black,0.6);
     draw_self();
}


PD: improvisado, a ver si funca :)
[spoiler="ola k ase clickarme o k ase"]la imagen no se quita xD
[/spoiler]

Kostra, igualmente se siguen dibujando, no sé por qué... Aquí está copy-pasteado el código que dengo en el draw del muro:
[gml]
if global.is_editing = false
{
  if !place_meeting(x+1,y,oPixel)
   {
    draw_set_alpha(0.6);
    draw_set_colour(c_black);
    draw_triangle(x+32,y,x+32,y+5,x+37,y+5,false);
    draw_triangle(x,y+32,x+5,y+32,x+5,y+37,false);
    draw_set_alpha(1);
   }
  draw_sprite_ext(sprite_index,0,x+5,y+5,1,1,0,c_black,0.6);
}
draw_sprite_ext(sprite_index,0,x,y,1,1,0,cc,1); //Dibuja una sub-imagen con un color
draw_sprite_ext(sprite_index,1,x,y,1,1,0,c2,1); //dibuja la otra con otro color
[/gml]

Además, hay algunas cosas en el juego que, con colisiones, podrían no funcionar del todo bien. Preferiría, si es posible, usar funciones de dibujo en vez de colisión
alaberga regué el café.

BA:STFW&RTFM

#5 Diciembre 02, 2015, 11:39:24 PM Ultima modificación: Diciembre 02, 2015, 11:51:49 PM por penumbra
Utiliza dos tipos de sombras:



Dependiendo de si a la izquierda o arriba hay otra celda.

Citar
Precisamente lo que quise evitar al escribir código para la sombra es modificar el sprite, ya que tengo muchos datos que están relacionados con su tamaño, y tendría que, básicamente reescribir el 50% de mi código
Esto tiene solución fácil: Usar una sprite como máscara. Para todo lo que tenga que ver con colisiones y tamaños, se usaría la máscara (que no contendría sombra, sólo la forma básica cuadrada). Los demás objetos y código nunca le harían caso a la sombra, ni sabrían que existe.

Por más que intento e intento, me dibuja todos los triángulos sin siquiera hacer caso al place_meeting, es un maldito desobediente mi juego!
Hice estos cambios a ver si funcionaba la fórmula: kostra+penumbra = solución ,pero lo de checkear las colisiones como que no sirve:
[gml]
draw_set_alpha(0.6);
draw_set_colour(c_black);
  if !place_meeting(x,y,oPixel) {
   draw_triangle(x+32,y,x+32,y+5,x+37,y+5,false);
   draw_triangle(x,y+32,x+5,y+32,x+5,y+37,false);
  draw_set_alpha(1); }
draw_sprite_ext(sprite_index,0,x+5,y+5,1,1,0,c_black,0.6);
[/gml]

Cita de: penumbra en Diciembre 02, 2015, 11:39:24 PM
Esto tiene solución fácil: Usar una sprite como máscara. Para todo lo que tenga que ver con colisiones y tamaños, se usaría la máscara (que no contendría sombra, sólo la forma básica cuadrada). Los demás objetos y código nunca le harían caso a la sombra, ni sabrían que existe.
Es que las colisiones no son lo único que cambiaría, tengo más cosas que dependen plenamente de su sprite.
alaberga regué el café.

BA:STFW&RTFM

trankilo, estoy en ello, milimétricamente, espera un poco y ahora te lo posteo :P
[spoiler="ola k ase clickarme o k ase"]la imagen no se quita xD
[/spoiler]

Gracias, espero con ansias  XD XD :'( :D :D :'( :'( :'( :'( :-[ :-X
alaberga regué el café.

BA:STFW&RTFM

#9 Diciembre 03, 2015, 12:10:52 AM Ultima modificación: Diciembre 03, 2015, 12:21:21 AM por penumbra
Esos cambios no servirán para el método de las dos sombras.

"Sé la celda, sé la celda." Repite "Soy la celda".

Soy la celda. Si a mi izquierda o arriba de mi hay otra celda, dibujaré la sombra recortada. En caso contrario, dibujo la sombra normal.

Caso especial: soy una  celda de la última columna de la derecha, y debajo de mi no hay otra celda. Pregunto si a mi derecha y hacia abajo no hay otras celdas. En caso que no haya, dibujo la sombra normal.


Gracias penumbra por esa detallada expllicación, y creo que lo he memorizado, soy la celda...xD
Intentaré hacerlo así a ver qué tal...xD
alaberga regué el café.

BA:STFW&RTFM

TOCHACO ALERT!!!

[gml]draw_set_colour(c_black);
draw_set_alpha(0.6);
if !place_meeting(x+1,y,object_index)
    draw_rectangle(x+32,y+5,x+36,y+31,false);
if !place_meeting(x,y+1,object_index)
    draw_rectangle(x+5,y+32,x+31,y+36,false);
if !place_meeting(x,y-1,object_index)
and !place_meeting(x+1,y,object_index)
    draw_triangle(x+32,y+1,x+36,y+5,x+32,y+5,false);
if !place_meeting(x+32,y+32,object_index)
and place_meeting(x,y+1,object_index)
    draw_rectangle(x+32,y+32,x+36,y+36,false);
if !place_meeting(x,y+1,object_index)
and !place_meeting(x+32,y+32,object_index)
    draw_rectangle(x+32,y+32,x+36,y+36,false);
if !place_meeting(x,y+1,object_index)
and !place_meeting(x-1,y,object_index)
    draw_triangle(x,y+32,x+5,y+32,x+5,y+36,false);
draw_set_alpha(1);
draw_self();[/gml]

muestra:
https://gyazo.com/070157b4b7a8d517671058294a72397b

Lo bueno, al poner object_index, puedes ponerlo en un script y usarlo para cualquier bloque 32x32
[spoiler="ola k ase clickarme o k ase"]la imagen no se quita xD
[/spoiler]

Ay dios mio! se veía tan solucionaproblemas ese código, pero lo voy a probar y PUM! no funcionó  :'(
alaberga regué el café.

BA:STFW&RTFM

usas walls distintos?, es, o son, de 32x32?

PD: si quieres pásame el proyecto por mp
[spoiler="ola k ase clickarme o k ase"]la imagen no se quita xD
[/spoiler]

#14 Diciembre 03, 2015, 12:44:58 AM Ultima modificación: Diciembre 03, 2015, 12:46:44 AM por NiuWeb
Ok, ya... si soy tonto, por dios!!!! :-[ :-[ :-[
Tenía la máscara de colisión descuadrada...xD
Ya!
La vida es bella... :D

dentro de poco marco como solucionado, aún no por si las dudas...xD
alaberga regué el café.

BA:STFW&RTFM