playerMovement

mail@pastecode.io avatar
unknown
csharp
a year ago
4.1 kB
8
Indexable
using UnityEngine;

public class PlayerMovement : MonoBehaviour
{
    [Header("Components")]
    private Rigidbody2D rb;
    private Animator anim;
    private SpriteRenderer spriteRend;

    [Header("Move Paramaeters")]
    [SerializeField] private float maxSpeed = 12f;
    [SerializeField] private float moveAcceleration = 50f;
    [SerializeField] private float linearDrag = 10f;

    private float horizontalInput;
    private bool changingDirection => (rb.velocity.x > 0f && horizontalInput < 0f) || (rb.velocity.x < 0f && horizontalInput > 0f);

    [Header("Jump Variables")]
    [SerializeField] private float jumpForce = 12f;
    [SerializeField] private float fallMultiplier = 8f;
    [SerializeField] private float lowJumpFallMultiplier = 5f;
    [SerializeField] private float airLinearDrag = 2.5f;
    [SerializeField] private int extraJumps = 1;
    private int extraJumpsValue;
    private bool canJump => Input.GetButtonDown("Jump") && (onGround || extraJumpsValue > 0);

    [Header("Layer Masks")]
    [SerializeField] private LayerMask groundLayer;

    [Header("Ground Collision")]
    [SerializeField] private float groundRaycastLength;
    private bool onGround;



    private void Awake()
    {
        rb = GetComponent<Rigidbody2D>();
        anim = GetComponent<Animator>();
        spriteRend = GetComponent<SpriteRenderer>();
    }

    private void Update()
    {
        horizontalInput = GetInput().x;
        if (canJump) Jump();

        anim.SetBool("isGrounded", onGround);
        anim.SetFloat("horizontalInput", Mathf.Abs(horizontalInput));

        if (rb.velocity.y < 0f)
        {
            anim.SetBool("isJumping", false);
            anim.SetBool("isFalling", true);
        }

        FlipSprite();
    }

    private void FixedUpdate()
    {
        CheckCollisions();
        MoveCharacter();
        if(onGround)
        {
            extraJumpsValue = extraJumps;
            ApplyGroundLinearDrag();

            anim.SetBool("isJumping", false);
            anim.SetBool("isFalling", false);
        }
        else
        {
            ApplyAirLinearDrag();
            FallMultipler();
        }
    }

    private Vector2 GetInput()
    {
        return new Vector2(Input.GetAxisRaw("Horizontal"), Input.GetAxisRaw("Vertical"));
    }

    private void MoveCharacter()
    {
        rb.AddForce(new Vector2(horizontalInput, 0) * moveAcceleration);

        if(Mathf.Abs(rb.velocity.x) > maxSpeed)
        {
            rb.velocity = new Vector2(Mathf.Sign(rb.velocity.x) * maxSpeed, rb.velocity.y);
        }
    }

    private void ApplyGroundLinearDrag()
    {
        if (Mathf.Abs(horizontalInput) < 0.4f || changingDirection)
        {
            rb.drag = linearDrag;
        }
        else
        {
            rb.drag = 0f;
        }
    }

    private void ApplyAirLinearDrag()
    {
        rb.drag = airLinearDrag;
    }

    private void FallMultipler()
    {
        if(rb.velocity.y < 0f)
        {
            rb.gravityScale = fallMultiplier;
        }
        else if(rb.velocity.y > 0f && !Input.GetButton("Jump"))
        {
            rb.gravityScale = lowJumpFallMultiplier;
        }
        else
        {
            rb.gravityScale = 1f;
        }
    }

    private void Jump()
    {
        if(!onGround)
        {
            extraJumpsValue--;
        }


        anim.SetBool("isJumping", true);
        anim.SetBool("isFalling", false);

        rb.velocity = new Vector2(rb.velocity.x, 0f);
        rb.AddForce(Vector2.up * jumpForce, ForceMode2D.Impulse);
    }

    private void CheckCollisions()
    {
        onGround = Physics2D.Raycast(transform.position, Vector2.down, groundRaycastLength, groundLayer);
    }

    private void OnDrawGizmos()
    {
        Gizmos.color = Color.magenta;
        Gizmos.DrawLine(transform.position, transform.position + Vector3.down * groundRaycastLength);
    }

    private void FlipSprite()
    {
        if(horizontalInput > 0)
        {
            spriteRend.flipX = false;
        }
        if(horizontalInput < 0)
        {
            spriteRend.flipX = true;
        }
    }
}