using UnityEngine; using Code.Gameplay.Camera; using KinematicCharacterController; namespace Code.Gameplay.Character.Controller.Abilities { public class DashMechanic { private readonly float _dashSpeed; private readonly float _dashDuration; private readonly float _dashCooldown; private float _dashTimer; private float _dashCooldownTimer; private Vector3 _dashDirection; private bool _dashRequested; public bool IsDashing { get; private set; } public DashMechanic(float dashSpeed, float dashDuration, float dashCooldown) { _dashSpeed = dashSpeed; _dashDuration = dashDuration; _dashCooldown = dashCooldown; } public void TickCooldown(float deltaTime) { if (_dashCooldownTimer > 0f) _dashCooldownTimer -= deltaTime; } public void RequestDash(bool dashPressed) { if (dashPressed && !_dashRequested && _dashCooldownTimer <= 0f) _dashRequested = true; } public void TryStartDash(KinematicCharacterMotor motor, CameraMode currentCameraMode, Quaternion firstPersonCameraRotation, Vector3 lookInputVector) { if (!_dashRequested || !motor.GroundingStatus.IsStableOnGround || _dashCooldownTimer > 0f) { _dashRequested = false; return; } IsDashing = true; _dashTimer = _dashDuration; var dir = currentCameraMode == CameraMode.FirstPerson ? firstPersonCameraRotation * Vector3.forward : lookInputVector; _dashDirection = Vector3.ProjectOnPlane(dir, motor.CharacterUp).normalized; if (_dashDirection.sqrMagnitude < 0.01f) _dashDirection = motor.CharacterForward; _dashCooldownTimer = _dashCooldown; _dashRequested = false; } public void HandleDash(ref Vector3 currentVelocity, float deltaTime, KinematicCharacterMotor motor) { _dashTimer -= deltaTime; if (_dashTimer <= 0f || !motor.GroundingStatus.IsStableOnGround) { EndDash(); return; } currentVelocity = _dashDirection * _dashSpeed; currentVelocity += motor.CharacterUp * 1.5f; } public void EndDash() { IsDashing = false; _dashTimer = 0f; } } }