[Duda] Como replicar mecánica

PaulVaso

Buenas gente, lo primero que me gustaría decir es que no soy ningún experto en gamedev para nada, puro hobby, ergo soy un noob.

La idea que tengo es replicar la siguiente mecánica del vídeo:

  • instanciado de unidades todos alrededor de una, es decir, si os fijáis cuando pasa por un "portal" de x 50 pues si tengo 1 unidad, pasaría a tener 50, y se ponen todas alrededor y van juntitas, pero parece como que hay una padre y que predomina no?
  • que cuando choquen contra la pared no se muevan ni nada (no tenga afectación los colliders), llegue a su límite.

Lo que tengo hasta ahora:

  • utilizando navmesh instancio todas en un mismo punto dentro de un gameobject padre, el resto dejo que las físicas de Unity se encarguen

problemas?

  • cuando chocan contra los "bordes" se salen las unidades y luego se adaptan obviamente, por que todas están apuntando siempre hacia el punto del mismo para recolocarse.
  • a veces se ponen a vibrar como un satisfyer

Otra cosa que haré es activar-desactivar las unidades en vez de instanciarlas, ya que supongo que consumirá menos recursos que estar instanciando y destruyendo todo el rato.

No sé si me he explicado bien, como haríais esto? he intentando de varias maneras, incluso he pensado de hacer una locura en plan calcular la cantidad de unidades que tengo y tener puntos de inicio para cada número del 1 al 50 por ejemplo.

Salu2

puntocom

Así mirándo rápido lo que dices parece que tiene sentido como lo has planteado.

Diría que lo de que cuando te acercas rápido a las paredes algunas unidades las atraviesen tiene que ver con el sistema de físicas de Unity, cuando algo colisiona a velocidades rápidas ocurren cosas raras de ese tipo, que la unidad atraviesa lo que no debería, sale volando o similar.

Creo que deberías intentar limitar de otra manera el que las unidades puedan atravesar las paredes (por código), algo del estilo lo que se ve en tu vídeo, que las unidades se salen del carril pero no están colisionando. En el vídeo parece que a mayor número de unidades, menor rango de movimiento hacia los lados tiene el jugador, de manera que realmente no están "chocando" contra nada.

El tema de instanciar/destruir aunque sería una buena práctica, para lo que estás haciendo en principio no creo que tenga ningún impacto, me centraría primero en resolver lo otro. Lo de tener los 50 puntos de inicio lo veo innecesario, lo que has enseñado se ve guay así.

B

Puedes probar con un trigger collider en vez de colisionadores.

Edit: sobre el traspaso de colisionadores, en la docu del rigidbody mira collision detection, te puede ser de ayuda.

Czhincksx

Tienes un punto central y un radio a su alrededor que determina dónde se tienen que distribuir las unidades. Se mueven todas con un kinematic rigidbody que intenta moverse siempre hacia el centro de tu circunferencia. Además cada uno de ellos detectan los triggers del escenario que les hacen desaparecer al colisionar. El movimiento horizontal lo tienes que limitar en función del radio de tu muchedumbre y ese radio lo alteras dinámicamente en función del número de personajes.

PaulVaso

Gracias por vuestras respuestas, han sido de gran ayuda.

Finalmente he hecho dos colliders a los costados y detectado que las unidades que choquen en un costado suman un contador de pared izq y pared derecha, es decir, hay 2 contadores, cuando las unidades unidades salgan del trigger de las paredes, se resta un valor al contador por unidad y si el contador está en 0, pues puedo moverme hacia la derecha por ejemplo. Ya subiré gif.

Ahora la cosa es que hariáis, mover las unidades hacia adelante por si solas? O mover el suelo hacia abajo?

B

Si tienes físicas sobre el mapa lo dejaría estático.

Si desplazas la cámara siguiendo al grupo es recomendable hacerlo desde LateUpdate()

Lo mismo si usas jerarquías, si la cámara tiene padre y aparecen problemas de "vibración" actualiza el padre desde LateUpdate()

PaulVaso

Buenas, tengo un problema que se me ponen a temblar las unidades cuando las activo (al final he hecho una pool con Queue y activo/desactivo la cantidad que quiero y se reposicionan).

Ejemplo de que se ponen a temblar
https://gyazo.com/79417bd6efb46bba81549e43fd7b9b5d

La verdad es que he hecho una guarrada, ya que tengo un GameObject padre que se encargaría de todo el tema de mover etc. lo que pasa es que en cada unidad tengo un script que coge la posición del ratón/pantalla táctil desde un GameManager y tienen en el FixedUpdate y rigidBody.MovePosition() a la nueva posición.

