0
votes
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class BlendShapesController : MonoBehaviour
{
    public float duration;
    [Range(0, 100)]
    public float valueRange;
    private SkinnedMeshRenderer bodySkinnedMeshRenderer;
    private bool randomizeNumbers = true;

    // Start is called before the first frame update
    void Start()
    {
        bodySkinnedMeshRenderer = GetComponent<SkinnedMeshRenderer>();
        //StartCoroutine(RandomNumbers());

        StartCoroutine(AnimateMouth());
    }

    // Update is called once per frame
    void Update()
    {
        //AnimateMouth();

        if(randomizeNumbers == true)
        {
            //StartCoroutine(RandomNumbers());

            randomizeNumbers = false;
        }
    }

    IEnumerator RandomNumbers()
    {
        int rand = Random.Range(0, 23);
        bodySkinnedMeshRenderer.SetBlendShapeWeight(0, rand);

        yield return new WaitForSeconds(0.3f);

        randomizeNumbers = true;
    }

    //Lerp between startValue and endValue over 'duration' seconds
    private IEnumerator LerpShape(float startValue, float endValue, float duration)
    {
        float elapsed = 0;
        while (elapsed < duration)
        {
            elapsed += Time.deltaTime;
            float value = Mathf.Lerp(startValue, endValue, elapsed / duration);
            bodySkinnedMeshRenderer.SetBlendShapeWeight(0, value);
            yield return null;
        }
    }

    private bool talking = true;
    //animate open and closed, then repeat
    public IEnumerator AnimateMouth()
    {
        while (talking)
        {
            //yield return StartCoroutine waits for that coroutine to finish before continuing
            yield return StartCoroutine(LerpShape(0, valueRange, duration));
            yield return StartCoroutine(LerpShape(valueRange, 0, duration)); 
        }

        yield return new WaitForSeconds(10);

        talking = false;
    }
}

At the bottom it's making a while loop while talking is true. I want that after 10 seconds talking will be false or to stop the Coroutine.

I tried this : but it does nothing the while loop is still working talking is still true.

yield return new WaitForSeconds(10);
    
talking = false;
1

1 Answers

1
votes

Instead of a Boolean for talking, set a deadline, e.g. a date/time stamp that says how long to talk.

public IEnumerator AnimateMouth()
{
    var talkUntil = DateTime.Now.AddSeconds(10);

    while (DateTime.Now < talkUntil)
    {
        yield return StartCoroutine(LerpShape(0, valueRange, duration));
        yield return StartCoroutine(LerpShape(valueRange, 0, duration)); 
    }
}