按键冷却

时间:2019-08-12 09:37:02

标签: c# unity3d

我正在研究水平2D无限流道的个人项目。我在跳跃动作方面遇到问题,玩家可以按住跳跃按钮并在触地时立即跳跃。我想强制播放器释放按钮以再次跳转。我想在他漂浮时做出相同的动作(在跳跃开始时,当玩家开始跌倒时,其y速度会降低几秒钟)。我遵循单一责任原则,因此跳转和浮动是2个单独的脚本。

我已经尝试实现一个计时器,该计时器将在玩家触地时进行计数,经过一段时间后,玩家将能够再次跳跃,但是由于您可以按住跳跃按钮,时间和确定的时间花费在地面播放器上之后,即使不释放按钮也只会再次跳动。

public class Jumping : MonoBehaviour
{
    public bool isJumping;
    public bool isGrounded;
    public float speedUp;
    public float verticalAxis;

    public float timePassed;
    public float jumpLimit;
    private Rigidbody2D rb;

    // Start is called before the first frame update
    void Start()
    {
        rb = gameObject.GetComponent<Rigidbody2D>();
    }

    // Update is called once per frame
    void Update()
    {
        verticalAxis = Input.GetAxisRaw("Vertical");
        if (verticalAxis > 0 && timePassed == 0)
        {
            isJumping = true;
        }
    }

    private void FixedUpdate()
    {
        if (isJumping)
        {
            Jump();
        }
    }

    private void OnCollisionStay2D(Collision2D collision)
    {
        if (collision.collider.tag == "Ground")
        {

            isGrounded = true;
            timePassed = 0f;
        }
    }


    private void Jump()
    {
        isGrounded = false;
        //Modifying y component of players rigidbody(jumping)
        Vector2 velocity = Vector2.up * speedUp * verticalAxis;
        rb.velocity = velocity;

        //Counting time when jumping 
        timePassed += Time.deltaTime;
        if (timePassed >= jumpLimit)
        {
            isJumping = false;
        }
    }
}

P.S。我试图按照stackoverflow的建议缩小代码中的代码,但是我不知道该切掉什么,因为对我来说,一切对于解决问题都是至关重要的。谢谢!

2 个答案:

答案 0 :(得分:1)

在不知道其余代码的情况下,我将使用一个附加标志,并且显然使用一些方法来获得冷却延迟,例如

public float jumpCoolDownTime;
private float coolDownTimer;
private bool canJump;

void Update()
{
    // if no can jump you can't jump again
    if(!canJump)
    {
        verticalAxis = Input.GetAxisRaw("Vertical");
        if (verticalAxis > 0)
        {
            canJump = false;
            isJumping = true;
            coolDownTimer = 0;
        }
    }
    else
    {
        // run timer to enable jump again
        if(isGrounded) coolDownTimer += Time.deltaTime;

        if(coolDownTimer >= jumpCoolDownTime)
        {
            canJump = true;
        }
    }
}

不过,您可以使用Coroutines

来简化代码
public bool isJumping;
public float speedUp;
public float verticalAxis;

public float jumpLimit;
public float coolDownTime;

private Rigidbody2D rb;

// Start is called before the first frame update
void Start()
{
    rb = gameObject.GetComponent<Rigidbody2D>();
}

void Update()
{
    // do nothing is already jumping
    if(isJumping) return;

    verticalAxis = Input.GetAxisRaw("Vertical");
    if (verticalAxis > 0)
    {
        // start jumping
        StartCoroutine(Jump());
    }
}

private void OnCollisionEnter2D(Collision2D collision)
{
    if (collision.collider.tag != "Ground") return;

    isGrounded = true;
    StartCoroutine(CoolDown());
}

private IEnumerator Jump()
{
    isJumping = true;
    isGrounded = false;
    coolDownTimer = 0;

    var timePassed = 0f;
    while(timePassed < jumpLimit)
    {
        // wait for the FixedUpdate call
        yield return new WaitForFixedUpdate();

        Vector2 velocity = Vector2.up * speedUp * verticalAxis;
        rb.velocity = velocity;
    }
}

private IEnumerator CoolDown()
{
    yield return new WaitForSeoncds(coolDownTime);

    isJumping = false;
}

答案 1 :(得分:0)

如果您正在使用轴进行跳跃,则可以通过以下方式查看玩家是否释放了按钮:

if (GetAxis("Vertical") == 0.0) { //Button up
     // do stuff
}
if(GetAxis("Vertical") > 0)
{
     //Button down, is jumping
}

在Unity轴上不是booleans,它们是系数,如果您使用控制器,则可以为不同的强度设置不同的行为。