En esta conferencia, examinaremos 'Flocado'.
El flocado tiene que ser uno de mis favoritos A. YO. técnicas
Implica reglas simples que generan comportamientos complejos que son fascinantes. El agrupamiento se puede utilizar para generar de manera
procesal el movimiento de grupos de individuos a los que les gusta permanecer juntos, mientras avanzan
hacia un objetivo común.
Me viene a la mente el vuelo de las aves, pero esta técnica se puede utilizar prácticamente en cualquier lugar
donde tenga un grupo que necesite comportamientos de movimiento complejos que no desee programar a mano.
En este taller, crearemos peces de flocado (o escolarización). Para seguir, descargue el paquete de 'AIfish' Unity
que viene con esta conferencia.
Abra un nuevo proyecto de Unity para 3D y traiga ese paquete.
Cuando lo agregue a los Activos, encontrará que hay un pez verde, un pez rosa y una escena llamada Natación. Si abre la escena de Natación en sí, obtendrá
el pez verde solo
con la cámara configurada apuntando hacia él y si presiona Reproducir,
encontrará que ese pez verde tiene una animación de natación adjunta.
Ahora, para crear una bandada, necesita más de 1 pez en este
caso porque la bandada es una actividad grupal.
Así que vamos a crear un administrador
de flocado y en la jerarquía, simplemente haga clic derecho allí y agregue un vacío y llámelo FlockManager.
Esto no es diferente a los otros Gerentes que hemos tenido antes para otros agentes, donde queríamos
crear múltiples versiones de ellos para que podamos enviar mensajes y realizar un seguimiento de ellos.
En este caso, los peces necesitan conocerse unos a otros, por lo que FlockManager creará un
montón de peces y luego podrá informar a todas las personas sobre los otros peces en la parvada (o en la escuela, supongo, pero yo
Lo llamo rebaño).
Bien, entonces tenemos nuestro FlockManager, que es un 'vacío'. Cree un script C # y llámelo FlockManager
y luego ese script se adjuntará a nuestro FlockManager.
Ahora vamos a abrir ese script y agregar este código. El código es bastante simple.
Crea una variedad de peces, crea instancias de todos esos objetos de peces y los coloca en una
ubicación aleatoria alrededor de la ubicación de su FlockManager.
Correcto.
Entonces, antes que nada, necesitará una variable pública, FishPrefab expuesta y pasamos nuestra prefabricada de peces aquí (que puede ser su pez
verde o el pez rosado o cualquier otra cosa). También puede hacer esto con cubos, no hará ninguna
diferencia y luego
un número público que hemos establecido en 20 (pero esto le permitirá cambiar la cantidad de peces que
tiene en una parvada en particular, a través de el inspector).
Luego crearemos nuestra gama de allFish y, a medida
que los instanciamos, entrarán en este allFish y luego tendremos un
Vector3 llamado swimLimits.
Este es el rango de ubicaciones dentro de las cuales se puede generar el pez.
Así que esto es como una caja que está alrededor de su administrador de bandadas y es 5x5x5, lo que lo
hace 10x10x10 porque este es un valor de
radio y luego usaremos swimLimits para generar la ubicación de nuestros peces dentro de esa caja.
Entonces todo esto está sucediendo en Inicio.
En primer lugar, creamos todos los peces y hacemos la matriz lo suficientemente grande como para contenerlos.
Luego está el ciclo 'for', que gira alrededor de ese número de veces y cada vez
crea una posición para colocar el pez y esta posición se basa en la posición del administrador de la parvada más un valor aleatorio de
Vector3 que está alrededor de esos límites de natación (así entre 'minus swimLimits' y 'swimLimits positivos')
que le proporcionarán el rango de posiciones.
Ahora, si desea que sea una caja de posiciones más grande, entonces simplemente aumentaría estos valores aquí
o podría hacerlos más pequeños si desea un grupo muy unido.
Luego, una vez que tenemos esta posición que hemos calculado, colocamos el pescado (lo instanciamos desde
nuestro prefabricado) en la posición que acabamos de calcular, usando una rotación neutral.
También puede establecer esto en la rotación
prefabricada de peces si los tiene apuntando en una dirección particular,
realmente no importa y eso llenará esta matriz.
Entonces, si guarda eso, vuelva a Unity, seleccione su FlockManager y desea configurar el prefabricado de peces.
El pez prefabricado no es este pez verde que está en la escena.
Okay.
Ese es el que se usó para hacer el prefabricado inicial.
De hecho, simplemente elimínelo, para que no se confunda con él y luego tome su prefabricado de
peces (que está en sus Activos) y arrástrelo y suéltelo en el FlockManager.
Vamos a crear 20 peces y llenará esta matriz aquí.
Así que presiona Play y encontrarás tus 20 peces (y si me
alejo, los verás) dentro de los límites de los límites de natación que hemos creado.
Ahora, si quieres más pescado que eso, digamos que querías 50 peces ... 50 aquí y presiona Play y obtendrás 50 peces.
Puedes verlos, todos han aparecido en la Jerarquía y todos están en el Inspector debajo de la matriz
allFish
y así cada pez puede encontrar a todos los demás peces que están en su rebaño.
Ok, es hora de que el pez se mueva. Para comenzar, vamos a configurar algunos valores de velocidad para
el pez y lo haremos en el FlockManager. Por lo tanto, haremos del FlockManager un lugar donde
podamos establecer todas las diferentes variables para los peces particulares que pertenecen a esa bandada y
luego puede tener múltiples bandadas para diferentes tipos de peces en su escena.
Así que volví a usar el script FlockManager. Lo que vas a hacer es agregar algunos valores públicos
como los que tengo aquí.
En primer lugar, en el Inspector, acabo de agregar una pequeña línea de 'Encabezado', que la separa y hace que sea
fácil de encontrar cuando intentas configurarlos.
Entonces tengo un 'Rango' aquí, entre 0. 0f y 5. 0f que le dará
un control deslizante en el Inspector y luego public minSpeed y public maxSpeed, con los mismos valores para el rango.
Una vez que haya agregado esas 5 líneas, simplemente guárdelo, vuelva a Unity y haga clic en Flock Manager
y encontrará en el Inspector que ahora tenemos esas configuraciones. Tenemos 'Configuración de pescado', Velocidad mínima y máxima (que luego
puede cambiar con los controles deslizantes a su gusto y también podrá hacerlo en tiempo real
y pasar esos valores de velocidad al pescado) . Para los peces, ahora crearemos un
nuevo archivo C # y lo llamaremos 'Flock'.
Este es el código que pasa al prefabricado de peces, así que arrastre y suelte eso en su pez verde y mientras estemos
aquí, lo arrastraremos y soltaremos también en el pez rosa.
Simplemente seleccione el pez verde en los Activos y verifique en el Inspector para asegurarse de que el script
esté realmente adjunto.
Ahora ábralo y lo primero que necesitaremos es un enlace a nuestro
administrador, por lo que crearemos un 'FlockManager myManager público' y luego necesitaremos un flotador para la velocidad.
Ahora en el Inicio, vamos a establecer la velocidad para que sea igual a Aleatorio. Rango entre la configuración de velocidad mínima del administrador y la configuración de
velocidad máxima del administrador. En la actualización, pondremos
una declaración de traducción para impulsar al pez hacia adelante a lo largo de su eje hacia adelante o su eje Z.
Observe que el valor de 'velocidad' va al eje Z.
Si su pez se enfrenta en una dirección diferente ...
así que si solo regreso a mi pez y agarro un pez, entonces el eje azul aquí está mirando hacia adelante y ese es
el que lo empujará.
Si su pez tiene un eje diferente, entonces tendrá que ajustar su código para empujarlo a lo largo
de ese eje.
Ok, entonces borraremos ese pez y volveremos al código y lo guardaremos, luego en su script
FlockManager, si lo abrimos, después de haber creado un pez dentro de ese ciclo for, desea configurar es
FlockManager (o myManager) para este FlockManager en particular.
Agregue este código y ahora ambos archivos (Flock y FlockManager) se vincularán entre sí.
De vuelta en el Editor, presione Reproducir y verá los resultados del código.
Entonces tienes tus peces que ahora están avanzando.
Tienen velocidades aleatorias sobre ellos.
Por supuesto, van a salir de escena muy rápidamente.
Puede ver que se mueven a diferentes velocidades (si puede acercarse). Sí.
Entonces todos tienen diferentes velocidades, pero
todos se mueven a lo largo de su eje Z. Ok, ahora es el momento de agregar nuestras 'reglas de flocado'.
Mencioné las reglas de agrupación al comienzo de esta
sección, pero repasemos de nuevo en detalle.
Ellos son: moverse hacia la posición promedio del grupo; Alinee con el encabezado promedio del grupo y evite
aglomerar a otros miembros del grupo.
Avanzar hacia la posición promedio del grupo implica tomar todas las posiciones de los miembros
individuales, sumarlas y dividirlas por el número del grupo.
Luego podemos averiguar dónde está un individuo, en relación con la ubicación promedio y hacer que
se vuelvan hacia él. Para alinearnos con el encabezado
promedio del grupo, sumamos todos los encabezados de los individuos y los dividimos por el tamaño del grupo.
Esto proporciona un vector promedio para que las personas intenten alinear su movimiento. Para evitar vecinos, un individuo debe ser consciente
de dónde están los
vecinos y luego apartarse de ellos.
Luego, para calcular un nuevo rumbo, un individuo agregará el vector para moverse hacia el centro de
un grupo, el vector para alinearse con el rumbo de los grupos y el vector para alejarse de un vecino.
Antes de comenzar a editar el código de Flock, solo agregaremos algunos valores más al FlockManager (los que
puede cambiar en tiempo de ejecución, para que pueda ver diferentes comportamientos en el pez)
y estas configuraciones para los comportamientos serán disponible para todos los peces en esa bandada
en particular.
Así que estoy agregando aquí otro rango para algo llamado vecinoDistance y otro rango para la velocidad
de rotación.
Entonces, una vez que los peces comiencen a obtener lugares hacia los que necesitan moverse, tendrán que dar la vuelta
en algún momento y usaremos un slerp para eso y eso necesita una velocidad de rotación, así
que agregué que ahí.
Ahora, la otra cosa con este vecinoDistance es que puedes tener una bandada de algo y todo en esa bandada podría
considerarse tu vecino o solo querrás
considerar a los pocos más cercanos (dentro de un metro de ti) como tu vecino real, así que
por lo tanto, puede modificar eso y obtiene diferentes comportamientos de todo el grupo cuando
solo consideran a los que están a su alrededor como vecinos en lugar de todos.
Ahora para los cambios en el rebaño. Ve a tu rebaño. código cs.
Vamos a crear un nuevo método llamado 'ApplyRules' y ese método se llamará aquí para que
no haya otros cambios en la parte superior, solo dentro de
la Actualización y luego agreguemos ApplyRules.
Ahora, este ApplyRules está haciendo esas 3 reglas de las que acabamos de hablar, con los diferentes cálculos vectoriales.
En primer lugar, está creando un soporte, para apoderarse de todos los peces en la bandada actual.
Entonces estos son los peces que queremos probar y encontrar la posición promedio, el rumbo promedio, etc. y son los peces que serán
considerados tus vecinos (o al menos son el conjunto completo y los vecinos serán
parte de ese conjunto, como verás en un minuto).
Ahora estamos calculando el centro promedio de los grupos, así que vamos a almacenar eso en 'vcentre'. Entonces también estamos
calculando el vector de evitación promedio.
Por lo tanto, no solo queremos evitar a un vecino,
sino a TODOS, y
eso también es un promedio.
Por lo tanto, debe calcular todos los vectores de evitación y luego promediarlos.
Entonces, inicialmente están configurados en 0.
Luego tenemos este flotador
llamado 'gSpeed' y esta es una velocidad global del grupo (una velocidad promedio en la que se
mueve el grupo) y también la usaremos en nuestros cálculos.
Luego tenemos un flotador 'nDistance', que es nuestra distancia vecina.
Así que vamos a tener que preguntar a cada pez qué tan lejos están y
luego calcular si consideramos que están lo suficientemente
cerca como para estar en nuestro grupo y así tenemos este contador 'groupSize' aquí, que contará cuántos de los los peces en el rebaño están en
nuestro grupo, por lo que el grupo es como esta pequeña sección del rebaño que está dentro de ese valor de distancia
vecino.
Ahora, con estos valores inicializados a 0, esencialmente, vamos a recorrer todos los peces
en la parvada.
Entonces usamos un bucle foreach.
Luego vamos a preguntar si el pez actual (que va a ser este objeto
del juego aquí: ir) siempre
que no sea igual al pez que ejecuta este código en este momento, entonces haremos el proceso porque no necesita encontrar
el promedio de usted mismo, no tiene que calcular la distancia a
sí
mismo, por lo que esto solo asegura que no calculemos los datos del pez por sí mismo.
Luego calculamos la distancia del vecino, así que recuerda que estamos girando alrededor de este ciclo for,
seleccionando cada pez y luego calculamos la distancia con un Vector3. Distancia entre el objeto del juego en nuestra
posición de matrices y nuestra posición en el mundo y luego preguntamos si esa distancia es 'menor o
igual que' la distancia vecina, lo que lo convierte en un pez de interés (uno que
vamos a considere parte de nuestro grupo muy unido) y luego agregaremos la posición de ese pez en particular al 'vcentre'.
vcentre será nuestra posición promedio de nuestro grupo, por lo
tanto, tenemos que dar vueltas y agregar todas las posiciones juntas y luego
dividirlas por el tamaño del grupo.
Entonces, al mismo tiempo que lo agregamos, también aumentamos el tamaño del grupo en 1.
Entonces, después de que este ciclo haya pasado, podemos calcular el promedio.
A continuación, tenemos una instrucción if para probar que nuestro vecinoDistance sea menor que un valor mucho menor, que he
codificado aquí como 1. 0 y, de
hecho, podríamos poner esto en el FlockManager como otro valor de distancia, pero así es lo
cerca que podemos estar de otro pez antes de considerar la posibilidad de evitarlo.
Ahora si, en este caso, la distancia es menor que 1. 0f, entonces se agregará el vector promedio de
evitar y, por lo tanto, tiene su propio valor + el vector alejado de ese pez.
Entonces, el vector alejado de algo (y vimos esto en una simulación de multitudes que
queríamos alejar) era nuestra posición actual menos la posición de la que queremos alejarnos
y eso se suma a medida que avanzamos por aquí también.
Ahora la velocidad global está sumando todas las velocidades de un pez particular de la parvada.
Así que seguimos adelante y agarramos el código Flock que está adjunto al pez que
estamos viendo en este momento y luego tomamos su velocidad y lo agregamos a este valor de gSpeed.
Ahora, cuando el código termina este bucle foreach, hemos pasado por todos
los peces de la parvada y lo hemos examinado. Si se considera que es un vecino cercano, entonces estamos encontrando su posición
y también su vector de evitación y sumando todo eso.
Ah y por supuesto la velocidad. Ahora debajo del bucle
foreach, tenemos una declaración if. La declaración if pregunta si el tamaño del grupo es> 0. Si el pez se mueve y
no hay nadie alrededor y el tamaño del grupo se convierte en 0, no
se aplicarán estas reglas. Simplemente seguirá moviéndose en línea recta.
Entonces, si este pez está influenciado por otro pez (u otro grupo de peces), entonces encontramos el promedio al
centro.
Entonces ese es el vector 'vcentre' que calculamos cuando los sumamos todos
juntos, ahora dividimos por el tamaño del grupo. La velocidad misma del pez se establece en la velocidad global, dividida
por el tamaño del grupo.
Con esa información, podemos determinar en qué dirección debe viajar el pez (o
en qué dirección quiere viajar).
Entonces, su 'dirección' es igual a 'vcentre array' + 'vavoid array', nuestra posición actual.
Ahora, si eso significa que la dirección es 0, ya estamos mirando
en la dirección correcta.
Si no es igual a cero, entonces tenemos
que rotar y entonces hacemos una transformación. rotación y usamos nuestro Slerp que hemos usado antes para otros NPC
y hacemos una pequeña rotación de acuerdo con nuestra velocidad de rotación y lo que esto hará
es girar lentamente el pez hacia la dirección que necesita. No va a girar en la
dirección perfecta y
es este slerp (y slerping un poco a poco) y constantemente actualiza tu
posición y comprueba dónde estás con respecto a todos los otros peces, lo que hace que este flocado
ocurrir, como estás a punto de ver. El tiempo en este video está a punto de agotarse, así que
rápidamente presionaremos Reproducir (asegúrese de que en su FlockManager proporcione una Distancia vecina y una Velocidad de rotación, de lo
contrario no obtendrá ninguna rotación en absoluto
y luego comenzarás a ver que se produce la congregación.
Investigaremos esto más en el próximo video.