Search code examples
c#unity-game-enginerigid-bodies

Unity rigidbody position y moving wrong


If you need other information, try to use this game's repo and check branches. Duplicate with Github

I set rigidbody at dynamic mode and set interpolorate as extrapolate. My first code was:

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

public class player : MonoBehaviour
{
    Vector2 Moveing;
    public float Speed = 2f;
    private Rigidbody2D rb;

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

    // Update is called once per frame
    void Update()
    {
        if (Input.GetKeyDown(KeyCode.LeftArrow))
        {
            transform.eulerAngles = new Vector2(0, 180);
        }
        else if (Input.GetKeyUp(KeyCode.LeftArrow))
        {
            transform.eulerAngles = new Vector2(0, 0);
        }
...
        else if (!Input.GetKey(KeyCode.LeftArrow) && !Input.GetKey(KeyCode.RightArrow) & IsHurt == true && attacking == false)
        {
            am.Play("hurt" + lv);
        }
        else if (Input.GetKey(KeyCode.RightArrow) && !Input.GetKey(KeyCode.UpArrow) && IsHurt == false && attacking == false)
        {
            Moveing = new Vector2(1, 0);
            am.Play("walk" + lv);
        }
        else if (Input.GetKey(KeyCode.RightArrow) && !Input.GetKey(KeyCode.UpArrow) && IsHurt == true)
        {
            Moveing = new Vector2(1, 0);
            am.Play("walkhurt" + lv);
        }
        else if (Input.GetKey(KeyCode.RightArrow) && Input.GetKey(KeyCode.UpArrow) && IsHurt == false && attacking == false)
        {
            Moveing = new Vector2(2, 0);
            am.Play("run" + lv);
        }
        else if (Input.GetKey(KeyCode.RightArrow) && Input.GetKey(KeyCode.UpArrow) && IsHurt == true)
        {
            Moveing = new Vector2(2, 0);
            am.Play("runhurt" + lv);
        }
...
        else if (!Input.GetKey(KeyCode.LeftArrow) && !Input.GetKey(KeyCode.RightArrow) & IsHurt == false && attacking == true)
        {
            Moveing = new Vector2(0, 0);
            am.Play("attack" + lv);
        }
        else
        {
            Moveing = new Vector2(0, 0);
            am.Play("idle" + lv);
        }
        if (Input.GetKeyDown(KeyCode.Space)) //jump
        {
            Moveing += new Vector2(0, Speed);
        }

        rb.MovePosition(new Vector2(transform.position.x, transform.position.y) + Speed * Time.deltaTime * Moveing.normalized);
    }
}

but player didn't jump. actually it jump but very little as 0.03.

I make second code:

if (Input.GetKeyDown(KeyCode.Space)) //jump
        {
            rb.addforce(new Vector2(0,Speed));
        }` It jumped but jumping like teleporting:Teleport up as Speed value and move down slowly(using rigidbody).

I make third code with making divorced `rb.MovePosition(new Vector2(transform.position.x, transform.position.y) + Speed * Time.deltaTime * Moveing.normalized);` so code was:`if (Input.GetKeyDown(KeyCode.Space)) //jump
        {
            rb.MovePosition(new Vector2(transform.position.x, transform.position.y) + Speed * Time.deltaTime * new Vector2(0,1).normalized);
        } 

but result was same as first code.

I make fourth code with not using rigidbody:

public class player : MonoBehaviour
{
    Vector2 Moveing;
    public float Speed = 2f;
    private Rigidbody2D rb;
    private bool IsGround;
    private int CurrentJumpFrame=0;

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

    // Update is called once per frame
    void Update()
    {
        if (Input.GetKeyDown(KeyCode.LeftArrow))
        {
            transform.eulerAngles = new Vector2(0, 180);
        }
        else if (Input.GetKeyUp(KeyCode.LeftArrow))
        {
            transform.eulerAngles = new Vector2(0, 0);
        }
...
        else if (!Input.GetKey(KeyCode.LeftArrow) && !Input.GetKey(KeyCode.RightArrow) & IsHurt == true && attacking == false)
        {
            am.Play("hurt" + lv);
        }
        else if (Input.GetKey(KeyCode.RightArrow) && !Input.GetKey(KeyCode.UpArrow) && IsHurt == false && attacking == false)
        {
            Moveing = new Vector2(1, 0);
            am.Play("walk" + lv);
        }
...
        else
        {
            Moveing = new Vector2(0, 0);
            am.Play("idle" + lv);
        }
        if (Input.GetKeyDown(KeyCode.Space)&&IsGround==true) //jump
        {
            Moveing += new Vector2(0, Speed);
            CurrentJumpFrame = 1;
            transform.position = new Vector2(transform.position.x, transform.position.y + Speed / 18 / 60);
        }
        if (CurrentJumpFrame>0&&CurrentJumpFrame<=60&&IsGround==false)
        {
            transform.position = new Vector2(transform.position.x, transform.position.y + Speed / 18 / 60);
            CurrentJumpFrame++;
        }
        else if (IsGround == true)
        {
            CurrentJumpFrame = 0;
        }

        rb.MovePosition(new Vector2(transform.position.x, transform.position.y) + Speed * Time.deltaTime * Moveing.normalized);
    }

    void OnCollisionEnter2D(Collision2D collision)
    {
        if (collision.collider.CompareTag("Grid"))
        {
            IsGround= true;
        }
    }
    void OnCollisionExit2D(Collision2D collision)
    {
        if (collision.gameObject.CompareTag("Grid"))
        {
            IsGround= false;
        }
    }
}

But it was same result again as first code!

I fix first and second code with changing Moving.Normalized to Moving. and result was same and have another problem. Player stuck at tilemap collider after moving 3~4 tile. I make Tilemap collider Merge but It wasn't fixed.


Solution

  • rb.AddForce(Vector2.up * Speed,ForceMode2D.Impulse);
    

    On the jump if statement.