- Home /
How to manage 2D animation states (of same behaviour) for multiple type of characters/enemies?
Hi all, I am a newbie to Unity, would like to know how is this situation normally handled in Unity:
The scenario:
My game (2D) has got 50 types of enemies with some generic behaviors and animation states:
standing : animation state idle
walking : animation state walk
attack : animation state attack ... and so on
[My old method]
I was previously making game on GM:S. I normally do it like following: Firstly create sprite for each states for all enemies respectively, and named them accordingly while importing to asset library. For instance:
spr_enemy1_idle,
spr_enemy1_walk,
spr_enemy1_attack,
spr_enemy2_idle,
spr_enemy2_walk,
spr_enemy2_attack...and so on.
Then i will have a parent object for generic enemy behavior, that will store the 'enemy name' and 'state name'. When i tell certain enemy instance on stage to perform an action, it will look for the 'enemy name' and 'state name', then look through the asset library and bring up the animation sprite (animation state) accordingly.
for example: when instance of enemy1 were to perform an attack action, the script will look for asset with name "spr_"+"enemy1"+"_"+"attack", get the sprite, and set the current sprite_index (or animation state in unity) accordingly.
in short, i import all my sprites, name them accordingly, and script the generic rules how the animation state works. Then when i create an enemy instance on scene, i just need to define the enemy name (eg. "enemy1", "enemy2") for it to work accordingly. If i need to further customize certain behavior, i can create a cub-class from there.
*note: The look up on the asset name can be done once when the instance initiated and stored in a reference variable, so that it won't be looking through the asset library every time when the animation state changed.
[in Unity]
From what i have learned so far. User normally create animator controller(for each enemy) and animation states (for each states of respective enemies) then link them in animator controller accordingly.
When i was following the 2D Roguelike tutorial, it uses ‘Animator Override Controller' to define animation state for Enemy2 which have similar behavior as Enemy1. Which is quite handy, but still, when i have 50 or more enemies, i still have to manually create another 49 'Animator Override Controller' then drag in corresponding animation states in to the component to override the states. I think this is rather repetitive and hard to manage. If i later decided i need to add a new state (eg: "jump"), i will have to go through the process 49 times again...
How is such situation normally handled in Unity?
Thank you :)
Answer by CarterG81 · Feb 09, 2017 at 08:21 PM
i still have to manually create another 49 'Animator Override Controller' then drag in corresponding animation states in to the component to override the states. I think this is rather repetitive and hard to manage. If i later decided i need to add a new state (eg: "jump"), i will have to go through the process 49 times again...
That is Unity for you... lots of time consuming, repetitive work.
Unity's animation system is IMO, pretty lacking. It's designed for very specific animation styles, like Don't Starve or Darkest Dungeon style 2D animation. You'll find a lot of problems (inefficiency) using it for anything outside of this intended purpose, like pixel art or SNES style sprite sheets.
It is a system which works much better without the need to change sprites ever single frame.
So unless you're doing this style, you probably won't find the Unity Animation System all that efficient.
How is such situation normally handled in Unity?
Most developers probably just do this repetitive work by hand. That's a very inefficient way, and you are entirely correct to want to avoid this pointless work. However Unity isn't the best tool in cases like this; in fact, it's downright horrible.
Smarter developers would handle it this way:
Automate the process. Write an (editor) script to automatically create these Animators/Animations & set them correctly based on naming conventions in the sprite.
Replace Unity's Animation System with your own, which is based on naming conventions in the sprites. (Like you did in your old method). This is what I would suggest.
Be sure to also automate the naming process, by using an app like Flash Renamer or something similar. It is a PITA to rename things by hand, just like it is to create the same animator/animations 49 times in a row. Bleh.
If for whatever reason you feel the need to retain some usage of the Unity Animator/Animation System, you can
Create an animation script exclusively for use in your Animations
Create a single animator & animations for all characters (assuming they all share the same animations)
Use Animation Events to do interesting stuff, change sprites, track the current animation, or whatever.
I use this method to link Animations with game logic (character actions from input). I use Unity's Animation System to very simply have a set time that an action takes to complete, such as harvesting grass. When the animation is complete, it calls an event. The actual animation is unnecessary. (You'll want to make sure your transitions have Exit Time of 1 & transition duration of 0, or else they can skip these animation events.) It's a quirky way to use the animation system, but it works.
Not sure if you'd even want to do this if you had your own system, but I figured I'd mention this in case, for some reason, you found it efficient to maintain usage of Unity's animation system.
using UnityEngine;
using System.Collections;
public class AnimationEventCommands : MonoBehaviour
{
public void MyParent_PlayerCharacter_StopPerformingAction()
{
this.transform.parent.parent.GetComponent<PlayerCharacterInput>().isPerformingAction = false;
}
public void ChangeAnimation(string animationName)
{
this.transform.parent.parent.GetComponent<CharacterAnimationManager>().SetAnimation(animationName);
}
public void Self_ColorMeRed()
{
//sprite.color = red;
}
public void Self_SelfDestroy()
{
Destroy(this.gameObject);
}
I could be wrong, but in all my years experience with Unity I have never found it useful for anything except 2D Skeletal style animating. It is basically a 2D animation system built only for animations that closely resemble 3D animation systems; just flattened.
Traditional 2D, where you change the entire texture in each frame, is not Unity Animation System's target style. I've found it nothing but troublesome for this type of animation. Sure it can be used, but unless you want to manage everything by hand & love repetition, it is simply awful.
Thank you so much for sharing your experience. After doing some forum crawling, I think it's like what you mentioned. Unity mechanim seems targeted more for 2D rigging type of animation. I can't remember from which thread i read, there was an old animation (not sure if it's an old system or class) that can handle old school sprite animation, but obsoleted. I decided to stick back with G$$anonymous$$:S at the moment. Reason being is that i am a program$$anonymous$$g noob, and prefer sprite animation for my little game. But i will definitely take a look at the script you posted and test it out. Again, thank you so much for sharing :)
While I am not entirely aware of what the "Studio 2" part of G$$anonymous$$:S is, hehe, just this past week I took a look at the "$$anonymous$$ade with Game $$anonymous$$aker" page, and WOW was that impressive! I$$anonymous$$O, far more impressive than "$$anonymous$$ade with Unity" page. It made me think I might have overlooked how great Game $$anonymous$$aker is. I never really gave it a chance to check it out; but man...some of the coolest games were made with Game $$anonymous$$aker! Definitely can't go wrong with that, and I hear it's great for those without as much program$$anonymous$$g experience. A great choice, I$$anonymous$$O. Nearly every game on their "$$anonymous$$ade with" page looked phenomenal. :)
I had the same problem and creating my own animation system seems the way to go. Thank you for your detailed answer.
Your answer
Follow this Question
Related Questions
Sprite animations won't export/run in a published build unless you play in editor first 1 Answer
Is it possible to change the texture property of a material via Animation clip? 2 Answers
Flipping animation in 2D sprites 2 Answers
Why does my sprite changes position after animation transition? 1 Answer