Dejo cacho de código: Si la speed la pongo a 0.1 no tiemblan, pero luego en el móvil no van a la velocidad que me gustaría, en cambio si pongo 0.8, o 0.9 ggs se ponen a vibrar como espermas.

spoiler

He probado de congelar la Z en el rigidbody y no tiemblan/vibran, pero a veces tienen un compartamiento raro

https://gyazo.com/7f1b835fb4fcee4062ae4587d861152b

y Aquí con la velocidad a 0.1

https://gyazo.com/e2e9020ffaaee3f7cf60ab4cf6c27320

Saludos!

B

Puedes poner una captura del ajuste del rigidbody y de los materiales físicos que usas?

1 respuesta
PaulVaso

#8

He probado a poner Kinematic e Interpotale (incluso Kinematic y Continuos) pero va lentísimo, en plan a fotogramas. Y como he dicho anteriormente congelando la Z no tiemblan... pero a veces tienen como vida propia y se reposicionan.

Czhincksx

Prueba a moverlos con un addforce en lugar de un movetoposition.

2 respuestas
B

Además de #10 ...

Para tener control de la física necesitas crear y aplicar https://docs.unity3d.com/Manual/class-PhysicsMaterial2D.html para definir el comportamiento.

No recuerdo que valores usa el engine en caso de no asignar material físico.

Prueba a asignar un material que tenga rebote a cero y juega con la fricción.

Probaría con fricción casi nula y mayor masa en el rigidbody.

1 respuesta
PaulVaso

#10 #11

El tema es que con el addforce si desactivo o destruyo las unidades no se recolocan solas, en cambio con el .moveposition se vuelven a colocar, probaré con el material me suena que tenía uno por ahí sin fricción que he utilizado en un proyecto.

Gracias por responder!

1
B

Hice una prueba.

Usando jerarquías...

El padre es un rigidbody seteado como estático y movido vía position.

Los hijos son rigidbodys dinámicos, van con masa 100 y drags a 10.

Todos con material físico ajustado a rebote y fricción 0.

Para el movimiento de los hijos AddForce((parent.position-position)*2000f);

edit: se podría acelerar el tiempo de la física (sin afectar al resultado) para mejorar la reincorporación de las unidades a su sitio.

1 respuesta
Czhincksx

Se ve chulo, pero dos apuntes. Un rigidbody estático no debería moverse nunca. Resulta costoso para el motor porque asume que es un objeto que no se va a mover y tiene que recalcular muchas cosas cuando lo hace. Al addforce ese le falta el multiplicarlo por Time.fixedDeltatime (y que se ejecute en el FixedUpdate). También te falta normalizar el vector de dirección.

2 respuestas
B

#14 cierto, además en este caso el estático es redundante... realmente no es necesario ya que va actualizando vía position, con el collider bastaría.

1 respuesta
Czhincksx

#15 anda pero si tú no eras el que abrió el hilo 🤣

1
B

#14 Si el código va en fixedupdate no necesitas interpolar con la multiplicación.

Es paso fijo, en caso de delay entre pasos lo que hace Unity es saltarse la llamada, multiplicar con fixedDeltatime equivale a multiplicar por una constante. Es redundante...

La función "usable" en la práctica de fixedDeltatime es variar el número de llamadas por segundo, si no lo modificas runtime se puede ahorrar la multiplicación.

El vector no está normalizado para que la fuerza sea proporcional a la distancia y agilizar la reincorporación.

1 respuesta
Czhincksx

#17 lo del vector no normalizado me parece bien con ese propósito, pero en lo del fixed update discrepo. Si el día de mañana ves que el rendimiento es pobre y quieres cambiarle el tiempo del fixed update, por ejemplo de 0.02 a 0.03, te va a tocar ir a todas las llamadas que lo usen y actualizar.

1 1 respuesta
B

#18 estarías modificando el número de llamadas... Cambio "si no lo modificas runtime" por "si no lo modificas"

Por cierto, en mi prueba la posición de los rigids dinámicos se fuerzan vía jerarquía, como no se altera la posición relativa entre hijos aparentemente no afecta al engine...

En teoría no se trata de buen uso del engine aunque parece que funciona sin problemas.

1 respuesta
Czhincksx

#19 bueno, el caso es que replicaste la mecánica que quería #1 y queda chula :)

1
PaulVaso

#13 Gracias por tú respuesta. He seguido la manera de que lo has hecho tú y va de lujo, me falta retoques respecto a que no se me salga de la pantalla cuando le doy con fuerza al deslizar el dedo/ratón.

https://gyazo.com/c42bffc0e54b329b2579a31b46a293b4

EDIT: No he utilizado un rigidbody ni collider en el GameObject padre.

2

Usuarios habituales