Пример #1
0
        public override void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (!attackData.Attacker.IsRanged || (SkillLevel == SecondarySkillLevel.None))
            {
                return;
            }

            double bonus;

            if (SkillLevel == SecondarySkillLevel.Basic)
            {
                bonus = 0.1;
            }
            else if (SkillLevel == SecondarySkillLevel.Advanced)
            {
                bonus = 0.25;
            }
            else
            {
                bonus = 0.5;
            }

            if (IsSpecialized)
            {
                bonus *= (1.0 + 0.05 * HeroStats.Level);
            }

            damageModifier.DamageBonuses.Add(bonus);
        }
Пример #2
0
        public override void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (SkillLevel == SecondarySkillLevel.None)
            {
                return;
            }

            double reduction;

            if (SkillLevel == SecondarySkillLevel.Basic)
            {
                reduction = 0.05;
            }
            else if (SkillLevel == SecondarySkillLevel.Advanced)
            {
                reduction = 0.1;
            }
            else
            {
                reduction = 0.15;
            }

            if (IsSpecialized)
            {
                reduction *= (1.0 + 0.05 * HeroStats.Level);
            }

            damageModifier.DamageReductions.Add(reduction);
        }
Пример #3
0
 public void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
 {
     foreach (SecondarySkill skill in SecondarySkills)
     {
         skill.ApplyOnDefense(attackData, damageModifier);
     }
 }
Пример #4
0
        public override void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (SkillLevel == SecondarySkillLevel.None)
            {
                return;
            }

            double reduction;

            if (SkillLevel == SecondarySkillLevel.Basic)
            {
                reduction = 0.05;
            }
            else if (SkillLevel == SecondarySkillLevel.Advanced)
            {
                reduction = 0.1;
            }
            else
            {
                reduction = 0.15;
            }

            if (IsSpecialized)
            {
                reduction *= (1.0 + 0.05 * HeroStats.Level);
            }

            damageModifier.DamageReductions.Add(reduction);
        }
Пример #5
0
        public override void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (!attackData.Attacker.IsRanged || (SkillLevel == SecondarySkillLevel.None))
            {
                return;
            }

            double bonus;

            if (SkillLevel == SecondarySkillLevel.Basic)
            {
                bonus = 0.1;
            }
            else if (SkillLevel == SecondarySkillLevel.Advanced)
            {
                bonus = 0.25;
            }
            else
            {
                bonus = 0.5;
            }

            if (IsSpecialized)
            {
                bonus *= (1.0 + 0.05 * HeroStats.Level);
            }

            damageModifier.DamageBonuses.Add(bonus);
        }
Пример #6
0
 public override void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
 {
     if (CasterStats.IsSpecialized)
     {
         double bonus = 0.03 * (CasterStats.SpecializationLevel / attackData.Attacker.Level);
         damageModifier.DamageBonuses.Add(bonus);
     }
 }
Пример #7
0
 public override void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
 {
     if (CasterStats.IsSpecialized)
     {
         double bonus = 0.03 * (CasterStats.SpecializationLevel / attackData.Attacker.Level);
         damageModifier.DamageBonuses.Add(bonus);
     }
 }
Пример #8
0
        public void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
        {
            int attackerId = attackData.Attacker.Id;
            int defenderId = attackData.Defender.Id;

            int minUnitId = Math.Min(attackerId, defenderId);
            int maxUnitId = Math.Max(attackerId, defenderId);

            // Opposite elementals

            bool isOppositeElementalPair = false;

            isOppositeElementalPair |= (minUnitId == 114 || minUnitId == 115) && (maxUnitId == 120 || maxUnitId == 121); // air / earth
            isOppositeElementalPair |= (minUnitId == 116 || minUnitId == 117) && (maxUnitId == 118 || maxUnitId == 119); // water / fire

            if (isOppositeElementalPair)
            {
                damageModifier.DamageBonuses.Add(1.0);
            }

            // Hate pairs

            bool isHatePair = false;

            isHatePair |= (minUnitId == 12 || minUnitId == 13) && (maxUnitId == 82 || maxUnitId == 83); // angels / devils
            isHatePair |= (minUnitId == 36 || minUnitId == 37) && (maxUnitId == 80 || maxUnitId == 81); // genies / efreets
            isHatePair |= (minUnitId == 41) && (maxUnitId == 69);                                       // titans / black dragons

            if (isHatePair)
            {
                damageModifier.DamageBonuses.Add(0.5);
            }

            // Attacker is Psychic Elemental, defender is immune to Mind spells

            if ((attackerId == 122) &&
                (
                    attackData.Defender.IsUndead ||
                    (defenderId == 32 || defenderId == 33 || defenderId == 134 || defenderId == 135) || // Golems
                    (defenderId == 40 || defenderId == 41) ||                                           // Giant / Titan
                    (defenderId == 69) ||                                                               // Black Dragon
                    (defenderId >= 114 && defenderId <= 123)                                            // Elementals
                ))
            {
                damageModifier.DamageReductions.Add(0.5);
            }

            // Magic Elemental vs Magic Elemental or Black Dragon

            if ((attackerId == 123) && (defenderId == 123 || defenderId == 69))
            {
                damageModifier.DamageReductions.Add(0.5);
            }
        }
