public FormClasses()
        {
            InitializeComponent();

            pData        = new Classe();
            IncrementTab = new Increment();
            BasicTab     = new Basic();
            StatTab      = new BaseStat();
            VitalTab     = new Vital();
            PhysicalTab  = new Physical();
            MagicTab     = new Magic();
            ExtraTab     = new Extra();
            ElementalTab = new Elemental();
            ResistTab    = new Resist();

            DockPanel.AddContent(BasicTab);
            DockPanel.AddContent(StatTab);
            DockPanel.AddContent(VitalTab);
            DockPanel.AddContent(PhysicalTab);
            DockPanel.AddContent(MagicTab);
            DockPanel.AddContent(ElementalTab);
            DockPanel.AddContent(ResistTab);
            DockPanel.AddContent(ExtraTab);

            DockPanel.ContentRemoved += DockPanel_ContentRemoved;
        }
Ejemplo n.º 2
0
        public void Setup()
        {
            GlobalReference.GlobalValues = new GlobalValues();

            elementalMob = new Mock <IElemental>();
            elemental    = new Elemental();
        }
Ejemplo n.º 3
0
        public void Setup()
        {
            GlobalReference.GlobalValues = new GlobalValues();

            world         = new Mock <IWorld>();
            settings      = new Mock <ISettings>();
            defaultValues = new Mock <IDefaultValues>();
            tagWrapper    = new Mock <ITagWrapper>();
            notify        = new Mock <INotify>();
            room          = new Mock <IRoom>();
            moneyToCoins  = new Mock <IMoneyToCoins>();

            world.Setup(e => e.Precipitation).Returns(100);
            world.Setup(e => e.WindSpeed).Returns(100);
            settings.Setup(e => e.MaxLevel).Returns(100);
            tagWrapper.Setup(e => e.WrapInTag(It.IsAny <string>(), TagType.Info)).Returns((string x, TagType y) => (x));
            moneyToCoins.Setup(e => e.FormatedAsCoins(0)).Returns("0 coins");

            GlobalReference.GlobalValues.World         = world.Object;
            GlobalReference.GlobalValues.Settings      = settings.Object;
            GlobalReference.GlobalValues.DefaultValues = defaultValues.Object;
            GlobalReference.GlobalValues.TagWrapper    = tagWrapper.Object;
            GlobalReference.GlobalValues.Notify        = notify.Object;
            GlobalReference.GlobalValues.MoneyToCoins  = moneyToCoins.Object;

            elemental        = new Elemental(ElementType.Air);
            roundTickCounter = elemental.GetType().GetProperty("RoundTickCounter", BindingFlags.NonPublic | BindingFlags.Instance);

            roundTickCounter.SetValue(elemental, -1);
        }
        public FormIncrement()
        {
            InitializeComponent();

            pData        = new Classe();
            IncrementTab = new Increment();
            //muda o modo de edição para incremento
            BasicTab = new Basic();
            BasicTab.IsClasseMode = false;

            StatTab      = new BaseStat();
            VitalTab     = new Vital();
            PhysicalTab  = new Physical();
            MagicTab     = new Magic();
            ExtraTab     = new Extra();
            ElementalTab = new Elemental();
            ResistTab    = new Resist();

            DockPanel.AddContent(BasicTab);
            DockPanel.AddContent(StatTab);
            DockPanel.AddContent(VitalTab);
            DockPanel.AddContent(PhysicalTab);
            DockPanel.AddContent(MagicTab);
            DockPanel.AddContent(ElementalTab);
            DockPanel.AddContent(ResistTab);
            DockPanel.AddContent(ExtraTab);

            DockPanel.ContentRemoved += DockPanel_ContentRemoved;
        }
Ejemplo n.º 5
0
        // HACK: ad-hoc placement code
        private void PlaceActors()
        {
            Game.Player.Pos = Map.GetRandomOpenPoint();
            Map.AddActor(Game.Player);

            for (int i = 0; i < Game._enemyCount[Level]; i++)
            {
                var         element   = (Element)(Rand.Next(4) + 1);
                int         enemyType = Rand.Next(4);
                Actor.Actor enemy;

                if (enemyType == 0)
                {
                    enemy = new Sprite(Map.GetRandomOpenPoint(), element);
                }
                else if (enemyType == 1)
                {
                    enemy = new Elemental(Map.GetRandomOpenPoint(), element);
                }
                else if (enemyType == 2)
                {
                    enemy = new Bomber(Map.GetRandomOpenPoint(), element);
                }
                else
                {
                    enemy = new Leech(Map.GetRandomOpenPoint(), element);
                }

                Map.AddActor(enemy);
            }

            Map.Refresh();
        }
Ejemplo n.º 6
0
 public void SetupBaseAttack(int r = 1, int d = 1, int a = 1, int act = 2, Elemental e = Elemental.None)
 {
     attackRange   = r;
     attackArea    = a;
     attackDamage  = d;
     attackElem    = e;
     attackActions = act;
 }
Ejemplo n.º 7
0
 public virtual void OnInteract(Elemental source)
 {
     Debug.Log("Interact!");
     //if(!isColored), then...
     if (!isColored && _anim)
     {
         isColored = true;
         _anim.SetTrigger("Interact");
     }
 }
Ejemplo n.º 8
0
        private static void SpawnElemental(IRoom room, ElementType elementType)
        {
            Elemental elemental = new Elemental(elementType);

            elemental.FinishLoad();
            room.AddMobileObjectToRoom(elemental);
            elemental.Room = room;
            ITranslationMessage translationMessage = new TranslationMessage($"A {elemental.KeyWords[0]} elemental appears out of nothing.");

            GlobalReference.GlobalValues.Notify.Room(elemental, null, room, translationMessage, null, true);
        }
Ejemplo n.º 9
0
        public void Elemental_ProcessElementalTick_Earth_NoChange()
        {
            elemental = new Elemental(ElementType.Earth);
            roundTickCounter.SetValue(elemental, -1);
            world.Setup(e => e.Precipitation).Returns(40);

            elemental.ProcessElementalTick();

            Assert.AreEqual(1, elemental.Level);
            world.Verify(e => e.Precipitation, Times.AtLeastOnce);
            notify.Verify(e => e.Room(elemental, null, null, It.IsAny <ITranslationMessage>(), null, true, false), Times.Never);
        }
