예제 #1
0
    /// <summary>
    /// Select a unit stack from a list of existing ones and make an illusory clone of it
    /// </summary>
    /// <param name="existing">The list of existing unit stacks</param>
    public override UnitStack Create(List <UnitStack> existing)
    {
        if (existing.Count > 0)
        {
            UnitStack toClone = existing[0];
            int       qty     = toClone.GetTotalQty();
            int       candidateQty;
            for (int i = 1; i < existing.Count; i++)
            {
                candidateQty = existing[i].GetTotalQty();
                if (candidateQty > qty)
                {
                    toClone = existing[i];
                    qty     = candidateQty;
                }
            }

            UnitType illusion = new UnitType(toClone.GetUnitType());
            illusion.SetShield(0);
            illusion.SetArmor(0);
            illusion.SetHitPoints(1);
            illusion.AddAttackQuality(AttackData.Quality.ILLUSORY);

            Unit      mirrorImage = new Unit(illusion, toClone.GetTotalQty());
            UnitStack stack       = new UnitStack(mirrorImage, toClone.GetProvinceToRetreat());
            stack.AffectBySpell(this);

            return(stack);
        }
        return(null);
    }
예제 #2
0
    /// <summary>
    /// Handles defender selection and related animations.
    /// </summary>
    private void ProcessPhaseWithAttacks()
    {
        FileLogger.Trace("COMBAT VIEW", "ProcessPhaseWithAttacks");
        // unit stacks could be created or destroyed - update the stack views
        UpdateUnitStackViews();
        if (!_model.AreThereUnresolvedAttacks())
        {
            _skipPhase = false;
            ProcessCombatTurn();
        }
        else
        {
            // show all attacks
            UpdateAttackViews();

            AttackRollResultsCollection currentAttackBatch = _model.SelectAttackRollResultsCollection();
            if (currentAttackBatch != null)
            {
                FileLogger.Trace("COMBAT", "Selected attacks by " + currentAttackBatch.GetUnitStack().GetUnitType().GetName());
                if (currentAttackBatch.GetUnitStack() != _currentAttacker)
                {
                    SetNewStackForCurrentAttackView(currentAttackBatch.GetUnitStack());
                    // a new defender will be selected against a new attack
                    _currentDefender = null;
                    _skipStack       = false;
                    FileLogger.Trace("COMBAT VIEW", "ProcessPhaseWithAttacks: Setting skip stack to false");
                }

                if (!_model.IsPlayerTurn())
                {
                    SelectAnNPCStackAsTarget();
                }
                else
                {
                    // if it's the player's turn
                    // and he already selected a defending stack, resolve the attack
                    if (_currentDefender != null && _currentDefender.GetTotalQty() > 0)
                    {
                        FileLogger.Trace("COMBAT", "Resolving an attack against " + _currentDefender.GetUnitType().GetName());
                        _model.ResolveCurrentAttack(false);
                    }
                    // else wait until the player will click on a stack view
                }
            }
            // else panic - there should be no case when there are unresolved attacks
            // but the model can't return an attack collection
        }
    }
예제 #3
0
 /// <summary>
 /// Select a target for the spell from a list of candidates and cast the spell on it
 /// </summary>
 /// <param name="potentialTargets">The list of potential targets</param>
 public override void CastOn(List <UnitStack> potentialTargets)
 {
     if (potentialTargets.Count > 0)
     {
         // note: the spell doesn't work on holy units
         UnitStack toTarget = potentialTargets[0];
         int       qty      = toTarget.GetTotalQty();
         int       candidateQty;
         for (int i = 1; i < potentialTargets.Count; i++)
         {
             candidateQty = potentialTargets[i].GetTotalQty();
             if (toTarget.IsAffectedBy(this) ||
                 toTarget.GetUnitType().IsHoly() ||
                 (candidateQty > qty &&
                  !potentialTargets[i].IsAffectedBy(this) &&
                  !potentialTargets[i].GetUnitType().IsHoly()))
             {
                 toTarget = potentialTargets[i];
                 qty      = candidateQty;
             }
         }
         if (!toTarget.IsAffectedBy(this) && !toTarget.GetUnitType().IsHoly())
         {
             toTarget.AffectBySpell(this);
         }
     }
 }
