2025-01-10 16:14:33 -05:00
using System.Collections ;
2025-01-17 20:11:04 -05:00
using TMPro ;
2025-01-10 16:14:33 -05:00
using UnityEngine ;
using UnityEngine.InputSystem ;
2025-01-15 16:55:07 -05:00
using UnityEngine.Tilemaps ;
2025-01-10 16:14:33 -05:00
2025-01-17 19:46:17 -05:00
[RequireComponent(typeof(Rigidbody2D))]
[RequireComponent(typeof(BoxCollider2D))]
[RequireComponent(typeof(PlayerInput))]
[RequireComponent(typeof(AnimationPlayer))]
[RequireComponent(typeof(Punch))]
2025-01-10 16:14:33 -05:00
public class PlayerMovement : MonoBehaviour
{
[Header("Ground Layers")]
public LayerMask ground ;
2025-01-17 20:11:04 -05:00
public TextMeshProUGUI playerText ;
2025-01-10 16:14:33 -05:00
[Header("Movement")]
public float walkSpeed ;
2025-01-13 15:58:50 -05:00
public float walkSpeedFactor = 1f ;
public float maxSpeed = 5f ;
2025-01-17 19:46:17 -05:00
public float slowdownMultiplier = 10f ;
2025-01-10 16:14:33 -05:00
public float virtualAxisX ;
public float virtualButtonJump ;
public float virtualButtonJumpLastFrame ;
public float turnaroundMultiplier = 2 ;
public float walkSmooth ;
public float secondsToFullSpeed ;
public float jumpSpeed ;
public float coyoteTime ;
public float jumpLenience ;
public float timeUnableToBeDeclaredNotJumping = 0.1f ;
public float groundCheckDistance ;
private Rigidbody2D body ;
private BoxCollider2D collide ;
2025-01-14 11:40:09 -05:00
private PlayerInput input ;
2025-01-17 19:46:17 -05:00
private AnimationPlayer animationPlayer ;
private Punch punch ;
2025-01-10 16:14:33 -05:00
private bool jumpInputStillValid = false ;
private float lastTimeJumpPressed ;
private bool canBeDeclaredNotJumping = true ;
private bool jumpPhysics ;
private bool jumping ;
private float lastTimeOnGround ;
private Vector3 positionLastFrame ;
void Start ( )
{
2025-01-15 14:07:17 -05:00
GetComponent < RespawnOnTriggerEnter > ( ) . spawnPoint = transform . position ;
2025-01-10 16:14:33 -05:00
body = GetComponent < Rigidbody2D > ( ) ;
collide = GetComponent < BoxCollider2D > ( ) ;
2025-01-14 11:40:09 -05:00
input = GetComponent < PlayerInput > ( ) ;
2025-01-17 19:46:17 -05:00
animationPlayer = GetComponent < AnimationPlayer > ( ) ;
punch = GetComponent < Punch > ( ) ;
2025-01-17 20:11:04 -05:00
playerText . text = input . playerIndex . ToString ( ) ;
2025-01-10 16:14:33 -05:00
}
private void Update ( )
{
Jump ( ) ;
UpdateVirtualAxis ( ) ;
}
private void FixedUpdate ( )
{
JumpPhysics ( ) ;
HorizontalMovement ( ) ;
Land ( ) ;
}
2025-01-15 16:55:07 -05:00
private void LateUpdate ( )
{
2025-01-17 19:46:17 -05:00
Animate ( ) ;
2025-01-15 16:55:07 -05:00
}
private void Animate ( )
{
if ( ! IsPhysicallyGrounded ( ) )
animationPlayer . SetState ( AnimationPlayer . AnimationState . Jump ) ;
else
{
if ( Mathf . Abs ( body . linearVelocityX ) > = 0.1f )
animationPlayer . SetState ( AnimationPlayer . AnimationState . Run ) ;
else
animationPlayer . SetState ( AnimationPlayer . AnimationState . Idle ) ;
}
2025-01-17 09:40:48 -05:00
if ( body . linearVelocityX < - 0.1f )
2025-01-15 16:55:07 -05:00
animationPlayer . backwards = true ;
2025-01-17 09:40:48 -05:00
else if ( body . linearVelocityX > 0.1f )
2025-01-15 16:55:07 -05:00
animationPlayer . backwards = false ;
}
2025-01-10 16:14:33 -05:00
private void Land ( )
{
if ( body . linearVelocity . y > = 0f ) return ;
if ( IsPhysicallyGrounded ( ) )
{
if ( canBeDeclaredNotJumping )
{
jumping = false ;
}
}
}
private void Jump ( )
{
2025-01-31 12:48:13 -05:00
//if (!punch.cancelable) return;
2025-01-17 19:46:17 -05:00
2025-01-10 16:14:33 -05:00
if ( virtualButtonJumpLastFrame = = 1f )
{
jumpInputStillValid = true ;
lastTimeJumpPressed = Time . time ;
}
bool isBasicallyGrounded = IsBasicallyGrounded ( ) ;
if ( ( virtualButtonJumpLastFrame = = 1f & & isBasicallyGrounded & & jumping = = false ) // Coyote Jump: Must have jump pressed this frame and be grounded in last time frame and not be actually jumping.
| | ( jumpInputStillValid & & Time . time - lastTimeJumpPressed < = jumpLenience & & IsPhysicallyGrounded ( ) ) ) // Buffered Jump: Must have pressed jump in the last time frame and be jumping
{
jumpPhysics = true ;
jumping = true ;
jumpInputStillValid = false ;
StartCoroutine ( NotJumpingDelay ( ) ) ;
}
}
private void JumpPhysics ( )
{
if ( jumpPhysics )
{
if ( body . linearVelocity . y < 0 | | ! IsPhysicallyGrounded ( ) ) body . linearVelocity = new Vector2 ( body . linearVelocity . x , 0 ) ;
body . AddForce ( Vector2 . up * jumpSpeed , ForceMode2D . Impulse ) ;
jumpPhysics = false ;
}
if ( ! IsPhysicallyGrounded ( ) & & ! ( virtualButtonJump = = 1f ) )
body . AddForce ( Vector2 . down * jumpSpeed ) ;
}
private IEnumerator NotJumpingDelay ( )
{
canBeDeclaredNotJumping = false ;
yield return new WaitUntil ( ( ) = > ! IsBasicallyGrounded ( ) ) ;
canBeDeclaredNotJumping = true ;
}
private void HorizontalMovement ( )
{
2025-01-31 12:48:13 -05:00
//if (!punch.cancelable) return;
2025-01-17 19:46:17 -05:00
2025-01-13 15:58:50 -05:00
body . AddForce ( new Vector2 ( virtualAxisX * walkSpeed * walkSpeedFactor , 0 ) , ForceMode2D . Force ) ;
if ( Mathf . Abs ( body . linearVelocityX ) > = maxSpeed )
{
2025-01-17 19:46:17 -05:00
body . AddForce ( new Vector2 ( - Mathf . Sign ( body . linearVelocityX ) * ( Mathf . Abs ( body . linearVelocityX ) - maxSpeed ) * slowdownMultiplier , 0 ) ) ;
2025-01-13 15:58:50 -05:00
}
2025-01-14 11:40:09 -05:00
if ( transform . position = = positionLastFrame & & ( input . actions . FindAction ( "Move" ) . ReadValue < Vector2 > ( ) . x = = 0 ) )
2025-01-10 16:14:33 -05:00
{
virtualAxisX = 0 ;
}
positionLastFrame = transform . position ;
}
private void UpdateVirtualAxis ( )
{
2025-01-14 11:40:09 -05:00
virtualButtonJump = input . actions . FindAction ( "Action" ) . ReadValue < float > ( ) ;
virtualButtonJumpLastFrame = input . actions . FindAction ( "Action" ) . WasPressedThisFrame ( ) ? 1 : 0 ;
2025-01-13 15:58:50 -05:00
2025-01-14 11:40:09 -05:00
virtualAxisX = input . actions . FindAction ( "Move" ) . ReadValue < Vector2 > ( ) . x ;
2025-01-13 15:58:50 -05:00
return ;
2025-01-10 16:14:33 -05:00
}
2025-01-14 11:40:09 -05:00
2025-01-10 16:14:33 -05:00
public bool IsBasicallyGrounded ( )
{
if ( IsPhysicallyGrounded ( ) )
{
lastTimeOnGround = Time . time ;
}
if ( Time . time - lastTimeOnGround < coyoteTime )
{
return true ;
}
return false ;
}
public bool IsPhysicallyGrounded ( )
{
RaycastHit2D leftCheck = Physics2D . Raycast ( GetPointInBoxCollider ( collide , - 1 , - 1 ) , Vector2 . down , groundCheckDistance , ground ) ;
RaycastHit2D rightCheck = Physics2D . Raycast ( GetPointInBoxCollider ( collide , 1 , - 1 ) , Vector2 . down , groundCheckDistance , ground ) ;
RaycastHit2D midCheck = Physics2D . Raycast ( GetPointInBoxCollider ( collide , 0 , - 1 ) , Vector2 . down , groundCheckDistance , ground ) ;
if ( leftCheck | | rightCheck | | midCheck )
{
return true ;
}
return false ;
}
public Vector2 GetPointInBoxCollider ( BoxCollider2D boxCollider2D , float horizontal , float vertical )
{
return new Vector2
(
boxCollider2D . bounds . center . x + ( horizontal * boxCollider2D . bounds . extents . x ) ,
boxCollider2D . bounds . center . y + ( vertical * boxCollider2D . bounds . extents . y )
) ;
}
2025-01-17 19:46:17 -05:00
public void StopVelocity ( )
{
if ( IsPhysicallyGrounded ( ) ) body . linearVelocity = Vector2 . zero ;
}
2025-01-10 16:14:33 -05:00
}