Ejemplo n.º 10
0
    private void OnTriggerEnter2D(Collider2D other)
    {
        Elemental e = other.gameObject.GetComponent <Elemental>();

        if (e != null)
        {
            if (e.Element.DefeatedElements.Contains(Element))
            {
                Destroy(gameObject);
            }
        }
    }
        public static void Generate(WeakAura wa)
        {
            var elemental = new Elemental();

            var builder = new SpecBuilder(ClassSpec.Elemental);

            Console.WriteLine("Pets and totems!");

            // Lightning Shield, Flametongue Weapon?
            builder.AddOverflow(
                elemental.EarthElemental.Buff(),
                elemental.AstralShift.Buff(),
                elemental.Heroism.Buff(),
                elemental.Hex.DeBuff(),
                elemental.CleanseSpirit,
                // or debuff?
                elemental.NaturesGuardian.Buff() // T5
                ).AddRightBar(
                elemental.Thunderstorm.DeBuff(),
                elemental.SpiritwalkersGrace.Buff(),
                elemental.WindRushTotem.Buff(),    // T5
                elemental.AncestralGuidance.Buff() // T5
                ).AddCoreRotation(
                elemental.FlameShock.DeBuff(),
                elemental.LavaBurst,
                elemental.EchoingShock.Buff(),   // T3
                elemental.ElementalBlast.Buff(), // T3
                elemental.Icefury.Buff()         // T6 (IceFury Overload might be the buff)
                ).AddCoreCooldowns(
                // todo: pet -or- totem tracking?
                elemental.FireElemental.Buff(),
                elemental.StaticDischarge.Buff(),  // T2
                elemental.LiquidMagmaTotem.Buff(), // T4
                elemental.Stormkeeper.Buff(),      // T7
                elemental.Ascendance.Buff()        // T7
                ).AddBottomBar(
                elemental.EarthbindTotem.Buff(),
                elemental.CapacitorTotem.Buff(),
                elemental.HealingStreamTotem.Buff(),
                elemental.TremorTotem.Buff(),
                elemental.WindShear,
                elemental.Purge
                ).AddTopBar(
                elemental.FrostShock.Passive().Buff(),
                elemental.SurgeOfPower.Passive().Buff(), // T6
                elemental.UnlimitedPower.Passive().Buff()
                ).AddAlerts(
                elemental.WaterWalking.Passive().Buff(),
                // todo: any reason not to have Lightning Shield!?
                elemental.LightningShield.Passive().MissingBuff()
                ).Build(wa);
        }
Ejemplo n.º 12
0
        public void Elemental_ProcessElementalTick_Earth_GainLevel()
        {
            elemental = new Elemental(ElementType.Earth);
            roundTickCounter.SetValue(elemental, -1);
            elemental.Level = 5;
            elemental.FinishLoad();
            Assert.AreEqual(5, elemental.EquipedArmor.Count());
            world.Setup(e => e.Precipitation).Returns(0);

            elemental.ProcessElementalTick();

            Assert.AreEqual(6, elemental.Level);
            Assert.AreEqual(6, elemental.EquipedArmor.Count());
            world.Verify(e => e.Precipitation, Times.AtLeastOnce);
            notify.Verify(e => e.Room(elemental, null, null, It.Is <ITranslationMessage>(f => f.Message == "The earth elemental grows stronger."), null, true, false), Times.Once);
        }
Ejemplo n.º 13
0
 void OnCollisionEnter2D(Collision2D other)
 {
     if (other.gameObject.GetComponent <Elemental>())
     {
         Elemental elemental = other.gameObject.GetComponent <Elemental> ();
         if (curElement == Element.fire)
         {
             elemental.Ignite();
         }
         else if (curElement == Element.ice)
         {
             elemental.Freeze();
         }
     }
     OrbSpawner.orbs.Remove(this);
     Destroy(gameObject);
 }
Ejemplo n.º 14
0
        public void Elemental_ProcessElementalTick_Earth_LooseLevel()
        {
            elemental      = new Elemental(ElementType.Earth);
            elemental.Room = room.Object;
            room.Setup(e => e.NonPlayerCharacters).Returns(new List <INonPlayerCharacter>()
            {
                elemental
            });
            roundTickCounter.SetValue(elemental, -1);
            elemental.Level = 1;
            elemental.FinishLoad();
            Assert.AreEqual(1, elemental.EquipedArmor.Count());
            elemental.ProcessElementalTick();

            Assert.AreEqual(1, elemental.Level);
            Assert.AreEqual(1, elemental.EquipedArmor.Count());
            world.Verify(e => e.Precipitation, Times.AtLeastOnce);
            notify.Verify(e => e.Room(elemental, null, room.Object, It.Is <ITranslationMessage>(f => f.Message == "The earth elemental has grown so weak it can no longer hold its form in this realm and slowly fades away."), null, true, false), Times.Once);
        }
Ejemplo n.º 15
0
    public static string GetElementLayer(Elemental elemental)
    {
        string layer = "default";

        switch (elemental.CurrentElement)
        {
        case Element.AIR:
            layer = "element_air";
            break;

        case Element.ICE:
            layer = "element_ice";
            break;

        case Element.FIRE:
            layer = "element_fire";
            break;

        case Element.NONE:
            layer = "element_none";
            break;

        case Element.WATER:
            layer = "element_water";
            break;

        case Element.EARTH:
            layer = "element_earth";
            break;

        default:
            Debug.LogError("Element not supported: " + elemental.CurrentElement.ToString());
            break;
        }

        return(layer);
    }
Ejemplo n.º 16
0
 public CombatAttributes(Elemental elemental, Normal normal)
 {
     elements = elemental;
     this.normal = normal;
 }
Ejemplo n.º 17
0
        public void Elemental_Constructor_Air()
        {
            elemental = new Elemental(ElementType.Air);

            Assert.AreEqual("air", elemental.KeyWords[0]);
        }
        protected int CountDownCounter; // Amount of Ticks until cooldown is deactivated

        /// <summary>
        /// Call at start of child instantiation
        /// Caches the Health and Elemental Components
        /// </summary>
        protected void Init()
        {
            EntityHealth     = GetComponent <Health>();
            EntityElement    = GetComponent <Elemental>();
            CountDownCounter = CountDownTime;
        }
Ejemplo n.º 19
0
        public Character GetEnemy(int id)
        {
            Character nextChar;

            switch (id)
            {
            //Low level
            case 100:
                nextChar = new Bat();
                return(nextChar);

            case 101:
                nextChar = new Rat();
                return(nextChar);

            case 102:
                nextChar = new Kobold();
                return(nextChar);

            case 103:
                nextChar = new Slime();
                return(nextChar);

            case 104:
                nextChar = new Farmer();
                return(nextChar);

            case 105:
                nextChar = new Imp();
                return(nextChar);

            case 106:
                nextChar = new Zombie();
                return(nextChar);

            case 107:
                nextChar = new Phantom();
                return(nextChar);

            case 108:
                nextChar = new Goblin();
                return(nextChar);

            case 109:
                nextChar = new Witch();
                return(nextChar);

            //Mid level
            case 110:
                nextChar = new Harpy();
                return(nextChar);

            case 111:
                nextChar = new Elemental();
                return(nextChar);

            case 112:
                nextChar = new Nymph();
                return(nextChar);

            case 113:
                nextChar = new Vampire();
                return(nextChar);

            case 114:
                nextChar = new Lamia();
                return(nextChar);

            case 115:
                nextChar = new Qilin();
                return(nextChar);

            case 116:
                nextChar = new Unicorn();
                return(nextChar);

            case 117:
                nextChar = new Jinn();
                return(nextChar);

            case 118:
                nextChar = new Xorn();
                return(nextChar);

            case 119:
                nextChar = new Antlion();
                return(nextChar);

            //High level
            case 120:
                nextChar = new Yeti();
                return(nextChar);

            case 121:
                nextChar = new Orc();
                return(nextChar);

            case 122:
                nextChar = new Minotaur();
                return(nextChar);

            case 123:
                nextChar = new Troll();
                return(nextChar);

            case 124:
                nextChar = new Cyclop();
                return(nextChar);

            case 125:
                nextChar = new Drake();
                return(nextChar);

            default:
                nextChar = new Slime();
                return(nextChar);
            }
        }
