Player constantly moving after implementing Dash function

Hi,

I’m a newbie just learning the ropes as I go and I’m trying to implement a dash function to my 2D player. I’ve followed tutorials on youtube and had some success but my player is moving after the dash in the direction I dash in.

I believe it’s something to do with the:

rb2d.linearVelocity = new Vector2(transform.localScale.x * dashingPower, 0f);

line of code. The player keeps moving at the dashingpower speed after the shift key has been pressed. Here is the full code for reference:

[Header("Inventory")]
public int scrollsCollected, smokebombsCollected, shurikensCollected;
public int health = 100;
private int maxHealth = 100;
public int ammo;

public Text scrollsText, shurikenText, smokebombText;
public Image healthBar, expBar, dashBar, playerImage1;



[Header("References")]
[SerializeField] private GameObject attackBox;
private Vector2 healthBarOriginalSize;
public Dictionary<string, Sprite> inventory = new Dictionary<string, Sprite>();
public Image inventoryItemImage;
public Sprite keySprite;
public Sprite shurikenSprite;
public Sprite smokeBombSprite;
public Sprite inventoryItemBlank;
// slot 1 = Shuriken
// slot 2 = SmokeBomb
// slot 3 = Keys
// Blank Sprite should Swap with the item Sprite

private bool canDash = true;
private bool isDashing;
private float dashingPower = 2.4f;
private float dashingTime = 0.2f;
private float dashingCooldown = 1f;


[SerializeField] private TrailRenderer tr;

private static NewPlayer instance;
public static NewPlayer Instance {
    get {
        if (instance == null) instance = GameObject.FindFirstObjectByType<NewPlayer>();
        return instance;
    }
}

private void Awake() {
    if (GameObject.Find("New Player")) Destroy(gameObject);
}

// Start is called before the first frame update
void Start() {
    scrollsText = GameObject.Find("Scrolls/Secret").GetComponent<Text>();


    healthBar = GameObject.Find("Health Bar").GetComponent<Image>();
    healthBarOriginalSize = healthBar.rectTransform.sizeDelta;
    DontDestroyOnLoad(gameObject);
    UpdateUI();
    SetSpawnPosition();
    gameObject.name = "New Player";

    // add an inventory item of key1 with a sprite of keysprite
    //AddInventoryItem("key1", keySprite);
    //AddInventoryItem("Shuriken", shurikenSprite);
    //AddInventoryItem("SmokeBomb", smokeBombSprite);

}

// Update is called once per frame
void Update() {

    if (isDashing)
    {
        return;
    }

    targetVelocity = new Vector2(Input.GetAxis("Horizontal") * maxSpeed, 0);

    //If the player presses "Jump" and we're grounded, set the velocity to a jump power value
    // If player attempts double jump,  it will jump at half the value of the first only once.
    if (Input.GetButtonDown("Jump") && grounded) {
        velocity.y = jumpPower;
        doubleJump = !doubleJump;
    } else if
        (Input.GetButtonDown("Jump") && doubleJump) {
        velocity.y += (jumpPower * 0.5f);
        doubleJump = false;
    }

    //Flip the player's localScale.x if the move speed is greater than .01 or less than -.01 - Something with this command is messing with the dash function
    if (targetVelocity.x < -.01) {
       transform.localScale = new Vector2(-1, 1);
     } else if (targetVelocity.x > .01) {
        transform.localScale = new Vector2(1, 1);
     }

    //If we press "Fire1", then set the attackBox to active. Otherwise, set active to false
    if (Input.GetButtonDown("Fire1")) {
        StartCoroutine(ActivateAttack());
    }

    //Check if player health is smaller than or equal to 0.
    if (health <= 0) {
        Die();
    }

    // Dash function
    if (Input.GetKeyDown(KeyCode.LeftShift) && canDash)
    {
        StartCoroutine(Dash());
    }
}

//Activate Attack Function
public IEnumerator ActivateAttack() {
    attackBox.SetActive(true);
    yield return new WaitForSeconds(attackDuration);
    attackBox.SetActive(false);
}

//Update UI elements
public void UpdateUI() {
    //If the healthBarOrigSize has not been set yet, match it to the healthBar rectTransform size!
    if (healthBarOriginalSize == Vector2.zero) healthBarOriginalSize = GameManager.Instance.healthBar.rectTransform.sizeDelta;
    GameManager.Instance.scrollsText.text = scrollsCollected.ToString();
    GameManager.Instance.healthBar.rectTransform.sizeDelta = new Vector2(healthBarOriginalSize.x * ((float)health / (float)maxHealth), GameManager.Instance.healthBar.rectTransform.sizeDelta.y);
}
public void SetSpawnPosition() {
    transform.position = GameObject.Find("Spawn Location").transform.position;
}

public void Die() {
    SceneManager.LoadScene("Level 1");
}


public void AddInventoryItem(string inventoryName, Sprite image = null) {


    inventory.Add(inventoryName, image);
    GameManager.Instance.inventoryItemImage.sprite = inventory[inventoryName];
}

public void RemoveInventoryItem(string inventoryName) {
    inventory.Remove(inventoryName);
    //The blank sprite should now swap with key sprite
    GameManager.Instance.inventoryItemImage.sprite = inventoryItemBlank;
}

private IEnumerator Dash()
{
    canDash = false;
    isDashing = true;
    float originalGravity = rb2d.gravityScale;
    rb2d.gravityScale = 0f;
    rb2d.linearVelocity = new Vector2(transform.localScale.x * dashingPower, 0f);
    tr.emitting = true;
    yield return new WaitForSeconds(dashingTime);
    tr.emitting = false;
    rb2d.gravityScale = originalGravity;
    isDashing = false;
    yield return new WaitForSeconds(dashingCooldown);
    canDash = true;
}

Hope someone can help. Thanks :slight_smile:

That just sounds like a bug… and that means… time to start debugging!

If you’re unsure of your overall approach, start with tutorials for dashing. Usually a timer is involved to “lock out” the primary controls for at least some portion of the dash, otherwise the next frame the dash will be stopped by primary controls. Again, all of this is well-covered in dashing tutorials.

By debugging you can find out exactly what your program is doing so you can fix it.

Use the above techniques to get the information you need in order to reason about what the problem is.

You can also use Debug.Log(...); statements to find out if any of your code is even running. Don’t assume it is.

Once you understand what the problem is, you may begin to reason about a solution to the problem.

Remember with Unity the code is only a tiny fraction of the problem space. Everything asset- and scene- wise must also be set up correctly to match the associated code and its assumptions.

I fixed this in the end by adding another line of code: rb2d.linearVelocity = default; after the dash function.

1 Like