Blend trees for 2D Games in Unity
In 2D games that use sprite sheets it’s very easy to create a spiderweb of transitions between different different animations:
Now any change to how the animations transition between each other might cause whole system to break. And how would you make this change with this kind of entangled mess?
In 3D games the transitions helps a lot since we can set up exactly how do we want our animations to blend between each other and Unity’s Animation system does a pretty good job there.
For 2D games that uses sprites we simply don’t need those transitions. On top of that the default setup will really give us a poor results:
The effect is a sloppy animation that is disconnected from the character movement:
We could of course fix the settings for the transitions. But what if we have 10 or 20 animations to set up - ex. in top down 2D project each movement direction has its own animation?
And as far as I know you can’t copy transitions settings and even if you could you still have to set up the transition condition and also trigger / set those parameters in your script. That is twice the work that you need to do in 2 different systems: animation system and in your own scripts.
Let’s call the animations directly for our code!
Animator object comes with a method:
public void Play(string stateName, int layer = -1, float normalizedTime = float.NegativeInfinity);
which allows us to simply specify the name of your animation (or a blend tree) and play it. For example form the animator setup at the top of the page we would call “Skeleton_Idle_Down 1” as the stateName.
Layer parameter is just the layer index where the Animator will search for this blend tree by name: leave on -1 if your animation or blend tree is in the Base Layer.
Last parameter is normalizedTime so the time offset - should we start playing this animation from the beginning 0 ? Or somewhere in the middle 0-1 value.
If you set your animation to loop it will be playing constantly. You can use this code to call animations / blend trees from our code:
private Animator animator; public void PlayAnimation(string name) { animator.Play(name, -1, 0f); }
What if we have a top down game and there are different animations per each movement direction?
Blend tree to the rescue!
Unity offers us a solution called blend tree:
In 3D games Blend Tree allows us to blend between different animations by setting DirectionX and DirectionY parameters in section (1) in our C# script on the Animator object using .SetFloat(“parameter name”,value); If we instead set those using Integer values so 0, -1 or 1 we can easily cover all the directions of movement. All we need to do is to Play(…) the correct animation and to set your parameters so that the correct animation is selected. Here is the code that we would use to set the movement/input direction for the animation:
public void SetDirectionValues(Vector2 movementVector) { animator.SetFloat("DirectionX", movementVector.x); animator.SetFloat("DirectionY", movementVector.y); }
To set the Blend Tree up we need to add enough Motions (2) - in my case I have 8-Directional movement where I reuse Up and Down animation for diagonal directions. You need to ensure that you set correctly X and Y parameters to represent specific directions of movement and that you add appropriate animations into those motions (3). Here is how you would set the blend tree up in your own project:
Great! Now we have a setup that we can reuse for multiple different blend trees - even if you have something like Death animation which may have only single animation you can put single animations for each motion in your blend tree and reuse the whole system just by providing the correct movement direction to DirectionX and DIrectionY fields and by calling animator.Play(…) to play the correct blend tree.
The initial setup might take some time but you end up with a system that allows you to easily extend it with new animations.
If you want to learn more about Making 2D games in Unity check out my video courses:
If you agree or disagree let me know by joining the Sunny Valley Studio discord channel :)
Thanks for reading!
Peter