Jump to content
UnitySpain
zelleGames

Duda entre usar enter collider o exit collider (eficiencia)

Recommended Posts

Buenas gente,

Estoy con un nuevo proyecto de plataformas 3D para movil y para controlar si el jugador cae al vacio y muera, he puesto debajo del escenario un box collider, entonces si el jugador entra dentro (EnterCollider) muere.

Probando el juego he visto que si el jugador va muy rapido y salta mucho fuera del escenario puede no caer encima del collider y entonces cae hasta el infinito, podría poner un box collider kilometrico pero me parece poco elegante, entonces pense en encerrar el escenario en un box collider y si sale de este muere.

 

Mi duda es si esto necesita de más procesamiento o es lo mismo. Al ser para movil quiero hacerlo lo más eficiente posible. 

He probado ambos y en el profiler no he visto diferencias, pero claro en el PC quizas no le suponga mucho como para notar una bajada de rendimiento en el profiler.

¡¡Saludos y gracias por adelantado!!

 

 

Edited by zelleGames

Share this post


Link to post
Share on other sites

No sé como son los códigos internos de unity, pero realmente no creo que vaya a haber alguna diferencia notable entre un tipo u otro. Sí seguramente hay posibles optimizaciones aquí o allá, pero con impacto tan mínimo que no creo que valga la pena rayarse en la diferencia de esas dos.

Share this post


Link to post
Share on other sites
11 hours ago, zelleGames said:

Mi duda es si esto necesita de más procesamiento o es lo mismo. Al ser para movil quiero hacerlo lo más eficiente posible. 

Enter vs Exit no es la gran cosa, si antes se detecto false y ahora true se dispara el mensaje Enter, si de lo contrartio antes era true y ahora false se dispara el otro. La parte de los mensajes disparados no implican problemas de rendimiento (en todo caso el stay supondría más "problemas"). Lo que hace la diferencia es registrar todas las colisiones y sus resultados (los famooss queries del motor de físicas), no es lo mismo correr la simulación física con la matriz de colisiones infestada de tildes que con los necesarios (revisá este link ).

La del exit collider no me gusta tanto pero es válida, aunque prefiero manejar los límites por posiciones

por ej una forma más simple y barata es:

if (player.position.y < death.position.y)
	Player.Death()

El transform "death" del ejemplo puede ser un simple objeto, esto sirve como "y general" (no te va a funcionar para tal parte del nivel, es general)

La otra (que me gusta más) es crear tus propios límites (basados en objetos de referencias, valores puros, como quieras), podrías determinar límites en los que el personaje muere, como por ej :

if( -10< x < 25 && Mathf.NegativeInfinity < y < 15 )
	Player.Death()

 

Prefiero esto y no usar triggers en este caso, sobretodo si tenés una única zona (sea 1, 10 o 1000, estos números son aún muy bajos para el calculo que tenés que hacer) distinto fuera si tenés pequeñas "zonas de muerte", no vas a definir todas por el inspector o andar poniendo referencias para crearlas porque te volvés loco.

 

Saludos

Share this post


Link to post
Share on other sites

Si es una "altura de muerte", lo más eficiente es no hacerlo por Colliders, sinó por matemática pura con un simple IF, comparando la posición.

Si es una "zona de muerte", no uses un Collider, usa un Trigger y usa el OnEnterTrigger, etc etc... Los Colliders se usan para obstáculos, muros, etc, no para "zonas de control".

 

Share this post


Link to post
Share on other sites

Gracias por las respuestas!

Ya la lie parda con mi primer juego que por cierto Lightbug, de nuevo agradezco la ayuda que me diste, aprendi mucho con tus consejos, ahora intento tener la eficiencia siempre en mente y desde el principio, jeje.

Lo de la matriz de colisiones lo habia mirado en su momento pero nunca lo habia puesto en práctica, asi que esta es una buena ocasión. No lo usare para ver cuando muere el player porque al final lo hare con una "altura mortal" ya que todos los niveles son planos o a lo mejor suben un poco, pero el caso es que hay un vacio y tras sobrepasarlo muere, con este codigo me vale.  