Ejemplo n.º 20
0
 protected override IEnumerable <MatcherData> CreateCollection() =>
 new StatMatcherCollection <IStatBuilder>(_modifierBuilder)
 {
     // attributes
     { "strength", Attribute.Strength },
     { "strength damage bonus", Attribute.StrengthDamageBonus },
     { "dexterity", Attribute.Dexterity },
     { "dexterity evasion bonus", Attribute.DexterityEvasionBonus },
     { "intelligence", Attribute.Intelligence },
     { "strength and dexterity", ApplyOnce(Attribute.Strength, Attribute.Dexterity) },
     { "strength and intelligence", ApplyOnce(Attribute.Strength, Attribute.Intelligence) },
     { "dexterity and intelligence", ApplyOnce(Attribute.Dexterity, Attribute.Intelligence) },
     { "attributes", ApplyOnce(Attribute.Strength, Attribute.Dexterity, Attribute.Intelligence) },
     // offense
     // - damage: see also DamageStatMatchers
     { "chance to deal double damage", Damage.ChanceToDouble },
     {
         "({DamageTypeMatchers}) damage (gained |added )?as (extra )?({DamageTypeMatchers}) damage",
         References[0].AsDamageType.Damage.AddAs(References[1].AsDamageType.Damage)
     },
     {
         "({DamageTypeMatchers}) damage as extra damage of a random element",
         Reference.AsDamageType.Damage.AddAs(RandomElement.Damage)
     },
     {
         "({DamageTypeMatchers}) damage converted to ({DamageTypeMatchers}) damage",
         References[0].AsDamageType.Damage.ConvertTo(References[1].AsDamageType.Damage)
     },
     { "({DamageTypeMatchers}) damage taken", Reference.AsDamageType.Damage.Taken },
     { "take ({DamageTypeMatchers}) damage", Reference.AsDamageType.Damage.Taken },
     { "damage taken", Damage.Taken },
     // - penetration
     // - crit
     { "(global )?critical strike multiplier", CriticalStrike.Multiplier },
     { "(global )?critical strike chance", CriticalStrike.Chance },
     // - projectiles
     { "projectile speed", Projectile.Speed },
     { "arrow speed", Projectile.Speed, Damage.With(Tags.Bow) },
     // - other
     { "accuracy rating", Stat.Accuracy },
     // defense
     // - life, mana, defences; see also PoolStatMatchers
     { "armour", Armour },
     { "evasion( rating)?", Evasion },
     { "evasion rating and armour", ApplyOnce(Armour, Evasion) },
     { "armour and evasion( rating)?", ApplyOnce(Armour, Evasion) },
     { "armour and energy shield", ApplyOnce(Armour, EnergyShield) },
     { "(global )?defences", ApplyOnce(Armour, Evasion, EnergyShield) },
     // - resistances
     { "({DamageTypeMatchers}) resistance", Reference.AsDamageType.Resistance },
     { "all elemental resistances", Elemental.Resistance },
     { "maximum ({DamageTypeMatchers}) resistance", Reference.AsDamageType.Resistance.Maximum },
     { "all maximum resistances", Elemental.And(Chaos).Resistance.Maximum },
     { "physical damage reduction", Physical.Resistance },
     // - leech
     {
         @"(?<pool>({PoolStatMatchers})) per second to \k<pool> Leech rate",
         Reference.AsPoolStat.Leech.RateLimit
     },
     {
         "({DamageStatMatchers}) leeched as ({PoolStatMatchers})",
         References[1].AsPoolStat.Leech.Of(References[0].AsDamageStat)
     },
     {
         "({DamageStatMatchers}) leeched as ({PoolStatMatchers}) and ({PoolStatMatchers})",
         References[1].AsPoolStat.Leech.Of(References[0].AsDamageStat),
         References[2].AsPoolStat.Leech.Of(References[0].AsDamageStat)
     },
     {
         "damage dealt by your totems is leeched to you as life",
         Life.Leech.To(Entity.ModifierSource).Of(Damage), For(Entity.Totem)
     },
     { "({PoolStatMatchers}) leeched per second", Reference.AsPoolStat.Leech.Rate },
     // - block
     { "chance to block", Block.AttackChance },
     { "block chance", Block.AttackChance },
     { "maximum block chance", Block.AttackChance.Maximum },
     { "chance to block spells", Block.SpellChance },
     { "chance to block spells and attacks", ApplyOnce(Block.SpellChance, Block.AttackChance) },
     // - other
     { "chance to dodge attacks", Stat.Dodge.AttackChance },
     { "chance to dodge spell damage", Stat.Dodge.SpellChance },
     { "chance to evade( attacks)?", Evasion.Chance },
     { "chance to evade projectile attacks", Evasion.ChanceAgainstProjectileAttacks },
     { "chance to evade melee attacks", Evasion.ChanceAgainstMeleeAttacks },
     {
         "damage is taken from ({PoolStatMatchers}) before ({PoolStatMatchers})",
         Damage.TakenFrom(References[0].AsPoolStat).Before(References[1].AsPoolStat)
     },
     {
         "({DamageTypeMatchers}) damage is taken from ({PoolStatMatchers}) before ({PoolStatMatchers})",
         References[0].AsDamageType.Damage.TakenFrom(References[1].AsPoolStat)
         .Before(References[2].AsPoolStat)
     },
     // speed
     { "attack speed", Skills[Keyword.Attack].Speed },
     { "cast speed", Skills.Speed, Not(With(Skills[Keyword.Attack])) },
     { "movement speed", Stat.MovementSpeed },
     {
         // not the most elegant solution but by far the easiest
         @"movement speed \(hidden\)",
         Stat.MovementSpeed, Not(Flag.IgnoreMovementSpeedPenalties.IsSet)
     },
     { "attack and cast speed", Skills.Speed },
     { "attack, cast( speed)? and movement speed", ApplyOnce(Skills.Speed, Stat.MovementSpeed) },
     { "animation speed", Stat.AnimationSpeed },
     // regen and recharge
     { "({PoolStatMatchers}) regeneration rate", Reference.AsPoolStat.Regen },
     { "energy shield recharge rate", EnergyShield.Recharge },
     {
         "recovery rate of life, mana and energy shield",
         Life.RecoveryRate, Mana.RecoveryRate, EnergyShield.RecoveryRate
     },
     // gain
     // charges
     { "(?<!maximum )({ChargeTypeMatchers})", Reference.AsChargeType.Amount },
     { "(?<!while at )maximum ({ChargeTypeMatchers})", Reference.AsChargeType.Amount.Maximum },
     {
         "maximum ({ChargeTypeMatchers}) and maximum ({ChargeTypeMatchers})",
         ApplyOnce(References[0].AsChargeType.Amount.Maximum, References[1].AsChargeType.Amount.Maximum)
     },
     { "chance to (gain|grant) an? ({ChargeTypeMatchers})", Reference.AsChargeType.ChanceToGain },
     {
         "chance to (gain|grant) an? ({ChargeTypeMatchers}) and an? ({ChargeTypeMatchers})",
         References[0].AsChargeType.ChanceToGain, References[1].AsChargeType.ChanceToGain
     },
     { "({ChargeTypeMatchers}) duration", Reference.AsChargeType.Duration },
     {
         "endurance, frenzy and power charge duration",
         Charge.Endurance.Duration, Charge.Frenzy.Duration, Charge.Power.Duration
     },
     // skills
     { "cooldown recovery speed", Skills.CooldownRecoverySpeed },
     { "mana cost( of skills)?", Skills.Cost },
     { "skill effect duration", Skills.Duration },
     { "mana reserved", Skills.Reservation },
     { "({KeywordMatchers}) duration", Skills[Reference.AsKeyword].Duration },
     // traps, mines, totems
     { "traps? placed at a time", Traps.CombinedInstances.Maximum },
     { "remote mines? placed at a time", Mines.CombinedInstances.Maximum },
     { "totems? summoned at a time", Totems.CombinedInstances.Maximum },
     { "trap trigger area of effect", Stat.TrapTriggerAoE },
     { "mine detonation area of effect", Stat.MineDetonationAoE },
     { "trap throwing speed", Traps.Speed },
     { "mine laying speed", Mines.Speed },
     { "totem placement speed", Totems.Speed },
     { "totem life", Life, For(Entity.Totem) },
     // minions
     {
         "maximum number of skeletons",
         Combine(Skill.SummonSkeleton, Skill.VaalSummonSkeletons).CombinedInstances.Maximum
     },
     { "maximum number of spectres", Skill.RaiseSpectre.Instances.Maximum },
     { "maximum number of zombies", Skill.RaiseZombie.Instances.Maximum },
     { "skeleton duration", Skill.SummonSkeleton.Duration, Skill.VaalSummonSkeletons.Duration },
     { "golem at a time", Golems.CombinedInstances.Maximum },
     // buffs
     { "effect of buffs granted by your golems", Buffs(Entity.Minion.With(Keyword.Golem)).Effect },
     {
         "effect of buffs granted by your elemental golems",
         Buffs(Entity.Minion.With(Keyword.Golem, Elemental)).Effect
     },
     { "effect of your curses", Buffs(Self).With(Keyword.Curse).Effect },
     { "effect of curses on you", Buffs(target: Self).With(Keyword.Curse).Effect },
     { "effect of non-curse auras you cast", Buffs(Self).With(Keyword.Aura).Without(Keyword.Curse).Effect },
     { "chance to fortify", Buff.Fortify.ChanceOn(Self) },
     { "effect of fortify on you", Buff.Fortify.Effect },
     { "fortify duration", Buff.Fortify.Duration },
     { "chance for attacks to maim", Buff.Maim.ChanceOn(Enemy), Damage.With(Source.Attack) },
     { "chance to taunt", Buff.Taunt.ChanceOn(Enemy) },
     { "taunt duration", Buff.Taunt.Duration },
     { "chance to blind enemies", Buff.Blind.ChanceOn(Enemy) },
     { "blind duration", Buff.Blind.Duration },
     // flags
     {
         "chance to (gain|grant) ({FlagMatchers})",
         Reference.AsFlagStat     // chance is handled by StatManipulationMatchers
     },
     { "({FlagMatchers}) duration", Reference.AsFlagStat.Duration },
     { "({FlagMatchers}) effect", Reference.AsFlagStat.Effect },
     // ailments
     { "chance to ({AilmentMatchers})( the enemy)?", Reference.AsAilment.Chance },
     {
         "chance to freeze, shock and ignite",
         Ailment.Freeze.Chance, Ailment.Shock.Chance, Ailment.Ignite.Chance
     },
     { "chance to avoid being ({AilmentMatchers})", Reference.AsAilment.Avoidance },
     { "chance to avoid elemental ailments", Ailment.Elemental.Select(a => a.Avoidance) },
     { "({AilmentMatchers}) duration( on enemies)?", Reference.AsAilment.Duration },
     { "duration of elemental ailments on enemies", Ailment.Elemental.Select(a => a.Duration) },
     // stun
     { "chance to avoid being stunned", Effect.Stun.Avoidance },
     { "stun and block recovery", Effect.Stun.Recovery, Block.Recovery },
     { "block recovery", Block.Recovery },
     { "stun threshold", Effect.Stun.Threshold },
     { "enemy stun threshold", Enemy.Stat(Effect.Stun.Threshold) },
     { "stun duration( on enemies)?", Enemy.Stat(Effect.Stun.Duration) },
     { "stun duration (?<inner>with .*) on enemies", Enemy.Stat(Effect.Stun.Duration), "${inner}" },
     {
         "chance to avoid interruption from stuns while casting",
         Effect.Stun.ChanceToAvoidInterruptionWhileCasting
     },
     { "chance to double stun duration", Effect.Stun.Duration.ChanceToDouble },
     // flasks
     { "effect of flasks( on you)?", Flask.Effect },
     { "flask effect duration", Flask.Duration },
     { "life recovery from flasks", Flask.LifeRecovery },
     { "mana recovery from flasks", Flask.ManaRecovery },
     { "flask charges used", Flask.ChargesUsed },
     { "flask charges gained", Flask.ChargesGained },
     { "flask recovery (speed|rate)", Flask.RecoverySpeed },
     // item quantity/quality
     { "quantity of items found", Stat.ItemQuantity },
     { "rarity of items found", Stat.ItemRarity },
     // range and area of effect
     { "area of effect", Skills.AreaOfEffect },
     { "melee weapon and unarmed range", Stat.Range, Not(MainHand.Has(Tags.Ranged)) },
     { "melee weapon range", Stat.Range, And(MainHand.Has(Tags.Weapon), Not(MainHand.Has(Tags.Ranged))) },
     // other
     { "rampage stacks", Stat.RampageStacks },
     { "chance to knock enemies back", Effect.Knockback.ChanceOn(Enemy) },
     { "knockback distance", Effect.Knockback.Distance },
     // Not really anything that can be done with them (yet), but should still be summed up
     { "character size", Stat.Unique("Character Size") },
     { "reflected elemental damage taken", Stat.Unique("Reduced Reflected Elemental Damage taken") },
     { "reflected physical damage taken", Stat.Unique("Reduced Reflected Physical Damage taken") },
     {
         "damage taken gained as mana over 4 seconds when hit",
         Stat.Unique("#% of Damage taken gained as Mana over 4 seconds when Hit")
     },
     { "light radius", Stat.Unique("Light Radius") },
 };
