using System.Collections; using Core; using UnityEngine; namespace Minigames.Airplane.Abilities { /// /// Drop Plane Ability: Swipe down to drop straight down. /// Sustained ability - drops for fixed duration/distance. /// Good for precision strikes on targets. /// Configuration loaded from settings at runtime. /// public class DropAbility : BaseAirplaneAbility { #region Configuration private readonly float dropForce; private readonly float dropDistance; private readonly bool zeroHorizontalVelocity; #endregion #region Constructor /// /// Create drop ability with configuration from settings. /// public DropAbility(string name, Sprite icon, float cooldown, float force, float distance, bool zeroHorizontal = true) : base(name, icon, cooldown) { dropForce = force; dropDistance = distance; zeroHorizontalVelocity = zeroHorizontal; } #endregion #region State private float originalXVelocity; private Vector3 dropStartPosition; private Coroutine dropCoroutine; #endregion #region Override Methods public override void Execute() { if (!ValidateAirplane()) return; if (!CanActivate) return; StartActivation(); var rb = currentAirplane.GetComponent(); if (rb != null) { // Store original velocity originalXVelocity = rb.linearVelocity.x; // Zero horizontal velocity if configured if (zeroHorizontalVelocity) { rb.linearVelocity = new Vector2(0f, rb.linearVelocity.y); } // Apply strong downward force rb.AddForce(Vector2.down * dropForce, ForceMode2D.Impulse); // Track drop distance dropStartPosition = currentAirplane.transform.position; // Start monitoring drop distance dropCoroutine = currentAirplane.StartCoroutine(MonitorDropDistance()); } if (showDebugLogs) { Logging.Debug($"[DropAbility] Activated - Force: {dropForce}, Distance: {dropDistance}"); } } public override void Deactivate() { if (!isActive) return; // Stop monitoring if (dropCoroutine != null && currentAirplane != null) { currentAirplane.StopCoroutine(dropCoroutine); dropCoroutine = null; } // Restore horizontal velocity (optional) if (currentAirplane != null) { var rb = currentAirplane.GetComponent(); if (rb != null && zeroHorizontalVelocity) { Vector2 currentVel = rb.linearVelocity; rb.linearVelocity = new Vector2(originalXVelocity * 0.5f, currentVel.y); // Resume at reduced speed } } base.Deactivate(); // Start cooldown StartCooldown(); if (showDebugLogs) { Logging.Debug("[DropAbility] Deactivated, cooldown started"); } } #endregion #region Drop Monitoring private IEnumerator MonitorDropDistance() { while (isActive && currentAirplane != null) { float distanceDropped = Mathf.Abs(dropStartPosition.y - currentAirplane.transform.position.y); if (distanceDropped >= dropDistance) { // Drop distance reached - deactivate Deactivate(); yield break; } yield return null; } } #endregion } }