Esempio n. 1
0
        public void TestBasicFight()
        {
            var attackerCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(2)
                                                .Special(0)
                                                .Speed(13)
                                                .Strength(7)
                                                .Build())
                                    .Weapons("Shortsword")
                                    .Build();

            var defenderCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(2)
                                                .Special(0)
                                                .Speed(13)
                                                .Strength(3)
                                                .Build())
                                    .Weapons("Shortsword")
                                    .Build();

            var attacker = new BaseCombatant(attackerCharacter, ArmyType.Friendly);
            var defender = new BaseCombatant(defenderCharacter, ArmyType.Friendly);

            attacker.Position = new Vector2(0, 1);
            defender.Position = new Vector2(0, 0);

            var map = new Map();

            map.AddCombatant(attacker);
            map.AddCombatant(defender);

            var skillDatabase = new SkillDatabase(map);

            var forecaster = new FightForecaster(map, skillDatabase);
            var forecast   = forecaster.Forecast(attacker, defender, SkillType.Melee);
            var finalizer  = new FightFinalizer(skillDatabase);

            var final        = finalizer.Finalize(forecast, new ConstantRandomizer(100));
            var initialPhase = final.InitialPhase;

            Assert.NotNull(initialPhase);

            var initialDamage = initialPhase.Effects.GetDefenderDamage();

            Assert.AreEqual(5, initialDamage);
            var counterPhase = final.CounterPhase;

            Assert.NotNull(counterPhase);

            var counterDamage = counterPhase.Effects.GetDefenderDamage();

            Assert.AreEqual(1, counterDamage);
        }
Esempio n. 2
0
        public void TestAttackerKillsOnDouble()
        {
            var attackerCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(2)
                                                .Special(0)
                                                .Speed(33)
                                                .Strength(10)
                                                .Build())
                                    .Weapons("Shortsword")
                                    .Build();

            var defenderCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(0)
                                                .Special(0)
                                                .Speed(13)
                                                .Strength(7)
                                                .Build())
                                    .Stats(new StatsBuilder()
                                           .ParryChance(0)
                                           .Build())
                                    .Weapons("Shortsword")
                                    .Build();

            var attacker = new BaseCombatant(attackerCharacter, ArmyType.Friendly);
            var defender = new BaseCombatant(defenderCharacter, ArmyType.Friendly);

            attacker.Position = new Vector2(0, 0);
            defender.Position = new Vector2(0, 1);

            var map           = new Map();
            var skillDatabase = new SkillDatabase(map);
            var forecaster    = new FightForecaster(map, skillDatabase);
            var forecast      = forecaster.Forecast(attacker, defender, SkillType.Melee);
            var finalizer     = new FightFinalizer(skillDatabase);
            var final         = finalizer.Finalize(forecast, new ConstantRandomizer(100));

            Assert.NotNull(final.InitialPhase);
            Assert.NotNull(final.CounterPhase);
            Assert.NotNull(final.DoubleAttackPhase);
            Assert.Null(final.FlankerPhase);
        }
Esempio n. 3
0
        public Battle(IMap map, IRandomizer randomizer, ICombatantDatabase combatants, List <ArmyType> turnOrder, List <IObjective> objectives,
                      MapConfig mapConfig)
        {
            TurnNumber            = 0;
            EventTileWalkedSignal = new Signal <string>();
            Objectives            = objectives;
            Map         = map;
            _randomizer = randomizer;
            _combatants = combatants;

            map.EventTileTriggeredSignal.AddListener(_relayEvent);

            var skillDatabase = new SkillDatabase(map);

            _forecaster = new FightForecaster(map, skillDatabase);
            _finalizer  = new FightFinalizer(skillDatabase);
            _turnOrder  = turnOrder
                          .Where(army => combatants.GetCombatantsByArmy(army).Count > 0)
                          .ToList();

            foreach (var combatant in combatants.GetAllCombatants())
            {
                RegisterCombatant(combatant, map);
            }

            foreach (var eventTile in mapConfig.EventTiles)
            {
                Map.AddEventTile(eventTile);
            }

            var firstArmy = _turnOrder[0];

            _currentTurn = new Turn(_combatants, firstArmy);

            _eventsByTurn = mapConfig.TurnEvents
                            .GroupBy(evt => evt.ActivationTurn)
                            .ToDictionary(x => x.Key, x => x.ToList());
        }