Ejemplo n.º 21
0
        public void Elemental_Constructor_Water()
        {
            elemental = new Elemental(ElementType.Water);

            Assert.AreEqual("water", elemental.KeyWords[0]);
        }
Ejemplo n.º 22
0
        public void Elemental_Constructor_Fire()
        {
            elemental = new Elemental(ElementType.Fire);

            Assert.AreEqual("fire", elemental.KeyWords[0]);
        }
Ejemplo n.º 23
0
 private void Start()
 {
     input     = GetComponent <IWeaponInput>();
     elemental = GetComponent <Elemental>();
 }
Ejemplo n.º 24
0
 public CombatAttributes(Decimal Fire, Decimal Ice, Decimal Air, Decimal Earth, Decimal Slashing, Decimal Bashing, Decimal Piercing)
 {
     elements = new Elemental(Fire, Ice, Air, Earth);
     normal = new Normal(Slashing, Bashing, Piercing);
 }
Ejemplo n.º 25
0
 public Rune(Elemental elemental)
 {
     this.elemental = elemental;
 }
Ejemplo n.º 26
0
 public CombatAttributes()
 {
     elements = new Elemental(0, 0, 0, 0);
     normal = new Normal(0, 0, 0);
 }
 public static float getElementPower(Elemental attaker, Elemental defender)
 {
     float ret = 1f;
     switch (attaker) {
         case Elemental.AIR:
             if (defender == Elemental.FIRE)
             {
                 ret = tolerant;
             }
             else if (defender == Elemental.EARTH)
             {
                 ret = weakness;
             }
             else if (defender == Elemental.DARK || defender == Elemental.LIGHT)
             {
                 ret = tolerant_lightdark;
             }
             else if (defender == Elemental.ETHER) {
                 ret = tolerant_ehter;
             }
             break;
         case Elemental.DARK:
             if (defender == Elemental.LIGHT)
             {
                 ret = weakness;
             }
             else if (defender != Elemental.ETHER) {
                 ret = weakness_lightdark;
             }
             break;
         case Elemental.EARTH:
             if (defender == Elemental.FIRE)
             {
                 ret = tolerant;
             }
             else if (defender == Elemental.EARTH)
             {
                 ret = weakness;
             }
             else if (defender == Elemental.DARK || defender == Elemental.LIGHT)
             {
                 ret = tolerant_lightdark;
             }
             else if (defender == Elemental.ETHER)
             {
                 ret = tolerant_ehter;
             }
             break;
         case Elemental.ETHER:
             if (defender == Elemental.ETHER)
             {
                 ret = weakness;
             }
             else {
                 ret = weakness_ehter;
             }
             break;
         case Elemental.FIRE:
             if (defender == Elemental.WATER)
             {
                 ret = tolerant;
             }
             else if (defender == Elemental.AIR)
             {
                 ret = weakness;
             }
             else if (defender == Elemental.DARK || defender == Elemental.LIGHT)
             {
                 ret = tolerant_lightdark;
             }
             else if (defender == Elemental.ETHER)
             {
                 ret = tolerant_ehter;
             }
             break;
         case Elemental.LIGHT:
             if (defender == Elemental.DARK)
             {
                 ret = weakness;
             }
             else if (defender != Elemental.ETHER) {
                 ret = weakness_lightdark;
             }
             break;
         case Elemental.WATER:
             if (defender == Elemental.EARTH)
             {
                 ret = tolerant;
             }
             else if (defender == Elemental.FIRE)
             {
                 ret = weakness;
             }
             else if (defender == Elemental.DARK || defender == Elemental.LIGHT)
             {
                 ret = tolerant_lightdark;
             }
             else if (defender == Elemental.ETHER)
             {
                 ret = tolerant_ehter;
             }
             break;
         case Elemental.NONE:
             if (defender == Elemental.DARK || defender == Elemental.LIGHT)
             {
                 ret = tolerant_lightdark;
             }
             else if (defender == Elemental.ETHER)
             {
                 ret = tolerant_ehter;
             }
             break;
     }
     return ret;
 }
