Title sums it neatly, I’m trying to animate a SpriteRenderer’s Sprite field using legacy animation, but it does not seem to have any effect. Other fields on SpriteRenderer animate just fine (enabled for example), but when I modify the Sprite field and play, nada, just stuck on the first frame.
As for the use case - I have animated effects in my game, explosions for argument’s sake. Their behavior is quite simple, they need to play an animation and cleanup themselves as soon as they are done, e.g
If that’s not at all possible, here’s my main concerns for using the new Animator controller:
It adds clutter and maintenance cost by having to manage 2 assets for each effect, an animation clip and an animation controller.
There’s no easy way to poll the animation play state ( animator.GetCurrentAnimatorStateInfo( 0 ).normalizedTime >= 1.0f ), atleast at glance, looks more expensive than animation.isPlaying and less reliable.
For love’s sake, it’s an 8 image sprite sequence, all it has to do is display 8 images and go poof. I does not transition to anything, it has no states, nothing. There’s no reason what so ever to use a super complex FSM for that, especially when it’s counter intuitive for what I’m trying to achieve AND comes with a bigger performance price tag.
So, to wrap it up - what’s my best course of action here for playing a simple sprite sequence as efficiently as possible?
Hello Martin, after following through your code, I thought to create an SpriteManager which will have a list of SpriteAnimation with its own fps, frames array, wrap mode and interpolation between frames since I realize that I could use the Animation Component information to take care of these parameters.
So I create a simple class (the code is simple but it is for example purposes):
using UnityEngine;
using System.Collections;
[RequireComponent(typeof(SpriteRenderer))]
[RequireComponent(typeof(Animation))]
public class SpriteManager : MonoBehaviour
{
private SpriteRenderer SpriteRenderer { get; set; }
private Animation Animation { get; set; }
void Awake()
{
SpriteRenderer = renderer as SpriteRenderer;
Animation = animation as Animation;
}
public void Play(string animationName)
{
Animation.Play(animationName);
}
public void SetNextSprite(Sprite sprite)
{
SpriteRenderer.sprite = sprite;
}
}
The trick happens when creating your animation clips, when setting your sprites over the keyframes just create an event calling the SetNextSprite method in the SpriteManager object and drag the same sprite texture used in the keyframe (note that you don’t need to put the right sprite in the animation clip keyframes but it is good for visualization).
The neat about this approach is that you don’t need to take care of the animation time etc…
It would be even better if you could create the animation clips on the fly.
This is a better approach, follow this simple steps:
1) Add this component:
using UnityEngine;
[RequireComponent(typeof(SpriteRenderer))]
[RequireComponent(typeof(Animation))]
[ExecuteInEditMode]
public class LegacyAnimateSpriteRenderer : MonoBehaviour
{
public float Frame; // Animate this value with the legacy Animator using the timeline, you can preview changes in edit mode.
public Sprite[] Frames; // Here yoy add all the sprites that will be animated
private SpriteRenderer Renderer;
void Start ()
{
Renderer = GetComponent<SpriteRenderer>();
}
void Update ()
{
int frame = Mathf.FloorToInt(Frame);
if (frame < 0 || Frames == null)
{
Frame = 0f;
return;
}
if (frame >= Frames.Length)
{
Frame = Frames.Length;
return;
}
if (Frames[frame] != Renderer.sprite)
Renderer.sprite = Frames[frame];
}
//This executes in Editor mode, we call Update so you can preview your animation in the editor.
void OnRenderObject()
{
if (!Application.isPlaying)
Update();
}
}
2) In the editor add all the frames sprites to the “Frames” List
3) Move the “Frame” value, note the frames changing.
4) Now you only need to animate the “Frames” value using the legacy system.
With this approach you don’t need to play the game to preview the animation, can use curves, add events and create all the animation clips you need because you are using the Unity tools.