Search Unity

Button Animation Transition Bug

Discussion in 'UGUI & TextMesh Pro' started by enchiridion, May 16, 2017.

  1. enchiridion

    enchiridion

    Joined:
    Oct 29, 2014
    Posts:
    57
    Hey guys

    Trying to animate my buttons when pushed (scale it down).

    I used the Animation Transition on the button and in the "Pressed" clip I set my button scale to 0.8.

    The problem is that if I am on the edge of my button, the states constantly switch between "Pressed" and "Highlighted" as seen in this GIF:


    If I remove the "Highlighted" state, then the button gets stuck in "Pressed" state.

    Another issue is that in the GIF above, the button doesn't actually get pressed/executed, because the cursor is not inside it on mouseUp.

    Am I doing this wrong or does someone have any idea of how to fix this?

    EDIT: even if I don't use any button transition and manually play animations through a script, the cursor not being inside the button on mouseUp is still an issue.
     
  2. tdelrue-poc

    tdelrue-poc

    Joined:
    Jul 27, 2017
    Posts:
    2
    Same problem for me, my trigger animation switch between Normal and Hightlighted constantly! Anyone have a solution?
     
  3. TonyLi

    TonyLi

    Joined:
    Apr 10, 2012
    Posts:
    12,697
    You can make the main button image invisible (set Color > Alpha to zero) and animate a child image. Unity UI will do its raycasts against the main button image, which remains the same size.
     
  4. enchiridion

    enchiridion

    Joined:
    Oct 29, 2014
    Posts:
    57
    Yes but that just seems so unnecessary.

    In my opinion, a button, no matter how simple or complex, should be:

    My Buttons (button component, animate this gameobjects scale)
    - child 1 (eg image)
    - child 2 (eg text)
    - etc

    Of course a fix would be:
    My Buttons (button component)
    - AnimationParent (animate this gameobjects scale)
    -- child 1
    - -child 2
    - -etc

    In fact not even sure if that would work.
     
    Last edited: Aug 1, 2017
  5. imphenzia

    imphenzia

    Joined:
    Jun 28, 2011
    Posts:
    413
    Hello,

    I worked around this problem by creating a script that I assign to a child object. It's not the prettiest solution but it's easy to implement for multiple buttons at least.

    1. Create a child gameobject of the button (it must be a direct child)
    2. Add this script to the gameobject:
    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4. using UnityEngine.UI;
    5.  
    6. [RequireComponent(typeof(Image))]
    7. [RequireComponent(typeof(RectTransform))]
    8. public class ButtonHitbox : MonoBehaviour
    9. {
    10.     private Image _image;
    11.     private RectTransform _rt;
    12.     private RectTransform _parent;
    13.     private Vector3 _orgScale;
    14.  
    15.     void Reset()
    16.     {
    17.         // Make it invisible when component is added
    18.         _image = GetComponent<Image>();
    19.         _image.color = new Color(0, 0, 0, 0);
    20.         // Reset the local position just in case
    21.         GetComponent<RectTransform>().localPosition = Vector3.zero;
    22.     }
    23.  
    24.     void Awake ()
    25.     {
    26.         _rt = GetComponent<RectTransform>();      
    27.         _parent = _rt.transform.parent.GetComponent<RectTransform>();
    28.         // Set transform size to same as parent
    29.         _rt.sizeDelta = _parent.sizeDelta;
    30.         _orgScale = _parent.localScale;
    31.     }
    32.  
    33.     void LateUpdate ()
    34.     {
    35.         // Always use parent scale to counter the scale - do it in lateupdate after the animation has been performed
    36.         _rt.localScale = new Vector3(_orgScale.x / _parent.localScale.x, _orgScale.y / _parent.localScale.y, 1);
    37.     }
    38. }
    That should do the trick. Basically it adds a transparent child image of equal size to the parent and it compensates for any animation resizing in LateUpdate so raycasting still hits the original area. Haven't tested it fully yet but it seems to do the trick.
     
  6. xuxu

    xuxu

    Joined:
    May 6, 2013
    Posts:
    3