【问题标题】:Unity3d delay in while true loop not working真正循环不起作用的Unity3d延迟
【发布时间】:2016-06-22 10:30:27
【问题描述】:

我仍在开发游戏,但遇到了另一个问题,我正在尝试创建一个无限循环,每次执行都会等待几秒钟,我目前有:


StartScript.cs

using UnityEngine;
using System.Collections;
using ProgressBar;

public class StartScript : MonoBehaviour {

    private ProgressBarBehaviour hunger;
    private ProgressBarBehaviour stamina;
    private ProgressRadialBehaviour health;
    private ProgressBarBehaviour thirst;

    public void OnGUI(){
        this.hunger = GameObject.Find("hungerBar").GetComponent<ProgressBarBehaviour>();
        this.stamina = GameObject.Find("staminaBar").GetComponent<ProgressBarBehaviour>();
        this.health = GameObject.Find("healthBar").GetComponent<ProgressRadialBehaviour>();
        this.thirst = GameObject.Find("thirstBar").GetComponent<ProgressBarBehaviour>();

        this.health.Value = 100f;
        this.stamina.Value = 100f;

        StartCoroutine ("runHunger");
    }

    bool addBar(ProgressBarBehaviour target, float percentage){
        Debug.Log (percentage);
        if ((target.Value + percentage) <= 100f) {
            target.IncrementValue (percentage);
            return true;
        }
        return false;
    }

    bool damageBar(ProgressBarBehaviour target, float percentage){
        if ((target.Value - percentage) >= 0f) {
            target.DecrementValue (percentage);
            return true;
        }
        return false;
    }

    bool addRadial(ProgressRadialBehaviour target, float percentage){
        if ((target.Value + percentage) <= 100f) {
            target.IncrementValue (percentage);
            return true;
        }
        return false;
    }

    bool damageRadial(ProgressRadialBehaviour target, float percentage){
        if ((target.Value - percentage) >= 0f) {
            target.DecrementValue (percentage);
            return true;
        }
        return false;
    }

    IEnumerator runHunger(){
        while (true) {
            yield return new WaitForSeconds(10f);
            /*if (!this.addBar(this.hunger,5f)) {
                this.damageRadial(this.health,3f);
            }*/
            Debug.Log("Time: "+Time.time);
        }
    }

    IEnumerator runHealth(){
        while (true) {

        }
    }
    /*
    IEnumerator runThirst(){
        while (true) {

            if (!this.thirst.Add (2)) {
                this.health.Damage(8);
            }

        }
    }*/
}

正如你们所看到的,我正在尝试使用yield return new WaitForSeconds() 创建一个while(true){} 循环,其想法是它每(在此测试用例中)10 秒运行一次循环中的函数。

第一次执行就像一个魅力,它等待 10 秒,但之后它只等待大约 0.1 秒并再次执行。


希望有人能帮我解决这个问题。

【问题讨论】:

  • ciao Giovanniu——永远,永远不要出于任何原因使用“ongui”——它已从 Unity 中删除!只需使用普通的 UI。非常简单,(1)点击“添加画布”(通常选择“缩放到屏幕大小”)。 (2) 点击“添加按钮”。 (3)你完成了..回家去老婆和酒!

标签: c# unity3d while-loop infinite-loop yield-return


【解决方案1】:

我目前在你的代码中看到了太多错误的东西。

这个:

IEnumerator runHealth(){
    while (true) {

    }
}

改成

IEnumerator runHealth(){
    while (true) {

        yield return null;
    }
}

还有这个

IEnumerator runThirst(){
    while (true) {

        if (!this.thirst.Add (2)) {
            this.health.Damage(8);
        }
    }           
}

改成

IEnumerator runThirst(){
    while (true) {

        if (!this.thirst.Add (2)) {
            this.health.Damage(8);
        }
        yield return null;
    }
}

如果你要在协程中使用while(true),你必须让 yield 返回一些东西,否则它会锁定你的程序。首先修复这些问题。最好将它放在 while 循环的右括号之前。

我相信您在其他 脚本中也做到了遍历其他脚本其余并做同样的事情。将yield return null inside 放入每个 coroutine 函数中的每个 while 循环

另一个大错误OnGUI函数删除所有代码,并将其放入Start函数中,如下所示。每帧代码被调用太多次,这将导致变慢,因为您将创建 很多 协程 从不 停止,因为您在协程函数中的 while 循环。把它放在 Start 函数中将调用它一次

void Start()
{
    this.hunger = GameObject.Find("hungerBar").GetComponent<ProgressBarBehaviour>();
    this.stamina = GameObject.Find("staminaBar").GetComponent<ProgressBarBehaviour>();
    this.health = GameObject.Find("healthBar").GetComponent<ProgressRadialBehaviour>();
    this.thirst = GameObject.Find("thirstBar").GetComponent<ProgressBarBehaviour>();

    this.health.Value = 100f;
    this.stamina.Value = 100f;

    StartCoroutine ("runHunger");
}

【讨论】:

  • 它目前正在 yield 返回一个新的 waitforseconds 所以它总是返回一些东西,唯一真正运行的是饥饿的东西
  • 不,我说的是 while(true) 的其他函数。那是一个无限循环,因此必须返回 yield return null。带有 yield return new WaitForSeconds(10f) 的那个很好。
  • 但整个问题是那些等待秒的人在这段时间内只想要一次
  • 我发现了另一个问题并编辑了我的答案。请修复所有这些。
  • np。如果你不修改runHealth和runThirst,你的游戏就会死机。
【解决方案2】:

拨打StartCoroutine ("runHunger"); OnGUI() 以外的地方。届时它将起作用。由于每次调用 OnGUI 都会启动一个新的协程

在 Start() 或其他地方调用 StartCoroutine

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-02-21
    • 2011-05-31
    • 1970-01-01
    相关资源
    最近更新 更多