协程在停止后仍然继续。

huangapple go评论58阅读模式
英文:

Coroutine keeps going after stopped

问题

以下是你要翻译的代码部分:

我正在制作一个类似《街头霸王》的游戏,并希望能够充能攻击。当你按住攻击键约1秒钟时,充能应该开始,然后每0.1秒增加0.1,直到达到最大值。当我释放键时,它应该停在当前位置并重置充能。但某种原因在我释放键后它会重新开始。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Attack : MonoBehaviour
{
    public KeyCode attackKey;
    public KeyCode stunKey;
    public int damage;
    public bool charging;
    public float maxChargeMultiplier;
    public float charge;
    public float attackDelay;
    public float attackTimer;
    public Stats target;

    private void Start()
    {
        attackTimer = attackDelay;
    }

    void Update()
    {
        // 开始充能
        if (Input.GetKeyDown(attackKey) && attackTimer >= attackDelay)
        {
            attackTimer = 0;
            StartCoroutine(ChargeAttack());
        }

        if (Input.GetKeyUp(attackKey))
        {
            Damage();
            StopCoroutine(ChargeAttack());
            charge = 0;
            StartCoroutine(RechargeAttack());
        }
    }

    public IEnumerator RechargeAttack()
    {
        for (int i = 0; i < attackDelay * 10; i++)
        {
            yield return new WaitForSecondsRealtime(0.1f);
            attackTimer += 0.1f;
        }
    }
    
    public IEnumerator ChargeAttack()
    {
        yield return new WaitForSecondsRealtime(1.25f);

        for(int c = 0; c < maxChargeMultiplier * 10; c++)
        {
            yield return new WaitForSecondsRealtime(0.1f);
            charge += 0.1f;
        }
    }

    public void Damage()
    {
        if(target != null)
        {
            if (target.blocking)
            {
                return;
            }
            else
            {
                target.health -= Mathf.RoundToInt(damage * charge);
                gameObject.GetComponent<Stats>().combo += 20;
            }
        }

        charge = 0;
    }

    private void OnTriggerEnter2D(Collider2D col)
    {
        if (col.GetComponent<Stats>())
        {
            target = col.gameObject.GetComponent<Stats>();
        }
    }

    private void OnTriggerExit2D(Collider2D col)
    {
        if (col.GetComponent<Stats>() == target)
        {
            target = null;
        }
    }
}
英文:

I am making a Street Fighter type game and want you to be able to charge an attack. it it meant to start when you hold the attack key for about 1 second, then it should count up by 0.1 every 0.1 seconds until at a maximum value. after i release the key it should stop where it is and reset the charge. Some reason it starts again after i release the key.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Attack : MonoBehaviour
{
public KeyCode attackKey;
public KeyCode stunKey;
public int damage;
public bool charging;
public float maxChargeMultiplier;
public float charge;
public float attackDelay;
public float attackTimer;
public Stats target;
private void Start()
{
attackTimer = attackDelay;
}
void Update()
{
//Start Charge
if (Input.GetKeyDown(attackKey) &amp;&amp; attackTimer &gt;= attackDelay)
{
attackTimer = 0;
StartCoroutine(ChargeAttack());
}
if (Input.GetKeyUp(attackKey))
{
Damage();
StopCoroutine(ChargeAttack());
charge = 0;
StartCoroutine(RechargeAttack());
}
}
public IEnumerator RechargeAttack()
{
for (int i = 0; i &lt; attackDelay * 10; i++)
{
yield return new WaitForSecondsRealtime(0.1f);
attackTimer += 0.1f;
}
}
public IEnumerator ChargeAttack()
{
yield return new WaitForSecondsRealtime(1.25f);
for(int c = 0; c &lt; maxChargeMultiplier * 10; c++)
{
yield return new WaitForSecondsRealtime(0.1f);
charge += 0.1f;
}
}
public void Damage()
{
if(target != null)
{
if (target.blocking)
{
return;
}
else
{
target.health -= Mathf.RoundToInt(damage * charge);
gameObject.GetComponent&lt;Stats&gt;().combo += 20;
}
}
charge = 0;
}
private void OnTriggerEnter2D(Collider2D col)
{
if (col.GetComponent&lt;Stats&gt;())
{
target = col.gameObject.GetComponent&lt;Stats&gt;();
}
}
private void OnTriggerExit2D(Collider2D col)
{
if (col.GetComponent&lt;Stats&gt;() == target)
{
target = null;
}
}
}

答案1

得分: 1

你需要停止已经启动的协程。

StartCoroutine 返回一个 Coroutine。这个 Coroutine 就是需要停止的对象。为了停止这个确切的协程,我们需要将它存储在一个变量中,这样我们以后可以在需要时再次引用它。

private Coroutine chargeAttackRoutine; // <- 存储已启动的协程的变量

private void Update()
{
    if (Input.GetKeyDown(attackKey))
    {
        chargeAttackRoutine = StartCoroutine(ChargeAttack()); // <- 存储协程
    }
    if (Input.GetKeyUp(attackKey))
    {
        StopCoroutine(chargeAttackRoutine); // <- 停止协程
    }
}
英文:

You need to stop the coroutine that was started.

StartCoroutine returns a Coroutine. This Coroutine is what needs to be stopped. In order to stop that exact coroutine, we need to store it in a variable so we can reference it again later when we want to stop it.

private Coroutine chargeAttackRoutine; // &lt;- Variable for the coroutine that was started
private void Update()
{
if (Input.GetKeyDown(attackKey))
{
chargeAttackRoutine = StartCoroutine(ChargeAttack()); // &lt;- Store the coroutine
}
if (Input.GetKeyUp(attackKey))
{
StopCoroutine(chargeAttackRoutine); // &lt;- Stop the coroutine
}
}

huangapple
  • 本文由 发表于 2023年6月8日 04:55:20
  • 转载请务必保留本文链接:https://go.coder-hub.com/76427064.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定