예제 #4
0
 public void UpdateView()
 {
     _quantityField.text = _model.GetTotalQty().ToString();
     _healthField.text   = _model.GetTotalHealth().ToString();
     _mirrorImageField.gameObject.SetActive(_model.IsAffectedBy("Mirror Image"));
     _confusionField.gameObject.SetActive(_model.IsAffectedBy("Confusion"));
     _magicShieldField.gameObject.SetActive(_model.IsAffectedBy("Magic Shield"));
     _stoneSkinField.gameObject.SetActive(_model.IsAffectedBy("Stone Skin"));
 }
예제 #5
0
 /// <summary>
 /// Select a target for the spell from a list of candidates and cast the spell on it
 /// </summary>
 /// <param name="potentialTargets">The list of potential targets</param>
 public override void CastOn(List <UnitStack> potentialTargets)
 {
     if (potentialTargets.Count > 0)
     {
         UnitStack toTarget = potentialTargets[0];
         int       qty      = toTarget.GetTotalQty();
         int       candidateQty;
         for (int i = 1; i < potentialTargets.Count; i++)
         {
             candidateQty = potentialTargets[i].GetTotalQty();
             if (toTarget.IsAffectedBy(this) || (candidateQty > qty && !potentialTargets[i].IsAffectedBy(this)))
             {
                 toTarget = potentialTargets[i];
                 qty      = candidateQty;
             }
         }
         toTarget.AffectBySpell(this);
     }
 }
예제 #6
0
    /// <summary>
    /// Resolve current attack
    /// </summary>
    /// <param name="useEstimates">Whether estimated results will be used or honest rolls will be made</param>
    public void ResolveCurrentAttack(bool useEstimates)
    {
        bool ok = false;

        if (_currentTarget != null && _currentAttacks != null && _currentAttacks.Count > 0)
        {
            ok = ResolveAnAttackAgainstTarget(_currentTarget, _currentAttacks.GetAt(_currentAttacks.Count - 1), useEstimates);
        }
        if (!ok || _currentAttacks == null || _currentAttacks.Count == 0 ||
            _currentTarget == null || _currentTarget.GetTotalQty() == 0)
        {
            _currentTarget  = null;
            _currentAttacks = null;
            FileLogger.Trace("COMBAT", "ResolveCurrentAttack: reset current target.");
        }
        else
        {
            FileLogger.Trace("COMBAT", "ResolveCurrentAttack: " + _currentAttacks.Count + " attacks and " + _currentTarget.GetTotalQty() + " targets left.");
        }
    }
예제 #7
0
    /// <summary>
    /// Is the unit stack a valid target for the attack?
    /// </summary>
    /// <param name="target">Unit stack which is a potential target for the attack</param>
    /// <param name="attackRollResult">Attack roll result representing the attack</param>
    /// <returns>Whether the unit stack is a valid target for the attack</returns>
    private bool IsValidAttackTarget(UnitStack target, AttackRollResult attackRollResult)
    {
        if (_attackers.Contains(target) && _attackers.Contains(attackRollResult.UnitStack))
        {
            FileLogger.Trace("COMBAT", "Both " + attackRollResult.UnitStack.GetUnitType().GetName() + " and " + target.GetUnitType().GetName() + " belong to the attacker");
            return(false);
        }

        if (_defenders.Contains(target) && _defenders.Contains(attackRollResult.UnitStack))
        {
            FileLogger.Trace("COMBAT", "Both " + attackRollResult.UnitStack.GetUnitType().GetName() + " and " + target.GetUnitType().GetName() + " belong to the defender");
            return(false);
        }

        if (target.GetTotalQty() == 0)
        {
            FileLogger.Trace("COMBAT", "No defenders left in this stack");
            return(false);
        }
        return(true);
    }