Untitled
unknown
plain_text
2 years ago
12 kB
17
Indexable
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Serialization;
public class Player : MonoBehaviour
{
public static Player Instance { get; private set; }
public event EventHandler OnStateChanged;
public State currentState;
[SerializeField] private float angularDrag;
[SerializeField] private State startState;
[SerializeField] private Transform grenadeSpawnPosition;
[SerializeField] private float throwStrength;
[SerializeField] private bool isActive = true;
[Header("Movement")]
[SerializeField] private float moveSpeed;
[SerializeField] private float accelerationForce;
[SerializeField] private float deccelerationForce;
[SerializeField] private float velPower;
[SerializeField] private float friction;
[Header("Jump")]
[SerializeField] private float jumpForce;
[SerializeField] private float doubleJumpForce;
[SerializeField] private float jumpCutMultiplier;
[SerializeField] private float jumpCutMultiplierDoubleJump;
[SerializeField] private float jumpCoyoteTime;
[SerializeField] private float jumpBufferTime;
[SerializeField] private float gravityScale;
[SerializeField] private float fallGravityMultiplier;
[SerializeField] private float additionalAirTimePeakStrength;
[Header("Checks")]
[SerializeField] private Transform groundCheckPoint;
[SerializeField] private Vector2 groundCheckSize;
[SerializeField] private LayerMask groundLayer;
[Header("GrenadeForce")]
[SerializeField] private float testForce;
[SerializeField] private Vector2 testVector;
[SerializeField] private AnimationCurve yCurve;
[SerializeField] private AnimationCurve xCurve;
[SerializeField] private AnimationCurve accelerationCurve;
[SerializeField] private float duration;
private Rigidbody2D playerRigidbody;
private bool isJumping;
private bool isFiringGrenade;
private bool isGrounded;
private bool isDoingSomethingElseThanIdle;
private State lastState;
private Vector2 moveDir;
private float moveInput;
private Vector3 mousePosition;
public bool justShoot;
private float scrollWheelInput;
private CollectableSO lastFiredCollectableSO;
private bool stillJumping;
private float lastGroundedTime;
private float lastJumpTime;
private bool jumpInputReleased = false;
private bool reducingJumpForce = false;
public CollectableSO collectableSoLeftMouse;
public CollectableSO collectableSoRightMouse;
#region PrivateVariables
private bool canDoubleJump = false;
private bool isDoubleJumping = false;
#endregion
public enum State
{
Start,
Idle,
Jump,
Fall,
ThrowingBomb,
GotHitMelee,
GotHitPink
}
private void Awake()
{
Instance = this;
currentState = startState;
lastState = State.Start;
isDoingSomethingElseThanIdle = false;
}
private void Start()
{
playerRigidbody = GetComponent<Rigidbody2D>();
playerRigidbody.angularDrag = angularDrag;
if (!isActive)
{
this.gameObject.SetActive(false);
}
}
private void Update()
{
mousePosition = Input.mousePosition;
moveInput = Input.GetAxisRaw("Horizontal");
OrientateCharacterLook();
if (Input.GetKeyDown(KeyCode.Q))
{
TestPhysics();
}
if (Input.GetKeyDown(KeyCode.W))
{
#region Jump
jumpInputReleased = false;
lastJumpTime = jumpBufferTime;
#endregion
}
if (Input.GetKeyUp(KeyCode.W))
{
OnJumpUp();
}
if (Input.GetKeyDown(KeyCode.Mouse0))
{
isFiringGrenade = true;
FiringGrenade(true);
}
if (Input.GetKeyDown(KeyCode.Mouse1) && !isFiringGrenade )
{
isFiringGrenade = true;
FiringGrenade(false);
}
if (currentState != lastState)
{
lastState = currentState;
OnStateChanged?.Invoke(this, EventArgs.Empty);
}
scrollWheelInput = Input.GetAxis("Mouse ScrollWheel");
if (scrollWheelInput != 0)
{
ChangeLeftAndRightAttachedCollectableSO();
PlayerInventory.Instance.UpdateInventory();
}
#region Timer
lastGroundedTime -= Time.deltaTime;
lastJumpTime -= Time.deltaTime;
#endregion
Debug.DrawRay(transform.position, -transform.up*5,Color.green);
}
private void FixedUpdate()
{
#region Run
float targetSpeed = moveInput * moveSpeed;
float speedDif = targetSpeed - playerRigidbody.velocity.x;
float accelRate = (Mathf.Abs(targetSpeed) > 0.01f) ? accelerationForce : deccelerationForce;
float movement = Mathf.Pow(Mathf.Abs(speedDif) * accelRate, velPower) * Mathf.Sign(speedDif);
playerRigidbody.AddForce(movement * Vector2.right);
#endregion
#region Friction
if (moveInput == 0)
{
float amount = Mathf.Min(Mathf.Abs(playerRigidbody.velocity.x), Mathf.Abs(friction));
amount *= Mathf.Sign(playerRigidbody.velocity.x);
playerRigidbody.AddForce(Vector2.right * -amount, ForceMode2D.Impulse);
}
#endregion
#region GroundCheck
if (Physics2D.OverlapBox(groundCheckPoint.position, groundCheckSize, 0, groundLayer))
{
isGrounded = true;
isJumping = false;
lastGroundedTime = jumpCoyoteTime;
currentState = State.Idle;
canDoubleJump = false;
isDoubleJumping = false;
}
/*
else
{
canDoubleJump = true;
}
*/
#endregion
#region Jump
if (lastGroundedTime > 0 && lastJumpTime > 0 && !isJumping && !canDoubleJump)
{
Debug.Log("JUMP");
Jump();
currentState = State.Jump;
canDoubleJump = true;
}
else if (canDoubleJump && !isDoubleJumping && lastJumpTime > 0)
{
Debug.Log("DoubleJump");
isDoubleJumping = true;
DoubleJump();
}
#endregion
#region Jump Gravity
if (isJumping && playerRigidbody.velocity.y < 0.1f && playerRigidbody.velocity.y > -0.1f)
{
playerRigidbody.AddForce(Vector2.up * additionalAirTimePeakStrength);
}
if (playerRigidbody.velocity.y < 0)
{
playerRigidbody.gravityScale = gravityScale * fallGravityMultiplier;
if(!isGrounded) currentState = State.Fall;
}
else
{
playerRigidbody.gravityScale = gravityScale;
}
#endregion
}
private void Jump()
{
playerRigidbody.AddForce(Vector2.up * jumpForce, ForceMode2D.Impulse);
lastGroundedTime = 0;
lastJumpTime = 0;
isJumping = true;
jumpInputReleased = false;
}
private void DoubleJump()
{
playerRigidbody.velocity = new Vector2(playerRigidbody.velocity.x, doubleJumpForce);
//playerRigidbody.AddForce(Vector2.up * doubleJumpForce, ForceMode2D.Impulse);
lastGroundedTime = 0;
lastJumpTime = 0;
jumpInputReleased = false;
}
private void OnJumpUp()
{
if (playerRigidbody.velocity.y > 0 && (isJumping && !isDoubleJumping))
{
playerRigidbody.AddForce(Vector2.down * playerRigidbody.velocity.y * (1 - jumpCutMultiplier));
}
else if (playerRigidbody.velocity.y > 0 && (isDoubleJumping))
{
playerRigidbody.AddForce(Vector2.down * playerRigidbody.velocity.y * (1 - jumpCutMultiplierDoubleJump));
}
jumpInputReleased = true;
lastJumpTime = 0;
}
private void FiringGrenade(bool leftMouse)
{
Debug.Log("---------------------------------------------------");
Vector2 grenadeDir = CalculateGrenadeDirNormalized();
lastFiredCollectableSO = leftMouse ? collectableSoLeftMouse : collectableSoRightMouse;
Transform grenadePrefab = lastFiredCollectableSO?.prefab;
if (grenadePrefab == null)
{
Debug.Log("Mouse doesnt contain any item");
isFiringGrenade = false;
return;
}
Debug.Log(lastFiredCollectableSO.name + " has " + PlayerInventory.Instance.playerInventoryDictionary[lastFiredCollectableSO] + " item");
PlayerInventory.Instance.playerInventoryDictionary[lastFiredCollectableSO] -= 1;
Debug.Log(lastFiredCollectableSO.name + " now has " + PlayerInventory.Instance.playerInventoryDictionary[lastFiredCollectableSO] + " item");
if (PlayerInventory.Instance.playerInventoryDictionary[lastFiredCollectableSO] == 0)
{
if (leftMouse)
{
collectableSoLeftMouse = null;
}
else
{
collectableSoRightMouse = null;
}
}
Transform grenade = Instantiate(grenadePrefab, grenadeSpawnPosition.position, Quaternion.identity);
Rigidbody2D rbGrenade = grenade.GetComponent<Rigidbody2D>();
rbGrenade.AddForce(grenadeDir * throwStrength * lastFiredCollectableSO.recoilForce,ForceMode2D.Impulse);
PlayerInventory.Instance.UpdateInventory(lastFiredCollectableSO);
Debug.Log("trigger");
Debug.Log("---------------------------------------------------");
}
private void OrientateCharacterLook()
{
if (moveInput == 0) return;
Vector3 currentScale = transform.localScale;
currentScale.x = moveInput * 3.5f;
transform.localScale = currentScale;
}
private Vector2 CalculateGrenadeDirNormalized()
{
Vector2 grenadeDir;
Vector3 worldPosition = Camera.main.ScreenToWorldPoint(mousePosition);
worldPosition.z = 0;
if (mousePosition != Vector3.zero)
{
grenadeDir = worldPosition - transform.position;
}
else
{
grenadeDir = (transform.up + transform.right) * throwStrength;
}
grenadeDir = grenadeDir.normalized;
if (grenadeDir.y > 0.5f) grenadeDir.y += 1f;
if (grenadeDir.x > 0.5) grenadeDir.x += 0.2f;
if (Mathf.Sign(transform.localScale.x) != Mathf.Sign(grenadeDir.x))
{
//return transform.right * Mathf.Sign(transform.localScale.x);
//or rotate
Vector3 currentScale = transform.localScale;
currentScale.x = -currentScale.x;
transform.localScale = currentScale;
}
return grenadeDir;
}
private void ChangeLeftAndRightAttachedCollectableSO()
{
CollectableSO temp = collectableSoLeftMouse;
collectableSoLeftMouse = collectableSoRightMouse;
collectableSoRightMouse = temp;
}
private void TestPhysics()
{
StartCoroutine(ApplyExplosionForce(playerRigidbody, testVector * testForce));
}
private IEnumerator ApplyExplosionForce(Rigidbody2D rb, Vector2 force)
{
float elapsedTime = 0f;
// Adjust the duration to control the acceleration speed
while (elapsedTime < duration)
{
float normalizedTime = elapsedTime / duration;
force = new Vector2(xCurve.Evaluate(normalizedTime) * force.x, yCurve.Evaluate(normalizedTime) * force.y);
float accelerationFactor = accelerationCurve.Evaluate(normalizedTime);
rb.AddForce(force * accelerationFactor, ForceMode2D.Force);
elapsedTime += Time.deltaTime;
yield return null;
}
}
}
Editor is loading...