Esempio n. 4
0
        public override void Execute()
        {
            var state = BattleViewModel.State;

            if (state == BattleUIState.Uninitialized ||
                state == BattleUIState.PhaseChanging ||
                state == BattleUIState.Preparations ||
                state == BattleUIState.Surveying)
            {
                return;
            }

            var combatant = BattleViewModel.Map.GetAtPosition(Position);

            if (state == BattleUIState.SelectingUnit)
            {
                if (combatant != null && combatant.Army == ArmyType.Friendly)
                {
                    var actions = AvailableActions.GetAvailableActionTypes(combatant);
                    if (actions.Count <= 0)
                    {
                        return;
                    }
                    // Mark the unit at Position as selected, change the battle state.
                    BattleViewModel.SelectedCombatant = combatant;
                    BattleViewModel.State             = BattleUIState.SelectingAction;
                    BattleViewModel.AvailableActions  = actions;

                    var dimensions    = BattleViewModel.Dimensions;
                    var worldPosition = dimensions.GetWorldPositionForGridPosition(combatant.Position);
                    UnitSelectedSignal.Dispatch(worldPosition);
                }
            }
            else if (state == BattleUIState.SelectingMoveLocation)
            {
                var map  = BattleViewModel.Map;
                var path = BattleViewModel.CurrentMovementPath;
                if (path != null)
                {
                    // Don't allow movement to the terminal points of a path if they are blocked.
                    var terminus = path.Terminus;
                    if (!map.IsBlocked(terminus))
                    {
                        var positions = path.Positions.GetRange(1, path.Positions.Count - 1);

                        var action = new MoveAction(map, path.Combatant, positions.Last(), positions);
                        AnimateActionSignal.Dispatch(action);
                        BattleViewModel.State = BattleUIState.CombatantMoving;
                    }
                }
            }
            else if (state == BattleUIState.SelectingInteractTarget)
            {
                var map  = BattleViewModel.Map;
                var tile = map.GetEventTile(Position);

                // Only if the player clicks on a tile that is actually interactible by clicks
                if (tile != null && tile.InteractionMode == InteractionMode.Use)
                {
                    EventTileInteractedSignal.Dispatch(tile);
                }
            }
            else if (state == BattleUIState.SelectingAttackTarget)
            {
                if (combatant != null && combatant.Army == ArmyType.Enemy)
                {
                    // Forecast the fight against this unit
                    var attacker             = BattleViewModel.SelectedCombatant;
                    var battle               = BattleViewModel.Battle;
                    var selectedUnitPosition = attacker.Position;
                    var distanceToTarget     = MathUtils.ManhattanDistance(selectedUnitPosition, Position);
                    var map = BattleViewModel.Map;

                    SkillType skill;
                    if (BattleViewModel.SpecialAttack)
                    {
                        if (!attacker.SpecialSkill.HasValue)
                        {
                            throw new ArgumentException("Combatant " + attacker.Id + " has no special skill configured.");
                        }
                        skill = attacker.SpecialSkill.Value;
                    }
                    else
                    {
                        skill = battle.GetWeaponSkillForRange(attacker, distanceToTarget);
                    }

                    var skillDatabase = new SkillDatabase(map);
                    var forecaster    = new FightForecaster(map, skillDatabase);
                    var fight         = forecaster.Forecast(BattleViewModel.SelectedCombatant, combatant, skill);
                    FightForecastSignal.Dispatch(fight);
                    BattleViewModel.FightForecast = fight;
                    BattleViewModel.State         = BattleUIState.ForecastingCombat;
                }
            }
        }
Esempio n. 5
0
        public void TestRangedCounter()
        {
            var attackerCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(2)
                                                .Special(0)
                                                .Speed(13)
                                                .Strength(7)
                                                .Build())
                                    .Stats(new StatsBuilder()
                                           .ParryChance(0)
                                           .Build())
                                    .Weapons("Slim Recurve")
                                    .Build();

            var defenderCharacter = new CharacterBuilder()
                                    .Attributes(new AttributesBuilder()
                                                .Health(15)
                                                .Skill(12)
                                                .Defense(2)
                                                .Special(0)
                                                .Speed(13)
                                                .Strength(7)
                                                .Build())
                                    .Stats(new StatsBuilder()
                                           .ParryChance(0)
                                           .Build())
                                    .Weapons("Slim Recurve")
                                    .Build();

            var attacker = new BaseCombatant(attackerCharacter, ArmyType.Friendly);
            var defender = new BaseCombatant(defenderCharacter, ArmyType.Friendly);

            attacker.Position = new Vector2(0, 0);
            defender.Position = new Vector2(0, 2);

            var map = new Map();

            map.AddCombatant(attacker);
            map.AddCombatant(defender);

            var skillDatabase = new SkillDatabase(map);
            var forecaster    = new FightForecaster(map, skillDatabase);
            var forecast      = forecaster.Forecast(attacker, defender, SkillType.Ranged);

            var finalizer = new FightFinalizer(skillDatabase);
            var final     = finalizer.Finalize(forecast, new ConstantRandomizer(100));

            var initialPhase = final.InitialPhase;

            Assert.NotNull(initialPhase);

            var initialEffects = initialPhase.Effects;

            Assert.AreEqual(5, initialEffects.GetDefenderDamage());

            var counterPhase = final.CounterPhase;

            Assert.NotNull(counterPhase);

            var counterEffects = counterPhase.Effects;

            Assert.AreEqual(5, counterEffects.GetDefenderDamage());

            Assert.Null(final.DoubleAttackPhase);
            Assert.Null(final.FlankerPhase);
        }