Author Topic: Making the text shake  (Read 2110 times)

BTStone

  • Beta User
  • Newbie
  • *
  • Posts: 20
Making the text shake
« on: April 30, 2016, 08:25:55 AM »
How would I go on and make my text shake like in this tutorial:

https://www.youtube.com/watch?v=3h5QKLUtgwg

Stephan B.

  • Administrator
  • Hero Member
  • *****
  • Posts: 5687
Re: Making the text shake
« Reply #1 on: April 30, 2016, 12:03:56 PM »
How would I go on and make my text shake like in this tutorial:

https://www.youtube.com/watch?v=3h5QKLUtgwg

I would suggest taking a look at the latest example included with TMP - Example "14 - Animating Vertex Attributes" and instead of adding the FX per character to do it per line or word.
« Last Edit: April 30, 2016, 01:41:04 PM by Stephan B. »

Stephan B.

  • Administrator
  • Hero Member
  • *****
  • Posts: 5687
Re: Making the text shake
« Reply #2 on: May 01, 2016, 03:24:47 AM »
Here is an example using a modified version of the example script I mentioned above.



Here is the modified script which works with the latest releases based on version 0.1.54.

Code: C#
  1. using UnityEngine;
  2. using System.Collections;
  3.  
  4.  
  5. namespace TMPro.Examples
  6. {
  7.  
  8.    public class VertexShakeA : MonoBehaviour
  9.    {
  10.  
  11.        public float AngleMultiplier = 1.0f;
  12.        public float SpeedMultiplier = 1.0f;
  13.        public float ScaleMultiplier = 1.0f;
  14.        public float RotationMultiplier = 1.0f;
  15.  
  16.        private TMP_Text m_TextComponent;
  17.        private bool hasTextChanged;
  18.  
  19.  
  20.        void Awake()
  21.        {
  22.            m_TextComponent = GetComponent<TMP_Text>();
  23.        }
  24.  
  25.        void OnEnable()
  26.        {
  27.            // Subscribe to event fired when text object has been regenerated.
  28.            TMPro_EventManager.TEXT_CHANGED_EVENT.Add(ON_TEXT_CHANGED);
  29.        }
  30.  
  31.        void OnDisable()
  32.        {
  33.            TMPro_EventManager.TEXT_CHANGED_EVENT.Remove(ON_TEXT_CHANGED);
  34.        }
  35.  
  36.  
  37.        void Start()
  38.        {
  39.            StartCoroutine(AnimateVertexColors());
  40.        }
  41.  
  42.  
  43.        void ON_TEXT_CHANGED(Object obj)
  44.        {
  45.            hasTextChanged = true;
  46.        }
  47.  
  48.        /// <summary>
  49.        /// Method to animate vertex colors of a TMP Text object.
  50.        /// </summary>
  51.        /// <returns></returns>
  52.        IEnumerator AnimateVertexColors()
  53.        {
  54.  
  55.            // We force an update of the text object since it would only be updated at the end of the frame. Ie. before this code is executed on the first frame.
  56.            // Alternatively, we could yield and wait until the end of the frame when the text object will be generated.
  57.            m_TextComponent.ForceMeshUpdate();
  58.  
  59.            TMP_TextInfo textInfo = m_TextComponent.textInfo;
  60.  
  61.            Matrix4x4 matrix;
  62.            Vector3[][] copyOfVertices = new Vector3[0][];
  63.  
  64.            int loopCount = 0;
  65.            hasTextChanged = true;
  66.  
  67.            while (true)
  68.            {
  69.                // Allocate new vertices
  70.                if (hasTextChanged)
  71.                {
  72.                    if (copyOfVertices.Length < textInfo.meshInfo.Length)
  73.                        copyOfVertices = new Vector3[textInfo.meshInfo.Length][];
  74.  
  75.                    for (int i = 0; i < textInfo.meshInfo.Length; i++)
  76.                    {
  77.                        int length = textInfo.meshInfo[i].vertices.Length;
  78.                        copyOfVertices[i] = new Vector3[length];
  79.                    }
  80.  
  81.                    hasTextChanged = false;
  82.                }
  83.  
  84.                int characterCount = textInfo.characterCount;
  85.  
  86.                // If No Characters then just yield and wait for some text to be added
  87.                if (characterCount == 0)
  88.                {
  89.                    yield return new WaitForSeconds(0.25f);
  90.                    continue;
  91.                }
  92.  
  93.                int lineCount = textInfo.lineCount;
  94.  
  95.                // Iterate through each line of the text.
  96.                for (int i = 0; i < lineCount; i++)
  97.                {
  98.  
  99.                    int first = textInfo.lineInfo[i].firstCharacterIndex;
  100.                    int last = textInfo.lineInfo[i].lastCharacterIndex;
  101.  
  102.                    // Determine the center of each line
  103.                    Vector3 centerOfLine = (textInfo.characterInfo[first].bottomLeft + textInfo.characterInfo[last].topRight) / 2;
  104.                    Quaternion rotation = Quaternion.Euler(0, 0, Random.Range(-0.25f, 0.25f) * RotationMultiplier);
  105.  
  106.                    // Iterate through each character of the line.
  107.                    for (int j = first; j <= last; j++)
  108.                    {
  109.                        // Skip characters that are not visible and thus have no geometry to manipulate.
  110.                        if (!textInfo.characterInfo[j].isVisible)
  111.                            continue;
  112.  
  113.                        // Get the index of the material used by the current character.
  114.                        int materialIndex = textInfo.characterInfo[j].materialReferenceIndex;
  115.  
  116.                        // Get the index of the first vertex used by this text element.
  117.                        int vertexIndex = textInfo.characterInfo[j].vertexIndex;
  118.  
  119.                        // Get the vertices of the mesh used by this text element (character or sprite).
  120.                        Vector3[] sourceVertices = textInfo.meshInfo[materialIndex].vertices;
  121.  
  122.                        // Need to translate all 4 vertices of each quad to aligned with center of character.
  123.                        // This is needed so the matrix TRS is applied at the origin for each character.
  124.                        copyOfVertices[materialIndex][vertexIndex + 0] = sourceVertices[vertexIndex + 0] - centerOfLine;
  125.                        copyOfVertices[materialIndex][vertexIndex + 1] = sourceVertices[vertexIndex + 1] - centerOfLine;
  126.                        copyOfVertices[materialIndex][vertexIndex + 2] = sourceVertices[vertexIndex + 2] - centerOfLine;
  127.                        copyOfVertices[materialIndex][vertexIndex + 3] = sourceVertices[vertexIndex + 3] - centerOfLine;
  128.  
  129.                        // Determine the random scale change for each character.
  130.                        float randomScale = Random.Range(0.995f - 0.001f * ScaleMultiplier, 1.005f + 0.001f * ScaleMultiplier);
  131.  
  132.                        // Setup the matrix rotation.
  133.                        matrix = Matrix4x4.TRS(Vector3.one, rotation, Vector3.one * randomScale);
  134.  
  135.                        // Apply the matrix TRS to the individual characters relative to the center of the current line.
  136.                        copyOfVertices[materialIndex][vertexIndex + 0] = matrix.MultiplyPoint3x4(copyOfVertices[materialIndex][vertexIndex + 0]);
  137.                        copyOfVertices[materialIndex][vertexIndex + 1] = matrix.MultiplyPoint3x4(copyOfVertices[materialIndex][vertexIndex + 1]);
  138.                        copyOfVertices[materialIndex][vertexIndex + 2] = matrix.MultiplyPoint3x4(copyOfVertices[materialIndex][vertexIndex + 2]);
  139.                        copyOfVertices[materialIndex][vertexIndex + 3] = matrix.MultiplyPoint3x4(copyOfVertices[materialIndex][vertexIndex + 3]);
  140.  
  141.                        // Revert the translation change.
  142.                        copyOfVertices[materialIndex][vertexIndex + 0] += centerOfLine;
  143.                        copyOfVertices[materialIndex][vertexIndex + 1] += centerOfLine;
  144.                        copyOfVertices[materialIndex][vertexIndex + 2] += centerOfLine;
  145.                        copyOfVertices[materialIndex][vertexIndex + 3] += centerOfLine;
  146.                    }
  147.                }
  148.  
  149.                // Push changes into meshes
  150.                for (int i = 0; i < textInfo.meshInfo.Length; i++)
  151.                {
  152.                    textInfo.meshInfo[i].mesh.vertices = copyOfVertices[i];
  153.                    m_TextComponent.UpdateGeometry(textInfo.meshInfo[i].mesh, i);
  154.                }
  155.  
  156.                yield return new WaitForSeconds(0.1f);
  157.            }
  158.        }
  159.  
  160.    }
  161. }
  162.  

BTStone

  • Beta User
  • Newbie
  • *
  • Posts: 20
Re: Making the text shake
« Reply #3 on: May 01, 2016, 07:23:08 AM »
Woah, didn't expect to get that script, thanks a ton, will check it out! Thank you!