/// <summary> /// Performs an ability on a target location, applying damage, healing, and status effects to any targets. /// </summary> /// <param name="attacker">The attacker performing the ability.</param> /// <param name="ability">The ability used to attack the enemy.</param> /// <param name="targetPosition">The position to target with the ability being used.</param> /// <param name="targetFormation">The Formation that the CombatEntity is targeting with its action.</param> /// <returns></returns> public AbilityResult PerformAbility(CombatEntity attacker, Ability ability, int targetPosition, Formation targetFormation) { var result = new AbilityResult(); // Target position is out of bounds if (!ability.IsPointBlank && !ability.IsPositionStatic && (targetPosition > 9 || targetPosition < 1)) { result.FailureReason = BattleErrorWriter.WriteTargetPositionOutOfBounds(); return(result); } if (!HasEnoughResources(attacker, ability, out string failureReason)) { result.FailureReason = failureReason; return(result); } if (ability.IsPointBlank) { targetPosition = GetTargetPosition(attacker, targetFormation); } var targets = FormationTargeter.GetTargets(ability, targetPosition, targetFormation).ToList(); if (targets == null || targets.Count == 0) { result.FailureReason = BattleErrorWriter.WriteNoTargets(); return(result); } // Filter out all dead targets targets = targets.Where(entity => entity != null && entity.Resources.CurrentHealth > 0).ToList(); // Will be an invalid Ability usage if all targets are dead (later on will add ability to revive) if (targets.Count == 0) { result.FailureReason = BattleErrorWriter.WriteAllTargetsAreDead(); return(result); } ConsumeResources(attacker, ability); ApplyEffects(attacker, ability, targets); targets.Add(attacker); result.AffectedEntities = targets; return(result); }
/// <summary> /// Creates an instance of a DelayedAbility. /// </summary> /// <param name="attacker">The CombatEntity starting the effect of a DelayedAbility.</param> /// <param name="ability">The Ability to convert into a DelayedAbility.</param> /// <param name="action">The object containing details about the action being performed.</param> /// <param name="targetFormation">The Formation that the CombatEntity is targeting with its action.</param> /// <returns></returns> public DelayedAbilityResult CreateDelayedAbility(CombatEntity attacker, Ability ability, BattleAction action, Formation targetFormation) { var result = new DelayedAbilityResult(); // Target out of bounds if (!ability.IsPointBlank && !ability.IsPositionStatic && (action.TargetPosition > 9 || action.TargetPosition < 1)) { result.FailureReason = BattleErrorWriter.WriteTargetPositionOutOfBounds(); return(result); } if (!HasEnoughResources(attacker, ability, out string failureReason)) { result.FailureReason = failureReason; return(result); } int targetPosition = action.TargetPosition; if (ability.IsPointBlank) { targetPosition = GetTargetPosition(attacker, targetFormation); } ConsumeResources(attacker, ability); bool isCrit = IsCritical(attacker, ability); result.DelayedAbility = new DelayedAbility { Actor = attacker, BaseAbility = ability, StoredDamage = DamageCalculator.GetDamage(attacker, ability, isCrit), StoredHealing = DamageCalculator.GetHeal(attacker, ability, isCrit), TargetFormation = targetFormation, TargetPosition = action.TargetPosition, IsCrit = isCrit, TurnsLeft = ability.DelayedTurns }; return(result); }