Setting up texts

You can set texts to Text Animator from two different UI systems:

This page contains some information already present in Install and Quick Start, but also other details and suggestions for each system and in general. Make sure to read the Best Practices section!


UI Toolkit

P.S. Assuming you already know how to use UI Toolkit and what it does.

From the UI Builder

  • Go to Library -> Project

  • Drag "AnimatedLabel" from "Custom Controls/Febucci/Text Animator for Unity" in your hierarchy!

We are working to make sure you can animate built in Labels and Buttons from UI toolkit directly! (Unity 6.3 and up.) Stay updated!

Your .uxml should look like this:

Via Code

You can create an instance of the "Febucci.TextAnimatorForUnity.AnimatedLabel" class and add it to your UI document, like this:

using UnityEngine;
using UnityEngine.UIElements;
using Febucci.TextAnimatorForUnity; // <- import Text Animator's namespace

public class ExampleScript : MonoBehaviour
{ 
    [SerializeField] UIDocument document;

    void Start()
    {
        var container = document.rootVisualElement.contentContainer;
        var animatedLabel = new AnimatedLabel(); // <- create an animated label
        container.Add(animatedLabel); // <- add it to the content container
        // [..]
        animatedLabel.SetText("<wave>hello"); // <- set the text
    }
}

Text Mesh Pro

P.S. Assuming you already know how to use Text Mesh Pro and how it works.

Add a Text Animator - Text Mesh Pro component on the same GameObject that has a TextMeshPro component (either UI or world space!):

Your inspector should look like this:

Best Practices for setting text via code

To set the text to your TextMeshPro object via code, please reference Text Animator's script instead of TMPro, like the following:

using UnityEngine;
using TMPro; 
using Febucci.TextAnimatorForUnity.TextMeshPro; // <- import Text Animator's namespace

public class ExampleScript : MonoBehaviour
{
    [SerializeField] TMP_Text textMeshPro;
    [SerializeField] TextAnimator_TMP textAnimator;

    void Start()
    {
        // 🚫 Don't: set text through TMPro
        textMeshPro.SetText("<wave>hello");

        // ✅ Do: set text through Text Animator directly
        textAnimator.SetText("<wave>hello");
    }

}

P.S. Referencing TMPro will work anyways, but setting the text with TextAnimator is better integrated as we have more control on the text.


Best Practices

Set the entire text/dialogue only once

Please try to set text just once, and use the typewriter / visibility methods to control how it appears.

If you really need to append text later in time, you can use the "textAnimator.AppendText" method.

Example

If you have a character that says "Helloooo how are you doing?", and you want to display it letter by letter, simply do: typewriter.ShowText("Hellooooo how are you doing?"); and that's it! Show and hide letters dynamically


If you're building a dynamic string, you can still do that before setting its value to the typewriter/animator.

int apples = 5; //later taken from the game state
string playerName = "Bob";

// build the entire dialogue line first
string dialogue = $"Hello {playerName}, you've got {apples} apples";

// then set the text once
typewriter.ShowText(dialogue);

(If you're using a Dialogue System, they'll do this for you - no worries ! Integrations)

Why should I set the entire text once, instead of character by character?

Performance! (Even if you didn't have Text Animator.)

Every time you set the text, TextMeshPro or UI toolkit need to calculate its mesh, positioning etc., and Text Animator has then to re-calculate character durations and more. This means that if you change it multiple times per second (e.g. adding more letters), you're doing these calculations every time.

To display characters one by one, you can simply set the full text once, and then start the typewriter: Show and hide letters dynamically