Ejemplo n.º 28
0
 private int GetElemStrength(int strength, Elemental elem, int row, int col)
 {
     if (Rules.HasFlag(Rules.Elemental))
     {
         return strength + ElementsOnBoard[row, col] == elem ? 1 : -1;
     }
     return strength;
 }
Ejemplo n.º 29
0
        public void Elemental_Constructor_Earth()
        {
            elemental = new Elemental(ElementType.Earth);

            Assert.AreEqual("earth", elemental.KeyWords[0]);
        }
Ejemplo n.º 30
0
    public void Initialize()
    {
        uiActionContainer = CombatFlow.cl.uiActionContainer;

        //utilisation du viewport de la camera pour placer les characters
        playerStartingPosition = CombatFlow.cl.camera.ViewportToWorldPoint(new Vector2(.2f, .5f));
        ennemiStartingPosition = CombatFlow.cl.camera.ViewportToWorldPoint(new Vector2(.8f, .5f));

        playerHp   = CombatFlow.cl.playerHp;             //pointeur vers le composant text des HP du joueur
        playerMana = CombatFlow.cl.playerMana;           //pointeur vers le composant text de la mana du joueur
        ennemiHP   = CombatFlow.cl.ennemiHP;             //pointeur vers le composant text des HP de l'ennemi
        ennemiMana = CombatFlow.cl.ennemiMana;           //pointeur vers le composant text de la mana de l'ennemi

        playerHpImage   = CombatFlow.cl.playerHpImage;   //pointeur vers le composant image des HP du joueur
        playerManaImage = CombatFlow.cl.playerManaImage; //pointeur vers le composant image de la mana du joueur
        ennemiHPImage   = CombatFlow.cl.ennemiHPImage;   //pointeur vers le composant image des HP de l'ennemi
        ennemiManaImage = CombatFlow.cl.ennemiManaImage; //pointeur vers le composant image de la mana de l'ennemi
        playerImage     = CombatFlow.cl.playerImage;     //pointeur vers le composant image du portrait du joueur
        ennemiImage     = CombatFlow.cl.ennemiImage;     //pointeur vers le composant image du portrait de l'ennemi

        switch (OmniPlayer.Instance.characterClass)
        {
        case CharacterClasses.Warrior:
            player             = new Warrior();
            playerImage.sprite = GameObject.Instantiate <Sprite>(Resources.Load <Sprite>("Sprites/Gladiator_Portrait"));
            playerObj          = GameObject.Instantiate <GameObject>(Resources.Load <GameObject>("Prefabs/Warrior"));
            break;

        case CharacterClasses.Wizard:
            player             = new Wizard();
            playerImage.sprite = GameObject.Instantiate <Sprite>(Resources.Load <Sprite>("Sprites/Wizards_Portrait"));
            playerObj          = GameObject.Instantiate <GameObject>(Resources.Load <GameObject>("Prefabs/Wizard"));
            break;

        default:
            Debug.Log("Unhandeled character class : " + player.characterClass);
            break;
        }
        CombatFlow.cl.PlayerCharacter = ChargerPlayer(player);

        switch (OmniEnemy.Instance.characterClass)
        {
        case CharacterClasses.Orc:
            ennemi             = new Orc();
            ennemiImage.sprite = GameObject.Instantiate <Sprite>(Resources.Load <Sprite>("Sprites/Orc_Portrait"));
            ennemiObj          = GameObject.Instantiate <GameObject>(Resources.Load <GameObject>("Prefabs/Orc"));
            break;

        case CharacterClasses.Elemental:
            ennemi             = new Elemental();
            ennemiImage.sprite = GameObject.Instantiate <Sprite>(Resources.Load <Sprite>("Sprites/Elemental_Portrait"));
            ennemiObj          = GameObject.Instantiate <GameObject>(Resources.Load <GameObject>("Prefabs/Elemental"));
            break;

        case CharacterClasses.Boss:
            ennemi             = new Boss();
            ennemiImage.sprite = GameObject.Instantiate <Sprite>(Resources.Load <Sprite>("Sprites/Golem_Portrait"));
            ennemiObj          = GameObject.Instantiate <GameObject>(Resources.Load <GameObject>("Prefabs/Boss"));
            break;

        default:
            Debug.Log("Unhandeled character class : " + player.characterClass);
            break;
        }
        CombatFlow.cl.EnemyCharacter = ennemi;


        playerObj.transform.position    = CombatFlow.cl.playerPosition = playerStartingPosition;
        playerObj.transform.localScale *= CHARACTER_SIZE;
        playerAnimator = playerObj.GetComponent <Animator>();

        ennemiObj.transform.position    = ennemiStartingPosition;
        ennemiObj.transform.localScale *= CHARACTER_SIZE;
        ennemiAnimator = ennemiObj.GetComponent <Animator>();

        playerEffect = playerObj.GetComponentsInChildren <ParticleSystem>();
        ennemiEffect = playerObj.GetComponentsInChildren <ParticleSystem>();
    }