Пример #9
0
        public override void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (!attackData.Attacker.IsRanged)
            {
                return;
            }

            if (CasterStats.SkillLevel <= SecondarySkillLevel.Basic)
            {
                damageModifier.DamageReductions.Add(0.25);
            }
            else
            {
                damageModifier.DamageReductions.Add(0.5);
            }
        }
Пример #10
0
        public override void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
        {
            if (!attackData.Attacker.IsRanged)
            {
                return;
            }

            if (CasterStats.SkillLevel <= SecondarySkillLevel.Basic)
            {
                damageModifier.DamageReductions.Add(0.25);
            }
            else
            {
                damageModifier.DamageReductions.Add(0.5);
            }
        }
Пример #11
0
        private int PerformCalculation(int baseDamage, CombatDamageModifier damageModifier)
        {
            double result = baseDamage;

            double totalBonus = 1;

            foreach (double damageBonus in damageModifier.DamageBonuses)
            {
                totalBonus += damageBonus;
            }

            result *= totalBonus;
            result  = Math.Floor(result);

            foreach (double damageReduction in damageModifier.DamageReductions)
            {
                result *= (1 - damageReduction);
                result  = Math.Floor(result);
            }

            int intResult = (int)result;

            return((intResult > 0) ? intResult : 1);
        }
Пример #12
0
        public void CalculateDamage(CombatDamageCalculatorInputData data, out int minDamage, out int maxDamage, out string notes)
        {
            if (data.AttackerCount == 0)
            {
                minDamage = 0;
                maxDamage = 0;
                notes = null;
                return;
            }

            CombatDamageModifier damageModifier = new CombatDamageModifier();
            AttackData attackData = new AttackData { Attacker = data.Attacker, Defender = data.Defender };

            List<ICombatUnitStatsModifier> attackerStatsModifiers = new List<ICombatUnitStatsModifier>();
            List<ICombatUnitStatsModifier> defenderStatsModifiers = new List<ICombatUnitStatsModifier>();
            List<ICombatDamageModifierProvider> attackerDamageModifierProviders = new List<ICombatDamageModifierProvider>();
            List<ICombatDamageModifierProvider> defenderDamageModifierProviders = new List<ICombatDamageModifierProvider>();

            if (data.Terrain != null)
            {
                attackerStatsModifiers.Add(data.Terrain);
                defenderStatsModifiers.Add(data.Terrain);
            }

            if (data.AttackerHeroStats != null)
            {
                attackerStatsModifiers.Add(data.AttackerHeroStats);
                attackerDamageModifierProviders.Add(data.AttackerHeroStats);
            }

            if (data.DefenderHeroStats != null)
            {
                defenderStatsModifiers.Add(data.DefenderHeroStats);
                defenderDamageModifierProviders.Add(data.DefenderHeroStats);
            }

            if (data.AttackerSpells != null)
            {
                attackerStatsModifiers.AddRange(data.AttackerSpells);
                attackerDamageModifierProviders.AddRange(data.AttackerSpells);
            }

            if (data.DefenderSpells != null)
            {
                defenderStatsModifiers.AddRange(data.DefenderSpells);
                defenderDamageModifierProviders.AddRange(data.DefenderSpells);
            }

            attackerStatsModifiers.Add(UnitUniqueTraitManager.Instance);
            defenderStatsModifiers.Add(UnitUniqueTraitManager.Instance);
            attackerDamageModifierProviders.Add(UnitUniqueTraitManager.Instance);
            defenderDamageModifierProviders.Add(UnitUniqueTraitManager.Instance);

            /////////////////////////

            UnitStats modifiedAttackerStats = data.Attacker.InitialStats.Copy();
            UnitStats modifiedDefenderStats = data.Defender.InitialStats.Copy();

            foreach (ICombatUnitStatsModifier modifier in attackerStatsModifiers)
            {
                modifier.ApplyPermanently(data.Attacker, modifiedAttackerStats);
                modifier.ApplyOnAttack(attackData, modifiedAttackerStats);
            }

            foreach (ICombatUnitStatsModifier modifier in defenderStatsModifiers)
            {
                modifier.ApplyPermanently(data.Defender, modifiedDefenderStats);
                modifier.ApplyOnDefense(attackData, modifiedDefenderStats);
            }

            int totalAttack = modifiedAttackerStats.Attack;
            int totalDefense = modifiedDefenderStats.Defense;

            if (totalAttack > totalDefense)
            {
                double primarySkillBonus = Math.Min((totalAttack - totalDefense) * 0.05, 3.0);
                damageModifier.DamageBonuses.Add(primarySkillBonus);
            }
            else if (totalAttack < totalDefense)
            {
                double primarySkillReduction = Math.Min((totalDefense - totalAttack) * 0.025, 0.7);
                damageModifier.DamageReductions.Add(primarySkillReduction);
            }

            /////////////////////////

            foreach (ICombatDamageModifierProvider provider in attackerDamageModifierProviders)
            {
                provider.ApplyOnAttack(attackData, damageModifier);
            }

            foreach (ICombatDamageModifierProvider provider in defenderDamageModifierProviders)
            {
                provider.ApplyOnDefense(attackData, damageModifier);
            }

            int minBaseDamage = data.AttackerCount * modifiedAttackerStats.MinDamage;
            int maxBaseDamage = data.AttackerCount * modifiedAttackerStats.MaxDamage;

            minDamage = PerformCalculation(minBaseDamage, damageModifier);
            maxDamage = PerformCalculation(maxBaseDamage, damageModifier);
            notes = GenerateNotes(data);
        }
Пример #13
0
        private int PerformCalculation(int baseDamage, CombatDamageModifier damageModifier)
        {
            double result = baseDamage;

            double totalBonus = 1;
            foreach (double damageBonus in damageModifier.DamageBonuses)
            {
                totalBonus += damageBonus;
            }

            result *= totalBonus;
            result = Math.Floor(result);

            foreach (double damageReduction in damageModifier.DamageReductions)
            {
                result *= (1 - damageReduction);
                result = Math.Floor(result);
            }

            int intResult = (int)result;
            return (intResult > 0) ? intResult : 1;
        }
Пример #14
0
        public void CalculateDamage(CombatDamageCalculatorInputData data, out int minDamage, out int maxDamage, out string notes)
        {
            if (data.AttackerCount == 0)
            {
                minDamage = 0;
                maxDamage = 0;
                notes     = null;
                return;
            }

            CombatDamageModifier damageModifier = new CombatDamageModifier();
            AttackData           attackData     = new AttackData {
                Attacker = data.Attacker, Defender = data.Defender
            };

            List <ICombatUnitStatsModifier>      attackerStatsModifiers          = new List <ICombatUnitStatsModifier>();
            List <ICombatUnitStatsModifier>      defenderStatsModifiers          = new List <ICombatUnitStatsModifier>();
            List <ICombatDamageModifierProvider> attackerDamageModifierProviders = new List <ICombatDamageModifierProvider>();
            List <ICombatDamageModifierProvider> defenderDamageModifierProviders = new List <ICombatDamageModifierProvider>();

            if (data.Terrain != null)
            {
                attackerStatsModifiers.Add(data.Terrain);
                defenderStatsModifiers.Add(data.Terrain);
            }

            if (data.AttackerHeroStats != null)
            {
                attackerStatsModifiers.Add(data.AttackerHeroStats);
                attackerDamageModifierProviders.Add(data.AttackerHeroStats);
            }

            if (data.DefenderHeroStats != null)
            {
                defenderStatsModifiers.Add(data.DefenderHeroStats);
                defenderDamageModifierProviders.Add(data.DefenderHeroStats);
            }

            if (data.AttackerSpells != null)
            {
                attackerStatsModifiers.AddRange(data.AttackerSpells);
                attackerDamageModifierProviders.AddRange(data.AttackerSpells);
            }

            if (data.DefenderSpells != null)
            {
                defenderStatsModifiers.AddRange(data.DefenderSpells);
                defenderDamageModifierProviders.AddRange(data.DefenderSpells);
            }

            attackerStatsModifiers.Add(UnitUniqueTraitManager.Instance);
            defenderStatsModifiers.Add(UnitUniqueTraitManager.Instance);
            attackerDamageModifierProviders.Add(UnitUniqueTraitManager.Instance);
            defenderDamageModifierProviders.Add(UnitUniqueTraitManager.Instance);

            /////////////////////////

            UnitStats modifiedAttackerStats = data.Attacker.InitialStats.Copy();
            UnitStats modifiedDefenderStats = data.Defender.InitialStats.Copy();

            foreach (ICombatUnitStatsModifier modifier in attackerStatsModifiers)
            {
                modifier.ApplyPermanently(data.Attacker, modifiedAttackerStats);
                modifier.ApplyOnAttack(attackData, modifiedAttackerStats);
            }

            foreach (ICombatUnitStatsModifier modifier in defenderStatsModifiers)
            {
                modifier.ApplyPermanently(data.Defender, modifiedDefenderStats);
                modifier.ApplyOnDefense(attackData, modifiedDefenderStats);
            }

            int totalAttack  = modifiedAttackerStats.Attack;
            int totalDefense = modifiedDefenderStats.Defense;

            if (totalAttack > totalDefense)
            {
                double primarySkillBonus = Math.Min((totalAttack - totalDefense) * 0.05, 3.0);
                damageModifier.DamageBonuses.Add(primarySkillBonus);
            }
            else if (totalAttack < totalDefense)
            {
                double primarySkillReduction = Math.Min((totalDefense - totalAttack) * 0.025, 0.7);
                damageModifier.DamageReductions.Add(primarySkillReduction);
            }

            /////////////////////////

            foreach (ICombatDamageModifierProvider provider in attackerDamageModifierProviders)
            {
                provider.ApplyOnAttack(attackData, damageModifier);
            }

            foreach (ICombatDamageModifierProvider provider in defenderDamageModifierProviders)
            {
                provider.ApplyOnDefense(attackData, damageModifier);
            }

            int minBaseDamage = data.AttackerCount * modifiedAttackerStats.MinDamage;
            int maxBaseDamage = data.AttackerCount * modifiedAttackerStats.MaxDamage;

            minDamage = PerformCalculation(minBaseDamage, damageModifier);
            maxDamage = PerformCalculation(maxBaseDamage, damageModifier);
            notes     = GenerateNotes(data);
        }