if (player.position.y < death.position.y)
	Player.Death()

 

Pero si para otras cosas como objetos que solo recoge el player, porque entiendo que aunque dos collider nunca se vayan a tocar por ejemplo unos cubos que coge el player que estan flotando y nunca tocaran el suelo, unity si que se esta revisando continuamente si se han tocado aunque nunca lo vayan hacer, o asi he entendido la utilidad de usar layers y la matriz de colisiones.

 

Esto que pusiste, ni idea de lo que hace, además que veo cualquier referencia a las matematicas y salgo huyendo, jaja.

 He buscado en la API Mathf.NegativeInfinity pero me quedo un poco igual, indica una referencia a un negativo infinito ?¿?¿?

 

¿Es como para representar el espacio de un cubo?

¿De ancho de -10 a 25 y alto de infinito negativo y 15 de alto?

Quote

if( -10< x < 25 && Mathf.NegativeInfinity < y < 15 )
	Player.Death()

 

¡Saludos y gracias a todos!

Share this post


Link to post
Share on other sites
1 hour ago, zelleGames said:

indica una referencia a un negativo infinito ?¿?¿?

exacto, es el Mathf.Infinity en versión negativa, Infinity equivale al malor máximo del float (supongo) así como el Epsilon indica el valor mínimo, tan pero tan mínimo que A + epsilon = A , imaginate.

1 hour ago, zelleGames said:

¿De ancho de -10 a 25 y alto de infinito negativo y 15 de alto?

Claro, lo puse para que los lados laterales tengan longitud "infinita", con la altura mortal creo que en tu caso te alcanza. Ese código de 4 límites imita (en resultado) al Rect.Contains que usas para saber si el cursor se encuentra dentro de un Rect, si la orientación del player es siempre la misma y la posición se encuentra en los piés (el pivot) el if es como está puesto. Si fuera alrevés y este trigger estuviera por encima del jugador tendrías que evaluar otro punto, no la posición directamente (player.position) sino la cabeza (player.posición + Vector3.up * alturaDelPlayer)

Share this post


Link to post
Share on other sites
Quote

Epsilon indica el valor mínimo, tan pero tan mínimo que A + epsilon = A , imaginate.

Que curioso no lo sabia, vamos que Epsilon es casi 0 o el valor posible más cercano a 0, interesante...

Quote

si la orientación del player es siempre la misma y la posición se encuentra en los piés (el pivot) el if es como está puesto. Si fuera alrevés y este trigger estuviera por encima del jugador tendrías que evaluar otro punto, no la posición directamente (player.position) sino la cabeza (player.posición + Vector3.up * alturaDelPlayer)

He probado con la altura mortal y funciona perfectamente, esta opción la pense en su momento pero no quería meterle mucha carga en Update(), pero imagino que Unity internamente tambien metera sus calculos de los collider en Update()...

El player realmente es una bola y al caer al vacio no necesita ser muy preciso cuand muera, de hecho muere tras caer un par de unidades por debajo del escenario para que se vea como cae que siempre da morbo, jaja.

saludos y gracias!

Share this post


Link to post
Share on other sites
On 4/26/2019 at 8:55 AM, zelleGames said:

Que curioso no lo sabia, vamos que Epsilon es casi 0 o el valor posible más cercano a 0, interesante...

Funciona así (sacado del manual):

  • anyValue + Epsilon = anyValue
  • anyValue - Epsilon = anyValue
  • 0 + Epsilon = Epsilon
  • 0 - Epsilon = -Epsilon

Es por el tema del exponente en punto flotante, cuando los valores empiezan a ser considerables cada vez menos valores intermedios soporta debido al error (de aca todos los errores feos del punto flotante). Epsilon casi ni existe, ni siquiera comparado con un valor pequeño no nulo, es tan pero tan insignificante que solamente cuando el valor que sumas es nulo no le queda otra que aparecer, es la única situación donde al pobre no lo pisan, osea que es genial para verificar si algun valor es aproximado a otro, Approximately funciona con epsilon.

Share this post


Link to post
Share on other sites

×
×
  • Create New...