Created
February 21, 2021 19:16
-
-
Save ashour/8c41811fccd33a56a3f26a8e0e402d6e to your computer and use it in GitHub Desktop.
Unity MonoBehaviour for 2D Platform Player Movement
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using UnityEngine; | |
[RequireComponent(typeof(Rigidbody2D))] | |
public class PlayerMovement : MonoBehaviour | |
{ | |
public static Action<Vector2, bool> OnMovementCalculated; | |
[SerializeField] private float _speed = 7; | |
[SerializeField] private float _jumpForce = 1000; | |
[Header("Ground Check")] | |
[SerializeField] private LayerMask _groundLayers; | |
[SerializeField] private Transform _groundCheck; | |
[SerializeField] private float _groundCheckRadius = 0.26f; | |
private readonly Collider2D[] _groundCheckResults = new Collider2D[1]; | |
private Vector3 _startingScale; | |
private Rigidbody2D _body; | |
private bool _isJumping; | |
public bool CanMove { get; set; } = true; | |
private void Awake() | |
{ | |
_body = GetComponent<Rigidbody2D>(); | |
if (_body.bodyType != RigidbodyType2D.Dynamic) | |
{ | |
Debug.LogWarning("Player movement is designed to " + | |
"work with a Dynamic Rigidbody2D."); | |
} | |
if (!_groundCheck) | |
{ | |
Debug.LogError("Please provide a ground check " + | |
"transform."); | |
} | |
_startingScale = transform.localScale; | |
} | |
private void OnDrawGizmosSelected() => | |
Gizmos.DrawWireSphere(_groundCheck.position, _groundCheckRadius); | |
public void MoveFromFixedUpdate(Vector2 input) | |
{ | |
var isOnGround = OnGround(); | |
if (CanMove) | |
{ | |
Move(input, isOnGround); | |
Orient(); | |
} | |
else { Stop(); } | |
OnMovementCalculated?.Invoke(_body.velocity, isOnGround); | |
} | |
private bool OnGround() | |
{ | |
var resultCount = Physics2D.OverlapCircleNonAlloc( | |
_groundCheck.position, | |
_groundCheckRadius, | |
_groundCheckResults, | |
_groundLayers); | |
return resultCount > 0; | |
} | |
private void Move(Vector2 input, bool isOnGround) | |
{ | |
if (isOnGround && input.y > 0 && !_isJumping) | |
{ | |
_isJumping = true; | |
_body.AddForce(new Vector2(0, _jumpForce)); | |
} | |
else if (isOnGround && _isJumping) | |
{ | |
_isJumping = false; | |
} | |
_body.velocity = new Vector2( | |
input.x * _speed, _body.velocity.y); | |
} | |
private void Orient() | |
{ | |
if (_body.velocity.x > 0) | |
{ | |
transform.localScale = _startingScale; | |
} | |
else if (_body.velocity.x < 0) | |
{ | |
transform.localScale = new Vector3( | |
_startingScale.x * -1, | |
_startingScale.y, | |
_startingScale.z); | |
} | |
} | |
private void Stop() => | |
_body.velocity = new Vector2(0, _body.velocity.y); | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment