Files
2026-01-21 10:56:26 -07:00

672 lines
20 KiB
C#

using System;
using System.Collections.Generic;
using UnityEngine;
public class playerController : MonoBehaviour
{
#region Imported Variables
private GroundCheck groundCheck;
private DoubleCheck doubleCheck;
private WallCheck wallCheck;
private Rigidbody2D body;
private Collider2D hBox;
public GameObject attackHitbox;
public GameObject gun;
#endregion
#region Keybinds / Controls
private KeyCode hop, up, down, left, right, dash, lightAttack, heavyAttack, ultimateAttack, forward;
private String currentDirection;
private int directionsHeld;
private bool RIGHT, LEFT, UP, DOWN, moveLock;
#endregion
#region Timers
private float coyoteTimeAmount = .1f, airjumpTurnaroundWindow = .1f, jumpBufferAmount = .2f, clickBufferAmount = .1f, wallStallAmount = .15f, dashLength = .15f, waveDashWindow = .18f, scrollSpeed = .15f;
private float CoyoteTimer, jumpBufferTimer, clickBufferTimer, airjumpTurnTimer, wallStallTimer, dashCooldownTimer, dashLeftTimer, dashRightTimer, waveDashTimer, hitboxTimer, scrollTimer, reloadTimer;
private float tempMaxSpeedTimer, dashCooldownAmount = 1, moveLockTimer, sideDashTimer, pauseGravTimer, dashEndTimer;
#endregion
#region Player Booleans
private bool allowedToWalk = true, allowedToJump = true, allowedToWallSlide = true, allowedToDash = true, speedClampingActive = true, canScroll = true;
public bool isGrounded, isWallSlide, canJumpAgain, isFacingRight = true, canDash, dashingLeft, dashingRight, alreadyAirDashed, waveDashing = false;
[SerializeField] private bool canDie = true;
#endregion
#region Player Floats
private float defaultMaxSpeed = 10f, defaultMoveSpeed = 10f, defaultJumpPower = 30f, defaultDashPower = 60f, defaultTurnResponsiveness = 4f, defaultExtraJumps = 1f; //Permanent Upgrades Will Affect These
private float tempMaxSpeed = 10f, tempMoveSpeed = 10f, tempJumpPower = 30f, tempDashPower = 60f, tempTurnResponsiveness = 8f, tempExtraJumps; //Temporary Upgrades/Debuffs Will Affect These
private float velocityDirection = 1, turnaround;
[SerializeField] private float playerHealth;
#endregion
#region Characters/Inventory Management
private List<String> playerInventory;
public int equippedIndex = 2;
public String equippedItem, SelectedPlayer;
#endregion
void Start()
{
body = GetComponent<Rigidbody2D>();
hBox = transform.GetComponent<BoxCollider2D>();
body.gravityScale = 6;
#region Character Movesets
switch (SelectedPlayer)
{
case "Cade":
playerInventory = new List<String> { "StaffSwing", "Fireball", "DragonBreath" };
break;
case "Sloane":
playerInventory = new List<String> { "Knife", "Grenade", "Rifle", "Shotgun" };
break;
case "Leo":
playerInventory = new List<String> { "ChargeFist", "JunkToss", "Grabble" };
break;
case "Gamma":
playerInventory = new List<String> { "ArmStab", "BlubberBomb", "BodyThrow" };
break;
default:
playerInventory = new List<String> { "Gun", "Melee"};
break;
}
equippedItem = playerInventory[equippedIndex];
#endregion
#region Character Controls
switch (SelectedPlayer)
{
case "Cade":
case "Sloane":
default:
hop = KeyCode.W;
up = KeyCode.W;
down = KeyCode.S;
left = KeyCode.A;
right = KeyCode.D;
dash = KeyCode.LeftShift;
break;
case "Leo":
case "Gamma":
hop = KeyCode.Space;
up = KeyCode.UpArrow;
down = KeyCode.DownArrow;
left = KeyCode.LeftArrow;
right = KeyCode.RightArrow;
dash = KeyCode.LeftShift;
lightAttack = KeyCode.X;
heavyAttack = KeyCode.C;
break;
}
forward = right;
#endregion
}
void Update()
{
StateCheck();
if (playerHealth > 0) {
PhysicsTimersHandler();
Movement();
ControllerTimersHandler();
CheckFaceDirection();
RangedCombat();
}
}
#region BEHIND-THE-SCENES STUFF
void StateCheck()
{
#region Ground Check
groundCheck = GetComponentInChildren<GroundCheck>();
doubleCheck = GetComponentInChildren<DoubleCheck>();
if (groundCheck.isGrounded && !doubleCheck.isInsideGround) isGrounded = true;
else isGrounded = false;
#endregion
#region Wall Check
wallCheck = GetComponentInChildren<WallCheck>();
if ((wallCheck.touchingWall) && !isGrounded && Input.GetKey(forward)) isWallSlide = true;
else isWallSlide = false;
#endregion
#region Reload Air Jumps
if (isGrounded && (tempExtraJumps < defaultExtraJumps))
tempExtraJumps = defaultExtraJumps;
if (tempExtraJumps > 0) canJumpAgain = true;
else canJumpAgain = false;
#endregion
#region Reload Dash
if (isGrounded) alreadyAirDashed = false;
#endregion
#region Health Update
playerHealth = GameObject.Find("GameData").GetComponent<GameData>().CurrentHealth;
if (playerHealth <= 0) body.linearVelocityX = 0;
#endregion
#region Most Recent Direction Input
if (moveLock == false) LEFT = Input.GetKey(left);
if (moveLock == false) RIGHT = Input.GetKey(right);
UP = Input.GetKey(up);
DOWN = Input.GetKey(down);
directionsHeld = 0;
if (LEFT) directionsHeld++; if (RIGHT) directionsHeld++; if (UP) directionsHeld++; if (DOWN) directionsHeld++;
if (UP) currentDirection = "up";
else if (DOWN) currentDirection = "down";
else if (LEFT || RIGHT)
{
if (LEFT && left != forward || RIGHT && right != forward) currentDirection = "backward";
if (LEFT && left == forward || RIGHT && right == forward) currentDirection = "forward";
}
else currentDirection = "neutral";
#endregion
#region Gravity Updates
if (pauseGravTimer <= 0)
{
if (DOWN && !UP) body.gravityScale = 8;
else body.gravityScale = 6;
}
#endregion
}
void CheckFaceDirection()
{
if ((body.linearVelocity.x > 0 && !isFacingRight || body.linearVelocity.x < 0 && isFacingRight) && isGrounded) Flip();
}
public void Flip()
{
if (forward == left) forward = right;
else if (forward == right) forward = left;
isFacingRight = !isFacingRight;
velocityDirection *= -1;
#region Change Player Orientation
Vector3 currentScale = transform.localScale;
currentScale.x *= -1;
transform.localScale = currentScale;
Vector3 gunScale = gun.transform.localScale;
gunScale.x *= -1;
gunScale.y *= -1;
gun.transform.localScale = gunScale;
#endregion
}
void PhysicsTimersHandler()
{
#region Coyote Time
if (isGrounded && !(body.linearVelocity.y > 0)) CoyoteTimer = coyoteTimeAmount;
if (CoyoteTimer > 0) CoyoteTimer -= Time.deltaTime;
#endregion
#region Jump Buffering
if (Input.GetKeyDown(hop)) jumpBufferTimer = jumpBufferAmount;
if (jumpBufferTimer > 0) jumpBufferTimer -= Time.deltaTime;
#endregion
#region Window To Change Directions After Air Jump
if (airjumpTurnTimer > 0) airjumpTurnTimer -= Time.deltaTime;
#endregion
#region Wall Stall
if (!isWallSlide || body.linearVelocity.y >= 0) wallStallTimer = wallStallAmount;
if (wallStallTimer > 0) wallStallTimer -= Time.deltaTime;
#endregion
#region WaveDashing
if (isGrounded && waveDashing) waveDashTimer -= Time.deltaTime;
if (waveDashTimer > 0) waveDashing = true;
else waveDashing = false;
#endregion
#region Resetting Speed Clamping
if (tempMaxSpeedTimer <= 0)
{
tempMaxSpeed = defaultMaxSpeed;
body.linearVelocity = new Vector2(Mathf.Clamp(body.linearVelocity.x, -tempMaxSpeed, tempMaxSpeed), Mathf.Clamp(body.linearVelocity.y, -tempJumpPower, tempJumpPower));
}
else
{
tempMaxSpeedTimer -= Time.deltaTime;
body.linearVelocity = new Vector2(Mathf.Clamp(body.linearVelocity.x, -tempMaxSpeed, tempMaxSpeed), Mathf.Clamp(body.linearVelocity.y, -tempMaxSpeed, tempMaxSpeed));
}
#endregion
#region Gravity
if (pauseGravTimer > 0) pauseGravTimer -= Time.deltaTime;
#endregion
#region Physics After A Dash Ends
if (dashEndTimer > 0) dashEndTimer -= Time.deltaTime;
if (dashEndTimer < 0)
{
dashEndTimer = 0;
if (body.linearVelocity.y > 0) body.linearVelocity = new Vector2(body.linearVelocity.x, 10);
}
#endregion
}
void ControllerTimersHandler()
{
#region Click Buffer & Reload Timers
if (Input.GetMouseButtonDown(0)) clickBufferTimer = clickBufferAmount;
if (clickBufferTimer > 0) clickBufferTimer -= Time.deltaTime;
if (reloadTimer > 0) reloadTimer -= Time.deltaTime;
#endregion
#region Dash Cooldown
if (dashCooldownTimer > 0) dashCooldownTimer -= Time.deltaTime;
if (dashCooldownTimer <= 0) canDash = true;
else canDash = false;
#endregion
#region Dash Input Window
/*
if (dashLeftTimer > 0 && Input.GetKeyDown(left) && canDash && !alreadyAirDashed) dashingLeft = true;
if (Input.GetKeyDown(left))
{
dashLeftTimer = dashWindowAmount;
dashRightTimer = 0;
}
if (dashRightTimer > 0 && Input.GetKeyDown(right) && canDash && !alreadyAirDashed) dashingRight = true;
if (Input.GetKeyDown(right))
{
dashRightTimer = dashWindowAmount;
dashLeftTimer = 0;
}
if (dashLeftTimer > 0) dashLeftTimer -= Time.deltaTime;
if (dashRightTimer > 0) dashRightTimer -= Time.deltaTime;
*/
#endregion
#region Attack Window
if (hitboxTimer >= 0) hitboxTimer -= Time.deltaTime;
if (hitboxTimer < 0) attackHitbox.SetActive(false);
#endregion
#region Inventory Scrolling
if (scrollTimer > 0) scrollTimer -= Time.deltaTime;
if (scrollTimer > 0) canScroll = false;
else canScroll = true;
#endregion
#region Left/Right Locks
if (moveLockTimer > 0)
{
moveLockTimer -= Time.deltaTime;
moveLock = true;
}
else moveLock = false;
#endregion
}
#endregion
#region PLAYER CONTROLLED ASPECTS
void Movement()
{
if (allowedToWalk)
{
#region Walking
if (!(LEFT && RIGHT))
{
#region Control Responsiveness
if (!isGrounded) turnaround = tempTurnResponsiveness * .75f;
else turnaround = tempTurnResponsiveness;
if (airjumpTurnTimer > 0) turnaround = tempTurnResponsiveness * 5f;
#endregion
#region Moving Left
if (LEFT) body.linearVelocity += new Vector2(-tempMoveSpeed * turnaround * Time.deltaTime, 0);
#endregion
#region Moving Right
if (RIGHT) body.linearVelocity += new Vector2(tempMoveSpeed * turnaround * Time.deltaTime, 0);
#endregion
}
#endregion
#region Friction
if (!(Input.GetKey(left) || Input.GetKey(right)) || (Input.GetKey(left) && Input.GetKey(right)))
{
float fric;
if (Math.Abs(body.linearVelocity.x) > 5f) { fric = .97f; }
else { fric = .92f; }
body.linearVelocity = new Vector2(body.linearVelocity.x * fric, body.linearVelocity.y);
if (Math.Abs(body.linearVelocity.x) < .4f) body.linearVelocity = new Vector2(0, body.linearVelocity.y);
}
#endregion
}
if (allowedToJump)
{
#region Normal Jumps
if (CoyoteTimer > 0 && jumpBufferTimer > 0)
{
body.linearVelocity = new Vector2(body.linearVelocity.x, tempJumpPower);
jumpBufferTimer = 0;
CoyoteTimer = 0;
if(waveDashTimer > 0) waveDashTimer = waveDashWindow;
Debug.Log("normalJump");
}
#endregion
#region Air Jumps
else if (canJumpAgain && Input.GetKeyDown(hop) && !isWallSlide)
{
Debug.Log("doubleJump");
jumpBufferTimer = 0;
Debug.Log("CHECKDOUBLE");
body.linearVelocity = new Vector2(body.linearVelocity.x, tempJumpPower * .8f);
tempExtraJumps--;
airjumpTurnTimer = airjumpTurnaroundWindow;
}
#endregion
#region Releasing Jump
if (!Input.GetKey(hop) && body.linearVelocity.y > 0)
{
body.linearVelocity = new Vector2(body.linearVelocity.x, body.linearVelocity.y * .97f);
}
#endregion
}
if (allowedToWallSlide)
{
#region Wall Sliding Friction
if (isWallSlide && wallStallTimer > 0 && body.linearVelocity.y < 0)
{
body.linearVelocity = new Vector2(body.linearVelocity.x, body.linearVelocity.y * .95f);
body.gravityScale = 0;
}
else if (isWallSlide && body.linearVelocity.y < 0) body.gravityScale = 2;
#endregion
#region Wall Jumps
if (isWallSlide && jumpBufferTimer > 0)
{
moveLockTimer = 0.15f;
body.linearVelocity = new Vector2(tempMoveSpeed * -velocityDirection, 20f);
if (velocityDirection < 0) { RIGHT = true; LEFT = false; }
else if (velocityDirection > 0) { LEFT = true; RIGHT = false; }
jumpBufferTimer = 0;
}
#endregion
}
if (allowedToDash)
{
#region Dashing
if (Input.GetKeyDown(dash) && canDash && !alreadyAirDashed)
{
tempMaxSpeed = tempDashPower;
tempMaxSpeedTimer = dashLength;
moveLockTimer = dashLength;
pauseGravTimer = dashLength;
body.linearVelocity = new Vector2(body.linearVelocity.x, 0);
body.gravityScale = 0;
dashCooldownTimer = dashCooldownAmount;
alreadyAirDashed = true;
if ((LEFT && DOWN || LEFT && UP || RIGHT && DOWN || RIGHT && UP) && directionsHeld == 2) tempDashPower = 0.70710678f * tempDashPower;
#region Neutral Dashing
if (!LEFT && !RIGHT && directionsHeld % 2 == 0)
{
if (forward == right)
{
RIGHT = true;
LEFT = false;
}
else if (forward == left)
{
LEFT = true;
RIGHT = false;
}
}
#endregion
#region Directional Dashes
if (LEFT && !RIGHT) body.linearVelocity = new Vector2(-tempDashPower, body.linearVelocity.y);
if (!LEFT && RIGHT) body.linearVelocity = new Vector2(tempDashPower, body.linearVelocity.y);
if (UP && !DOWN) { body.linearVelocity = new Vector2(body.linearVelocity.x, 2f * tempDashPower); dashEndTimer = .15f; }
if (!UP && DOWN) body.linearVelocity = new Vector2(body.linearVelocity.x, -2f * tempDashPower);
#endregion
if ((DOWN && RIGHT || DOWN && LEFT) && directionsHeld == 2) waveDashTimer = waveDashWindow;
tempDashPower = defaultDashPower;
}
#endregion
}
}
public void RangedCombat()
{
#region Weapon Wheel
float scrollInput = Input.GetAxis("Mouse ScrollWheel");
if (scrollInput != 0 && canScroll)
{
int scrollDirection = Math.Sign(scrollInput);
int nextIndex = equippedIndex + scrollDirection;
scrollTimer = scrollSpeed;
equippedIndex = (nextIndex % playerInventory.Count + playerInventory.Count) % playerInventory.Count;
equippedItem = playerInventory[equippedIndex];
reloadTimer = 0;
}
#endregion
#region Shooting
if (clickBufferTimer > 0 && reloadTimer <= 0)
{
switch (equippedItem)
{
#region Cade's Weapons
case "StaffSwing":
break;
case "Fireball":
break;
case "DragonBreath":
break;
#endregion
#region Sloane's Weapons
case "Knife":
break;
case "Grenade":
break;
case "Rifle":
break;
case "Shotgun":
break;
#endregion
#region Leo's Weapons
case "ChargeFist":
break;
case "JunkToss":
break;
case "Grabble":
break;
#endregion
#region Gamma's Weapons
case "ArmStab":
break;
case "BlubberBomb":
break;
case "BodyThrow":
break;
#endregion
#region Test Weapons
case "Melee":
attackHitbox.SetActive(true);
hitboxTimer = .2f;
reloadTimer = .3f;
Debug.Log("swing");
break;
case "Gun":
GetComponent<ShootScript>().Shoot("Bullet", 2000f, 15f, 25f, .25f, 3, .05f);
reloadTimer = .5f;
break;
#endregion
}
}
#endregion
}
public void DirectionalCombat()
{
if (Input.GetKeyDown(lightAttack) && reloadTimer <= 0)
{
switch (currentDirection) {
case ("up"):
break;
case ("down"):
break;
case ("backward"):
break;
case ("forward"):
break;
case ("right"):
break;
}
}
if (Input.GetKeyDown(heavyAttack) && reloadTimer <= 0)
{
switch (currentDirection)
{
case ("up"):
break;
case ("down"):
break;
case ("left"):
break;
case ("right"):
break;
}
}
}
#endregion
}