我有2个类:static TimeManagerball,其中ball依赖于TimeManager

TimeManager.cs:

void FixedUpdate()
{
    if (isMoving) Timer();
    else
    {
        //isMoving = true;   //<- When I uncomment this, the problem occurs
    }

}

void Timer()
{
    currentTimeMove += Time.deltaTime * TimeDeductSpeed;

    if (currentTimeMove >= timeToMove)
    {
        isMoving = false;
        currentTimeMove = 0;
        perc = 0;
    }
    else perc = currentTimeMove / timeToMove;
}


Ball.cs:

void FixedUpdate() => MovePerBlock();

void MovePerBlock()
{
    if (TimeManager.ins.isMoving)
        transform.localPosition = Vector3.Lerp(startPosition, endPosition, TimeManager.ins.perc);
    else //<- This statement does not execute when TimeManager.isMoving = true is uncommented
    {
        startPosition = transform.localPosition;
        endPosition = startPosition + transform.forward;
    }
}


每个ball实例上的移动将取决于TimeManager
他们一起移动并停下来。如果我等到脚本停止移动并在检查器上手动设置isMoving,甚至重复相同的操作,脚本就可以正常工作。

当我取消注释“ isMoving = true”时,else中的ball.cs语句并不总是执行。我相信这是因为执行时间很快。

最佳答案

查看您的方法还可以解释您的问题。

void FixedUpdate()
{
    if (isMoving) Timer();
    else // this is same as else if(isMoving == false)
    {
        //isMoving = true;   //<- When I uncomment this, the problem occurs
    }
}


当isMoving为true时,调用Timer方法。在Timer中,您可以执行某些操作,并且在某个时候,随着操作完成,Timer会将isMoving设置为false。

但是下一帧,Timer方法将isMoving设置为false(其他语句),在else语句中,isMoving设置为true。因此,在下一帧,您将再次执行Timer操作。

结果,只有一帧没有动作。最后,您似乎只看到项目在移动,从未停止。

isMoving需要通过其他条件设置,而不是自身为假。

编辑:当您描述预期的效果时,我不明白您为什么使用此逻辑。看来您的球本来就应该一直运动,那么我不明白为什么您需要重置。从我看来,您需要创建一个锯齿波。

public float amplitude = 2f;
public float period = 2f;

void Update(){
    float tOverP = Time.time / period;
    float result = (tOverP - Mathf.Floor(tOverP)) * amplitude;
    Debug.Log (result);
}


通过此过程,您无需重置任何内容,而是继续进行下去。 perc变量是结果变量。

幅度是您想要移动的幅度。使用此设置,它从0到2。周期变量定义从0到振幅的时间。因此,使用此设置,可以在2秒内从0到2。

07-27 23:08