我正在使用协程来管理游戏中的通电冷却时间。当玩家与加电碰撞时,他们会获得效果,并且会开始冷却,因此他们在一定时间内无法再次使用它。
我正在使用协同程序来管理这些冷却时间-将gameObject设置为false,等待冷却时间,然后将gameObject
设置为true。
我的代码:
IEnumerator RespawnTime ()
{
gameObject.SetActive(false);
Debug.Log("disabled");
yield return new WaitForSeconds(3f);
gameObject.SetActive(true);
Debug.Log("enabled");
}
private void OnCollisionEnter2D (Collision2D collision)
{
// Health stuff goes in here.
Debug.Log("Health regen!");
// Start cooldown
StartCoroutine(RespawnTime());
}
但是,一旦禁用,gameObject就再也不会激活。我认为问题不在于产量,因为注释掉SetActive语句会导致两个调试消息都在正确的时间显示。
编辑:
对不起,我没有澄清。我知道协同程序不会在已禁用的GameObjects
上运行。我制作了一个PowerUpManager
脚本,但是没有用。代码:
在PowerUp
脚本中,在OnCollisionEnter2D
方法中
StartCoroutines(PowerUpManager.RespawnTime(gameObject))
在PowerUpManager
脚本中
public static IEnumerator RespawnTime(GameObject powerUp)
{
powerUp.SetActive(false);
yield return new WaitForSeconds(3f);
powerUp.SetActive(true);
}
答案 0 :(得分:2)
打来电话的那一刻
gameObject.SetActive(false);
此对象不再收到Update
消息,因此也不再执行Coroutine。
MonoBehaviour被销毁时,或者附加了
GameObject
的协同作用也被禁用。
您第二次尝试不起作用的原因是:您仍在同一StartCoroutine
上调用GameObject
,因此PowerUpManager
类的协程现在在您的计算机上执行 GameObject
=>具有相同的效果。
如果您真的想使用PowerUpManager
,则需要一个Singleton实例,并在该实例上调用StartCoroutine
,例如
在PowerUpManager
中拥有
public static PowerUpManager Instance;
private void Awake()
{
Instance = this;
}
然后您可以从脚本中调用
PowerUpManager.Instance.StartCoroutine(PowerUpManager.RespawnTime(gameObject));
在您不需要平滑移动等简单情况下,只需一个简单的延迟,我建议您根据需要使用Invoke
。这还将在禁用或无效的GameObject
上执行。
private void EnableAfterCooldown()
{
gameObject.SetActive(true);
Debug.Log("enabled");
}
private void OnCollisionEnter2D (Collision2D collision)
{
// Health stuff goes in here.
Debug.Log("Health regen!");
gameObject.SetActive(false);
Invoke("EnableAfterCooldown", 3f);
}
答案 1 :(得分:1)
如果停用游戏对象,所有对象的组件也会被禁用,因此协程将不再被调用。
您可以做的是,将协程冷却和检查碰撞的脚本分成2个单独的脚本。
我们叫Cooldown.cs
和Powerup.cs
。
然后,让它们相互交叉引用。
在powerup.cs中,您拥有
private void OnCollisionEnter2D (Collision2D collision)
{
// Health stuff goes in here.
Debug.Log("Health regen!");
// Start cooldown
Cooldown cd = gameObject.GetComponent<cooldown>();
cd.CooldownCoroutine();
}
在Cooldown.cs中:
IEnumerator RespawnTime ()
{
Powerup pu = gameObject.GetComponent<Powerup>()
pu.SetActive(false);
Debug.Log("disabled");
yield return new WaitForSeconds(3f);
pu.SetActive(true);
Debug.Log("enabled");
}
public void CooldownCoroutine()
{
// Health stuff goes in here.
Debug.Log("Health regen!");
// Start cooldown
StartCoroutine(RespawnTime());
}
这样,您将不会禁用整个对象,而只会禁用检查冲突的脚本。
答案 2 :(得分:0)
协程不能在禁用的游戏对象上运行!
您应该在另一个游戏对象上运行它。