Ejemplo n.º 31
0
 protected override IReadOnlyList <MatcherData> CreateCollection() =>
 new StatMatcherCollection <IStatBuilder>(_modifierBuilder)
 {
     // attributes
     { "strength", Attribute.Strength },
     { "strength damage bonus", Attribute.StrengthDamageBonus },
     { "dexterity", Attribute.Dexterity },
     { "dexterity evasion bonus", Attribute.DexterityEvasionBonus },
     { "intelligence", Attribute.Intelligence },
     { "strength and dexterity", ApplyOnce(Attribute.Strength, Attribute.Dexterity) },
     { "strength and intelligence", ApplyOnce(Attribute.Strength, Attribute.Intelligence) },
     { "dexterity and intelligence", ApplyOnce(Attribute.Dexterity, Attribute.Intelligence) },
     { "(all )?attributes", ApplyOnce(Attribute.Strength, Attribute.Dexterity, Attribute.Intelligence) },
     // offense
     // - damage: see also DamageStatMatchers
     { "chance to deal double damage", Damage.ChanceToDouble },
     // - damage multiplier
     {
         "({DamageTypeMatchers}) damage over time multiplier",
         Reference.AsDamageType.DamageMultiplier.With(DamageSource.OverTime)
     },
     {
         "non-ailment ({DamageTypeMatchers}) damage over time multiplier",
         Reference.AsDamageType.DamageMultiplier.WithSkills(DamageSource.OverTime)
     },
     // - damage taken
     { "damage taken", Damage.Taken },
     { "({DamageTypeMatchers}) damage taken", Reference.AsDamageType.Damage.Taken },
     { "take ({DamageTypeMatchers}) damage", Reference.AsDamageType.Damage.Taken },
     { "damage taken from hits", Damage.Taken.WithHits },
     { "({DamageTypeMatchers}) damage taken from hits", Reference.AsDamageType.Damage.Taken.WithHits },
     { "damage taken from damage over time", Damage.Taken.With(DamageSource.OverTime) },
     {
         "({DamageTypeMatchers}) damage taken over time",
         Reference.AsDamageType.Damage.Taken.With(DamageSource.OverTime)
     },
     {
         "take ({DamageTypeMatchers}) damage over time",
         Reference.AsDamageType.Damage.Taken.With(DamageSource.OverTime)
     },
     { "damage taken from projectiles", Damage.Taken.With(Keyword.Projectile) },
     {
         "damage taken from trap or mine hits",
         Damage.Taken.With(Keyword.Trap).WithHits, Damage.Taken.With(Keyword.Mine).WithHits
     },
     // - damage taken as
     {
         "({DamageTypeMatchers}) damage from hits taken as lightning damage",
         Reference.AsDamageType.HitDamageTakenAs(DamageType.Lightning)
     },
     {
         "({DamageTypeMatchers}) damage from hits taken as cold damage",
         Reference.AsDamageType.HitDamageTakenAs(DamageType.Cold)
     },
     {
         "({DamageTypeMatchers}) damage from hits taken as fire damage",
         Reference.AsDamageType.HitDamageTakenAs(DamageType.Fire)
     },
     {
         "({DamageTypeMatchers}) damage from hits taken as chaos damage",
         Reference.AsDamageType.HitDamageTakenAs(DamageType.Chaos)
     },
     // - penetration
     // - crit
     { "(global )?critical strike multiplier", CriticalStrike.Multiplier.WithSkills },
     { "(global )?critical strike chance", CriticalStrike.Chance },
     {
         "({KeywordMatchers}) critical strike multiplier",
         CriticalStrike.Multiplier.WithSkills.With(Reference.AsKeyword)
     },
     { "({KeywordMatchers}) critical strike chance", CriticalStrike.Chance.With(Reference.AsKeyword) },
     { "projectiles have critical strike chance", CriticalStrike.Chance.With(Keyword.Projectile) },
     // - projectiles
     { "projectile speed", Projectile.Speed },
     { "arrow speed", Projectile.Speed, And(With(Keyword.Attack), MainHand.Has(Tags.Bow)) },
     // - other
     { "(global )?accuracy rating", Stat.Accuracy },
     { "minion accuracy rating", Stat.Accuracy.For(Entity.Minion) },
     // defense
     // - life, mana, defences; see also PoolStatMatchers
     { "armour", Armour },
     { "evasion( rating)?", Evasion },
     { "evasion rating and armour", ApplyOnce(Armour, Evasion) },
     { "armour and evasion( rating)?", ApplyOnce(Armour, Evasion) },
     { "armour and energy shield", ApplyOnce(Armour, EnergyShield) },
     { "(global )?defences", ApplyOnce(Armour, Evasion, EnergyShield) },
     { "minion maximum life", Life.For(Entity.Minion) },
     // - resistances
     { "({DamageTypeMatchers}) resistance", Reference.AsDamageType.Resistance },
     {
         "({DamageTypeMatchers}) and ({DamageTypeMatchers}) resistances",
         References[0].AsDamageType.Resistance, References[1].AsDamageType.Resistance
     },
     { "all elemental resistances", Elemental.Resistance },
     { "maximum ({DamageTypeMatchers}) resistance", Reference.AsDamageType.Resistance.Maximum },
     { "all maximum resistances", Elemental.And(Chaos).Resistance.Maximum },
     { "physical damage reduction", Physical.Resistance },
     // - leech
     {
         @"(?<pool>({PoolStatMatchers})) per second to \k<pool> Leech rate",
         Reference.AsPoolStat.Leech.RateLimit
     },
     {
         "damage leeched as ({PoolStatMatchers})",
         Reference.AsPoolStat.Leech.Of(Damage)
     },
     {
         "attack damage leeched as ({PoolStatMatchers})",
         Reference.AsPoolStat.Leech.Of(Damage.With(DamageSource.Attack))
     },
     {
         "spell damage leeched as ({PoolStatMatchers})",
         Reference.AsPoolStat.Leech.Of(Damage.With(DamageSource.Spell))
     },
     {
         "({DamageTypeMatchers}) damage leeched as ({PoolStatMatchers})",
         References[1].AsPoolStat.Leech.Of(References[0].AsDamageType.Damage)
     },
     {
         "({DamageTypeMatchers}) attack damage leeched as ({PoolStatMatchers})",
         References[1].AsPoolStat.Leech.Of(References[0].AsDamageType.Damage.With(DamageSource.Attack))
     },
     {
         "damage leeched as ({PoolStatMatchers}) and ({PoolStatMatchers})",
         References[0].AsPoolStat.Leech.Of(Damage), References[1].AsPoolStat.Leech.Of(Damage)
     },
     {
         "attack damage leeched as ({PoolStatMatchers}) and ({PoolStatMatchers})",
         References[0].AsPoolStat.Leech.Of(Damage.With(DamageSource.Attack)),
         References[1].AsPoolStat.Leech.Of(Damage.With(DamageSource.Attack))
     },
     {
         "damage dealt by your totems is leeched to you as life",
         Life.Leech.Of(Damage.For(Entity.Totem))
     },
     { "({PoolStatMatchers}) leeched per second", Reference.AsPoolStat.Leech.Rate },
     // - block
     { "chance to block", Block.AttackChance },
     { "chance to block attack damage", Block.AttackChance },
     { "chance to block spell damage", Block.SpellChance },
     { "chance to block spell and attack damage", Block.SpellChance, Block.AttackChance },
     { "enemy block chance", ApplyOnce(Block.SpellChance, Block.AttackChance).For(Enemy) },
     { "maximum chance to block attack damage", Block.AttackChance.Maximum },
     // - other
     { "chance to dodge attacks", Stat.Dodge.AttackChance },
     { "chance to dodge attack hits", Stat.Dodge.AttackChance },
     { "chance to dodge spell hits", Stat.Dodge.SpellChance },
     { "chance to dodge attack and spell hits", Stat.Dodge.AttackChance, Stat.Dodge.SpellChance },
     {
         "enemies have chance to dodge hits",
         ApplyOnce(Stat.Dodge.AttackChance, Stat.Dodge.SpellChance).For(Enemy)
     },
     { "chance to evade( attacks)?", Evasion.Chance },
     { "chance to evade projectile attacks", Evasion.ChanceAgainstProjectileAttacks },
     { "chance to evade melee attacks", Evasion.ChanceAgainstMeleeAttacks },
     {
         "damage is taken from ({PoolStatMatchers}) before ({PoolStatMatchers})",
         AnyDamageType.DamageTakenFrom(References[0].AsPoolStat).Before(References[1].AsPoolStat)
     },
     {
         "({DamageTypeMatchers}) damage is taken from ({PoolStatMatchers}) before ({PoolStatMatchers})",
         References[0].AsDamageType.DamageTakenFrom(References[1].AsPoolStat)
         .Before(References[2].AsPoolStat)
     },
     // speed
     { "attack speed", Stat.CastRate.With(DamageSource.Attack) },
     {
         "({KeywordMatchers}) attack speed",
         Stat.CastRate.With(DamageSource.Attack).With(Reference.AsKeyword)
     },
     { "cast speed", Stat.CastRate.With(DamageSource.Spell), Stat.CastRate.With(DamageSource.Secondary) },
     { "cast speed for curses", Stat.CastRate.With(DamageSource.Attack).With(Keyword.Curse) },
     { "movement speed", Stat.MovementSpeed },
     {
         // not the most elegant solution but by far the easiest
         @"movement speed \(hidden\)",
         Stat.MovementSpeed, Not(Flag.IgnoreMovementSpeedPenalties.IsSet)
     },
     { "attack and cast speed", Stat.CastRate },
     { "attack, cast( speed)? and movement speed", Stat.CastRate, Stat.MovementSpeed },
     { "hit rate", Stat.HitRate },
     { "brand activation frequency", Stat.HitRate, With(Keyword.Brand) },
     // regen and recharge
     { "({PoolStatMatchers}) regeneration rate", Reference.AsPoolStat.Regen },
     { "energy shield recharge rate", EnergyShield.Recharge },
     {
         "recovery rate of life, mana and energy shield",
         Life.RecoveryRate, Mana.RecoveryRate, EnergyShield.RecoveryRate
     },
     // gain
     // charges
     { "(?<!maximum |have an? )({ChargeTypeMatchers})", Reference.AsChargeType.Amount },
     { "(?<!while at )maximum ({ChargeTypeMatchers})", Reference.AsChargeType.Amount.Maximum },
     {
         "maximum ({ChargeTypeMatchers}) and maximum ({ChargeTypeMatchers})",
         ApplyOnce(References[0].AsChargeType.Amount.Maximum, References[1].AsChargeType.Amount.Maximum)
     },
     { "chance to (gain|grant) (an?|1) ({ChargeTypeMatchers})", Reference.AsChargeType.ChanceToGain },
     {
         "chance to (gain|grant) an? ({ChargeTypeMatchers}) and an? ({ChargeTypeMatchers})",
         References[0].AsChargeType.ChanceToGain, References[1].AsChargeType.ChanceToGain
     },
     {
         // Isn't really useful to parse, but if not, no damage related stat would be parsed, leading to
         // a ParseException because this is "on Hit with Claws".
         "chance to steal power, frenzy, and endurance charges",
         Charge.ChanceToSteal
     },
     { "({ChargeTypeMatchers}) duration", Reference.AsChargeType.Duration },
     {
         "endurance, frenzy and power charge duration",
         Charge.Endurance.Duration, Charge.Frenzy.Duration, Charge.Power.Duration
     },
     // skills
     { "cooldown recovery speed", Stat.CooldownRecoverySpeed },
     { "warcry cooldown recovery speed", Stat.CooldownRecoverySpeed, With(Keyword.Warcry) },
     { "cooldown recovery speed for throwing traps", Stat.CooldownRecoverySpeed, With(Keyword.Trap) },
     { "mana cost( of skills)?", Mana.Cost },
     {
         "mana cost of skills that place mines or throw traps",
         Mana.Cost, Or(With(Keyword.Mine), With(Keyword.Trap))
     },
     { "mana reserved", AllSkills.Reservation },
     { "mana reservation of skills", AllSkills.Reservation },
     { "mana reservation of ({KeywordMatchers}) skills", Skills[Reference.AsKeyword].Reservation },
     { "({SkillMatchers}) has mana reservation", Reference.AsSkill.Reservation },
     { "skill effect duration", Stat.Duration },
     { "skill duration", Stat.Duration },
     { "buff duration", Stat.Duration },
     { "warcry duration", Stat.Duration, With(Keyword.Warcry) },
     { "curse duration", Stat.Duration, With(Keyword.Curse) },
     // traps, mines, totems
     { "trap duration", Stat.Trap.Duration },
     { "mine duration", Stat.Mine.Duration },
     { "totem duration", Stat.Totem.Duration },
     { "traps? placed at a time", Traps.CombinedInstances.Maximum },
     { "remote mines? placed at a time", Mines.CombinedInstances.Maximum },
     { "totems? summoned at a time", Totems.CombinedInstances.Maximum },
     { "maximum number of summoned totems", Totems.CombinedInstances.Maximum },
     { "trap trigger area of effect", Stat.Trap.TriggerAoE },
     { "mine detonation area of effect", Stat.Mine.DetonationAoE },
     { "trap throwing speed", Stat.Trap.Speed },
     { "mine laying speed", Stat.Mine.Speed },
     { "totem placement speed", Stat.Totem.Speed },
     { "totem life", Life.For(Entity.Totem) },
     // minions
     {
         "maximum number of skeletons",
         Skills.SummonSkeleton.Instances.Maximum, Skills.VaalSummonSkeletons.Instances.Maximum
     },
     { "maximum number of spectres", Skills.RaiseSpectre.Instances.Maximum },
     { "maximum number of zombies", Skills.RaiseZombie.Instances.Maximum },
     { "minion duration", Stat.Duration, With(Keyword.Minion) },
     { "skeleton duration", Stat.Duration, WithSkeletonSkills },
     { "skeleton movement speed", Stat.MovementSpeed.For(Entity.Minion), WithSkeletonSkills },
     { "golem at a time", Golems.CombinedInstances.Maximum },
     // buffs
     // - effect
     { "({BuffMatchers}) effect", Reference.AsBuff.Effect },
     { "effect of ({BuffMatchers})", Reference.AsBuff.Effect },
     { "effect of ({BuffMatchers}) on you", Reference.AsBuff.EffectOn(Self) },
     { "({SkillMatchers}) has buff effect", Reference.AsSkill.Buff.Effect },
     { "effect of buffs granted by your golems", Buffs(Entity.Minion).With(Keyword.Golem).Effect },
     {
         "effect of buffs granted by your elemental golems",
         Buffs(Entity.Minion).With(Keyword.Golem, Fire).Effect,
         Buffs(Entity.Minion).With(Keyword.Golem, Cold).Effect,
         Buffs(Entity.Minion).With(Keyword.Golem, Lightning).Effect
     },
     { "effect of heralds on you", Buffs(targets: Self).With(Keyword.Herald).Effect },
     { "effect of your curses", Buffs(Self).With(Keyword.Curse).Effect },
     { "effect of curses on you", Buffs(targets: Self).With(Keyword.Curse).Effect },
     {
         "effect of non-curse auras from your skills",
         Buffs(Self).With(Keyword.Aura).Without(Keyword.Curse).Effect
     },
     { "warcry buff effect", Buffs(targets: Self).With(Keyword.Warcry).Effect },
     { "aura effect", Skills.ModifierSourceSkill.Buff.Effect },
     { "(?<!area of )effect of aura", Skills.ModifierSourceSkill.Buff.Effect },
     { "effect of supported curses", Skills.ModifierSourceSkill.Buff.Effect },
     { "non-curse auras from supported skills have effect", Skills.ModifierSourceSkill.Buff.Effect },
     { "effect of curse against players", Skills.ModifierSourceSkill.Buff.EffectOn(Entity.Character) },
     // - chance
     { "chance to (gain|grant) ({BuffMatchers})", Reference.AsBuff.Chance },
     { "chance to fortify", Buff.Fortify.Chance },
     { "chance to maim", Buff.Maim.Chance },
     { "chance for attacks to maim", Buff.Maim.Chance.With(DamageSource.Attack) },
     { "chance to taunt", Buff.Taunt.Chance },
     { "chance to blind( enemies)?", Buff.Blind.Chance },
     { "chance to cover rare or unique enemies in ash", Buff.CoveredInAsh.Chance, Enemy.IsRareOrUnique },
     { "chance to impale enemies", Buff.Impale.Chance },
     // - duration
     { "({BuffMatchers}) duration", Reference.AsBuff.Duration },
     { "blinding duration", Buff.Blind.Duration },
     // ailments
     { "chance to ({AilmentMatchers})( the enemy| enemies)?( on hit)?", Reference.AsAilment.Chance },
     {
         "chance to freeze, shock and ignite",
         Ailment.Freeze.Chance, Ailment.Shock.Chance, Ailment.Ignite.Chance
     },
     { "chance to cause bleeding( on hit)?", Ailment.Bleed.Chance.With(DamageSource.Attack) },
     { "chance to avoid being ({AilmentMatchers})", Reference.AsAilment.Avoidance },
     { "chance to avoid elemental ailments", Ailment.Elemental.Select(a => a.Avoidance) },
     { "({AilmentMatchers}) duration( on enemies)?", Reference.AsAilment.Duration },
     {
         "duration of ailments on enemies",
         Ailment.Elemental.Append(Ailment.Bleed, Ailment.Poison).Select(a => a.Duration)
     },
     { "duration of elemental ailments on enemies", Ailment.Elemental.Select(a => a.Duration) },
     { "effect of shock", Ailment.ShockEffect },
     { "effect of chill( on enemies)?", Ailment.ChillEffect },
     { "effect of non-damaging ailments on enemies", Ailment.ShockEffect, Ailment.ChillEffect },
     // stun
     { "chance to avoid being stunned", Effect.Stun.Avoidance },
     { "stun and block recovery", Effect.Stun.Recovery, Block.Recovery },
     { "block recovery", Block.Recovery },
     { "stun threshold", Effect.Stun.Threshold },
     { "enemy stun threshold", Effect.Stun.Threshold.For(Enemy) },
     { "stun duration( on enemies)?", Effect.Stun.Duration },
     { "stun duration (?<inner>with .*) on enemies", Effect.Stun.Duration, "${inner}" },
     {
         "chance to avoid interruption from stuns while casting",
         Effect.Stun.ChanceToAvoidInterruptionWhileCasting
     },
     { "chance to double stun duration", Effect.Stun.Duration.ChanceToDouble },
     // flasks
     { "effect of flasks( on you)?", Flask.Effect },
     { "flask effect duration", Flask.Duration },
     { "life recovery from flasks", Flask.LifeRecovery },
     { "mana recovery from flasks", Flask.ManaRecovery },
     { "flask charges used", Flask.ChargesUsed },
     { "flask charges gained", Flask.ChargesGained },
     { "flask recovery (speed|rate)", Flask.RecoverySpeed },
     // item quantity/quality
     { "quantity of items found", Stat.ItemQuantity },
     { "quantity of items dropped by enemies slain", Stat.ItemQuantity },
     { "rarity of items found", Stat.ItemRarity },
     { "rarity of items dropped by enemies slain", Stat.ItemRarity },
     // range and area of effect
     { "area of effect", Stat.AreaOfEffect },
     { "aura area of effect", Stat.AreaOfEffect, With(Keyword.Aura) },
     { "radius", Stat.Radius },
     { "explosion radius", Stat.Radius },
     { "melee weapon and unarmed( attack)? range", Stat.Range.With(Keyword.Melee) },
     { "melee range", Stat.Range.With(Keyword.Melee) },
     { "melee weapon range", Stat.Range.With(Keyword.Melee), MainHand.HasItem },
     // other
     { "rampage stacks", Stat.RampageStacks },
     { "chance to knock enemies back", Effect.Knockback.Chance },
     { "knockback distance", Effect.Knockback.Distance },
     { "character size", Stat.CharacterSize },
     { "reflected elemental damage taken", Elemental.ReflectedDamageTaken },
     { "reflected physical damage taken", Physical.ReflectedDamageTaken },
     { "damage taken gained as mana over 4 seconds when hit", Stat.DamageTakenGainedAsMana },
     { "light radius", Stat.LightRadius },
 };