Hola Nosotros en Playrix decidimos hacer
nuestro Unity3D . Y ahí está Animator. En este artículo te contaré cómo lo hicimos en casa y cómo funciona.
Cuando comenzamos a diseñar la arquitectura de nuestros gráficos de animación, por supuesto, observamos otros análogos, en particular en Unity Animator. Sin embargo, queríamos hacer una solución más universal. A diferencia de la misma Unidad, tenemos personalización de estados de animación a través de la interfaz del controlador. Pero primero, vale la pena descubrir qué es un gráfico de estado animado. Si ya se ha encontrado con esto, tiene sentido omitir la parte introductoria y pasar a las características de implementación.
Entonces, ¿qué es exactamente este gráfico de estado animado?
Un gráfico de estado de animación le permite representar gráficamente las transiciones entre diferentes estados de animación.
Tomemos, por ejemplo, animación de personajes:
Tenemos un modelo tridimensional de un hombre y hay varias de sus animaciones:
- inactivo - se detiene;
- caminar - avanza;
- sentado
- hola - agita una mano.
El enfoque clásico para administrar animaciones es el siguiente: si desea que el objeto se pare - encienda inactivo, camine - camine, siéntese - sentado. Pero hay ciertas dificultades con esto.
Primero, debe controlar manualmente la duración y la secuencia de las animaciones. Por ejemplo, para que una persona se siente, primero debe reproducir la animación, cómo se sienta y luego comenzar a reproducir la animación en bucle, donde la persona ya está sentada. Personalizar las uniones de estas animaciones en el código es difícil e inconveniente.
En segundo lugar, las uniones entre las animaciones se vuelven notorias si los extremos de la animación no coinciden, o si necesitamos incluir otra animación en el medio de la actual. En este caso, es simplemente imposible hacer coincidir perfectamente las animaciones. Recuerda los viejos juegos donde las animaciones de los personajes cambiaban instantáneamente.
El gráfico de animación está diseñado para resolver estos problemas. Con él no necesita operar animaciones manualmente, ahora opera con estados. Cómo se animará un objeto para lograr este estado es el trabajo de animadores y diseñadores. Ahora el programador no piensa en el tiempo y la secuencia de la animación, solo indica en qué estado debe entrar el objeto.
Además, con el gráfico de animación, desaparece el problema de unir animaciones. En la transición entre estados, podemos hacer una transición suave de una animación a otra. Esto se hace usando pesas. El peso es un factor de mezcla de 0 a 1, donde 0 significa que la animación no afecta al objeto de ninguna manera, y 1 lo afecta por completo.
Por ejemplo, la transición entre caminar (inactivo) y estar de pie (inactivo) es muy exigente para configurar el proceso. En cualquier punto de la animación a pie, el personaje puede detenerse. Por lo tanto, la transición no se lleva a cabo instantáneamente, sino por un período de tiempo pequeño. En este momento, el peso para caminar disminuye de 1 a 0 y el peso de pie aumenta de 0 a 1. Es importante que la suma de los pesos sea igual a uno; de lo contrario, pueden aparecer artefactos.
¿Cómo funciona todo?
Un gráfico consta de estados y transiciones. Un estado es un conjunto de controladores de animación, cada uno de los cuales puede reproducir algún tipo de animación en un objeto o ejecutar algún tipo de lógica. El controlador tiene puntos de entrada y salida: estos son los momentos en que el gráfico activa el estado con este controlador y lo desactiva en consecuencia. El controlador también tiene una función de actualización, donde, además del intervalo de tiempo desde el último cuadro, viene el peso de la transición. Para mezclar animaciones, debe tenerse en cuenta.
Los controladores tienen una sola interfaz. Además, los desarrolladores pueden agregar sus controladores. Por ejemplo, puede hacer un controlador que ejecute algún tipo de lógica o establezca texto en una ventana emergente, etc. Esta sencilla personalización le permite utilizar el gráfico de animación de manera muy flexible.
También tenemos variables. Estas variables se pueden establecer externamente, incluso desde el código, y luego leerlas en los controladores. Entonces, por ejemplo, puedes cambiar algún tipo de animación para un personaje en el mismo estado. En general, incluso puede repetir el paradigma de transición entre estados a través de variables y condiciones, como Unity. En combinación con controladores personalizables, resulta bastante conveniente.
Las transiciones pueden ser cualquier número. Muchas transiciones pueden entrar en estado y salir de la misma manera de forma ilimitada. Las transiciones determinan la posibilidad de alcanzar estados. Por ejemplo, si no hay una transición directa entre los estados A y F, pero hay una cadena A → B → C → D → E → F, entonces, cuando solicite una transición de A a F, el gráfico comprenderá que necesita pasar por los estados intermedios B, C, D y E.
Las transiciones tienen configuraciones de intervalo de inicio y duraciones. Con la duración, todo es simple: este es el momento en que se realizará la transición. Pero el intervalo ya es más complicado: determina el período de tiempo aceptable para la animación cuando se puede iniciar la transición.
Por ejemplo, para que un personaje se siente, primero debes reproducir la animación mientras se sienta y luego comenzar la animación del asiento. En este caso, el intervalo de transición de "se sienta" a "se sienta" debe estar al final de la animación "se sienta" para que podamos ver cómo se sienta, y luego, al final, ir rápida y suavemente a la animación del asiento.
Otro ejemplo: un personaje camina y necesita detenerse. En este caso, el intervalo de inicio de transición debe ser la duración completa de la animación, porque el personaje puede detenerse en cualquier momento.
El gráfico de animación hace todo el trabajo relacionado:
- planea un camino hacia el estado necesario;
- Actualiza los estados actualmente en ejecución
- hace una transición suave entre estados;
- ajusta los pesos en ellos.
Características interesantes
Hay muchos tipos diferentes de animaciones en el motor Playrix: modelos 3D, Spine, Flash, efectos de partículas, animación esquelética. Cada tipo tiene un controlador específico.
Además de los controladores de animación simples, tenemos varios auxiliares. Por ejemplo, un controlador aleatorio. Puede incluir una lista de otros controladores y la probabilidad de su elección. Cada vez que un objeto entra en un estado con dicho controlador aleatorio, se realiza una selección aleatoria teniendo en cuenta las probabilidades, y el controlador seleccionado comienza a funcionar. El resto está durmiendo e inactivo, esperando su momento.
Pero a veces en un estado necesitamos cambiar animaciones. Por ejemplo, si varios personajes tienen el mismo gráfico y todos tienen algún tipo de animación de acción. Un personaje necesita su escoba y comenzar su venganza, otro para obtener su cámara y comenzar a tomar fotos, el tercero es comer helado. Para tales situaciones, hay un controlador especial, que también contiene una lista de controladores, pero, a diferencia de los aleatorios, aquí selecciona un controlador dependiendo de la variable.
Las variables se establecen en el gráfico y se pueden cambiar externamente, por ejemplo, desde el código. En este ejemplo, se usa un tipo de cadena y cada tipo de acción corresponde a un cierto valor de la variable. Cuando se crea un personaje en el juego, esta variable se establece para él dependiendo del comportamiento deseado.
También tenemos un controlador que puede mezclar múltiples animaciones. Por ejemplo, puede mezclar animaciones para caminar, izquierda, derecha y adelante. Por lo tanto, en las curvas, puede ajustar los pesos entre ellos para que las piernas del personaje no resbalen y caminar parezca natural.
Necesitamos profundizar
Hay muchas ventajas en el hecho de que hagamos nuestra Unidad. Una de ellas es que podemos hacer lo que queramos y lo que queramos. Y queríamos una oportunidad ilimitada para expandir el gráfico de animación.
Tenemos una interfaz de controlador, hay varios controladores "listos para usar", y existe la capacidad de implementar la interfaz y hacer cualquier cosa en ella (y no necesariamente una animación):
- cambiar el texto en el botón;
- interactuar con otros objetos en la jerarquía;
- e incluso administrar otro gráfico de animación.
Utilizamos este enfoque en los visitantes del zoológico en el juego Wildscapes. Cada visitante tiene dos gráficos: uno para animar el modelo y el otro para animar el comportamiento.
El primer gráfico es bastante simple, controla caminar, puede reproducir algunas animaciones de personajes separadas.
El segundo gráfico es mucho más complicado y tiene algunos escenarios de comportamiento. Por ejemplo, primero el personaje se va, luego se sienta en un banco, saluda a alguien, toma fotos y continúa. Esta es una rama estatal separada.
Esta lógica podría colocarse en la primera columna, pero luego las animaciones se duplicarían muchas veces. Pero con dos gráficos, todo es mucho más simple. El gráfico de control contiene una cadena de estados, incluidos los estados del primer gráfico, que se ejecuta en paralelo.
Que sigue
Nuestro gráfico ya sabe mucho, pero todavía hay mucho espacio para el desarrollo. Los planes hacen una agrupación de varios estados, con anidamiento. Esto simplificará enormemente las columnas de misiones. Los planes también incluyen trabajo para mejorar la visualización de gráficos y enlaces. Ahora las conexiones en gráficos grandes se parecen a espaguetis (incluso el color es similar), y a veces es fácil confundirse.