OldBlueWater/BlueWater/Assets/02.Scripts/Character/CombatPlayer2D/CombatMovement.cs

145 lines
4.4 KiB
C#

using System.Collections;
using Sirenix.OdinInspector;
using UnityEngine;
// ReSharper disable once CheckNamespace
namespace BlueWaterProject
{
public class CombatMovement : MonoBehaviour
{
[SerializeField] private Rigidbody rb;
[SerializeField] private Transform visualLook;
[HideInInspector] public CombatAnimator combatAnimator;
[Range(1f, 10f), Tooltip("이동 속도")]
[SerializeField] private float moveSpeed = 7f;
// Dash
[Range(1f, 50f), Tooltip("대쉬 속도")]
[SerializeField] private float dashSpeed = 20f;
[Range(0.1f, 1f), Tooltip("대쉬 시간")]
[SerializeField] private float dashTime = 0.2f;
[Range(0f, 5f), Tooltip("대쉬 쿨타임")]
[SerializeField] private float dashCooldown = 0.5f;
// Ground
[Range(0.1f, 10.0f), Tooltip("지면 감지 거리")]
[SerializeField] private float groundCheckDistance = 2.0f;
[SerializeField] private LayerMask groundLayer;
private Animator Animator => combatAnimator.animator;
private Vector3 currentMoveDirection;
private Vector3 previousMoveDirection = Vector3.back;
private float finalSpeed;
private bool isMoving;
private bool enableDash = true;
private bool isDashing;
private void Update()
{
MoveAnimation();
FlipVisualLook();
}
private void FixedUpdate()
{
//CheckGround();
if (isDashing) return;
var finalVelocity = rb.position + currentMoveDirection * (moveSpeed * Time.fixedDeltaTime);
rb.MovePosition(finalVelocity);
}
[Button("셋팅 초기화")]
private void InitSetting()
{
rb = GetComponent<Rigidbody>();
visualLook = GetComponentInChildren<Transform>();
}
public void InputMovementValue(Vector2 movementInput)
{
currentMoveDirection = new Vector3(movementInput.x, 0, movementInput.y).normalized;
if (currentMoveDirection != Vector3.zero)
{
previousMoveDirection = currentMoveDirection;
}
isMoving = currentMoveDirection != Vector3.zero;
}
public void HandleDash()
{
if (!enableDash || isDashing) return;
StartCoroutine(nameof(DashCoroutine));
}
private IEnumerator DashCoroutine()
{
var dashDirection = previousMoveDirection;
isDashing = true;
enableDash = false;
combatAnimator.SetIsDash(true);
var elapsedTime = 0f;
while (!Animator.GetCurrentAnimatorStateInfo(0).IsName("DashState"))
{
elapsedTime += Time.deltaTime;
if (elapsedTime >= 1f)
{
yield break;
}
yield return null;
}
var animationLength = Animator.GetCurrentAnimatorStateInfo(0).length;
Animator.speed = animationLength / dashTime;
while (Animator.GetCurrentAnimatorStateInfo(0).IsName("DashState") &&
Animator.GetCurrentAnimatorStateInfo(0).normalizedTime < 1f)
{
var finalVelocity = rb.position + dashDirection * (dashSpeed * Time.fixedDeltaTime);
rb.MovePosition(finalVelocity);
yield return null;
}
Animator.speed = 1f;
isDashing = false;
combatAnimator.SetIsDash(false);
StartCoroutine(Utils.CoolDown(dashCooldown, () => enableDash = true));
}
private void MoveAnimation()
{
combatAnimator.SetIsMoving(isMoving);
if (isMoving)
{
combatAnimator.SetXDirection(previousMoveDirection.x);
combatAnimator.SetZDirection(previousMoveDirection.z);
}
}
private void FlipVisualLook()
{
var localScale = visualLook.localScale;
localScale.x = previousMoveDirection.x switch
{
> 0.01f => Mathf.Abs(localScale.x),
< -0.01f => -Mathf.Abs(localScale.x),
_ => localScale.x
};
visualLook.localScale = localScale;
}
}
}