Skip to content

Instantly share code, notes, and snippets.

@ashour
Created February 21, 2021 19:16
Show Gist options
  • Save ashour/8c41811fccd33a56a3f26a8e0e402d6e to your computer and use it in GitHub Desktop.
Save ashour/8c41811fccd33a56a3f26a8e0e402d6e to your computer and use it in GitHub Desktop.
Unity MonoBehaviour for 2D Platform Player Movement
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