Пример #15
0
 public virtual void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
 {
 }
Пример #16
0
        public void ApplyOnAttack(AttackData attackData, CombatDamageModifier damageModifier)
        {
            int attackerId = attackData.Attacker.Id;
            int defenderId = attackData.Defender.Id;

            int minUnitId = Math.Min(attackerId, defenderId);
            int maxUnitId = Math.Max(attackerId, defenderId);

            // Opposite elementals

            bool isOppositeElementalPair = false;

            isOppositeElementalPair |= (minUnitId == 114 || minUnitId == 115) && (maxUnitId == 120 || maxUnitId == 121); // air / earth
            isOppositeElementalPair |= (minUnitId == 116 || minUnitId == 117) && (maxUnitId == 118 || maxUnitId == 119); // water / fire

            if (isOppositeElementalPair)
            {
                damageModifier.DamageBonuses.Add(1.0);
            }

            // Hate pairs

            bool isHatePair = false;
            isHatePair |= (minUnitId == 12 || minUnitId == 13) && (maxUnitId == 82 || maxUnitId == 83); // angels / devils
            isHatePair |= (minUnitId == 36 || minUnitId == 37) && (maxUnitId == 80 || maxUnitId == 81); // genies / efreets
            isHatePair |= (minUnitId == 41) && (maxUnitId == 69); // titans / black dragons

            if (isHatePair)
            {
                damageModifier.DamageBonuses.Add(0.5);
            }

            // Attacker is Psychic Elemental, defender is immune to Mind spells

            if ((attackerId == 122) &&
                (
                 attackData.Defender.IsUndead ||
                 (defenderId == 32 || defenderId == 33 || defenderId == 134 || defenderId == 135) || // Golems
                 (defenderId == 40 || defenderId == 41) || // Giant / Titan
                 (defenderId == 69) || // Black Dragon
                 (defenderId >= 114 && defenderId <= 123) // Elementals
                ))
            {
                damageModifier.DamageReductions.Add(0.5);
            }

            // Magic Elemental vs Magic Elemental or Black Dragon

            if ((attackerId == 123) && (defenderId == 123 || defenderId == 69))
            {
                damageModifier.DamageReductions.Add(0.5);
            }
        }
Пример #17
0
 public virtual void ApplyOnDefense(AttackData attackData, CombatDamageModifier damageModifier)
 {
 }