Reputation: 61
I am working on a simple animation for my UI elements.
I have an animator component which has 2 different animations - ZoomIn and ZoomOut.
These animations are displayed whenever an UI element (e.g. Button) needs to be displayed on the screen.
I normally prefer deactivating the gameobject when not displaying.
I have written the following method for the animations:
private IEnumerator ToggleObjectWithAnimation (GameObject gameObj) {
Animator gameObjectAnimator = gameObj.GetComponent<Animator> (); // Animator is set to unscaled time
if (gameObj.activeSelf == false) {
gameObj.transform.localScale = new Vector3 (0, 0, 1.0f);
gameObj.SetActive (true);
gameObjectAnimator.SetTrigger ("ZoomIn");
yield return new WaitForSeconds (0.5f);
} else if(gameObj.activeSelf == true) {
gameObjectAnimator.SetTrigger ("ZoomOut");
yield return new WaitForSeconds (0.5f);
gameObj.SetActive (false); // code not execute when timescale = 0
}
yield return null;
}
The code works fine when for most of the screens, but shows problem when I pause the game using Time.timeScale = 0
.
When timescale is 0, the line gameObj.SetActive(false)
does not work.
Upvotes: 6
Views: 4475
Reputation: 90813
I know it's probably a bit late but:
The problem is not the SetActive
but that WaitForSeconds
is affected by the Time.timeScale
!
The actual time suspended is equal to the given time multiplied by
Time.timeScale
. SeeWaitForSecondsRealtime
if you wish to wait using unscaled time.
So if you have Time.timescale=0
the WaitForSeconds
will never finish!
You should rather use WaitForSecondsRealtime
private IEnumerator ToggleObjectWithAnimation (GameObject gameObj)
{
Animator gameObjectAnimator = gameObj.GetComponent<Animator> (); // Animator is set to unscaled time
if (gameObj.activeSelf == false)
{
gameObj.transform.localScale = new Vector3 (0, 0, 1.0f);
gameObj.SetActive (true);
gameObjectAnimator.SetTrigger ("ZoomIn");
yield return new WaitForSecondsRealtime (0.5f);
}
else if (gameObj.activeSelf == true)
{
gameObjectAnimator.SetTrigger ("ZoomOut");
yield return new WaitForSecondsRealtime (0.5f);
gameObj.SetActive (false); // code not execute when timescale = 0
}
yield return null;
}
Upvotes: 13