Ejemplo n.º 1
0
        /* Spell data is computed in the following stages:
         * 1. SpellData with constants
         * 2. ComputedSpell containing computed data for a generic target (thus excluding crit, mastery, targets, effective healing)
         * 3. ComputedSpell with RaidAction and TankAction filled with information except effective healing and multiplication by number of targets
         * 4. SpellAction adding effective healing, targets and strange options, plus special SpellActions containing combination of spells
         * 5. Actions containing the SpellActions converted to EPS/MPS/time format
         * 
         * Note that Tank mostly means "target always with hots, hit frequently" while Raid means "target which might have hots (from wild growth), hit rarely"
         */

        ComputedSpell[] computeDivisionSpells(TreeStats stats, TreeComputedData data)
        {
            ComputedSpell[] spells = new ComputedSpell[(int)TreeSpell.Count];
            for (int i = 0; i < (int)TreeSpell.Count; ++i)
            {
                SpellData spdata = CalculationsTree.SpellData[i];
                if(i == (int)TreeSpell.WildGrowth && opts.WildGrowthNerf)
                    spdata = CalculationsTree.NerfedWildGrowthSpellData;
                spells[i] = new ComputedSpell(spdata, stats);
            }

            spells[(int)TreeSpell.Tranquility].DirectMultiplier *= 4 * 5;
            spells[(int)TreeSpell.Tranquility].TickMultiplier *= 4 * 5;

            #region Talents
            double rejuvenationInstantTicks = 0;

            spells[(int)TreeSpell.Swiftmend].ExtraDirectBonus += 0.02f * Talents.Genesis;

            spells[(int)TreeSpell.Rejuvenation].ExtraTickBonus += Talents.BlessingOfTheGrove * 0.02f;

            spells[(int)TreeSpell.Nourish].TimeReductionMS += 250 * Talents.Naturalist;
            spells[(int)TreeSpell.HealingTouch].TimeReductionMS += 250 * Talents.Naturalist;

            spells[(int)TreeSpell.Rejuvenation].ExtraTickBonus += 0.05f * Talents.ImprovedRejuvenation;
            spells[(int)TreeSpell.Swiftmend].ExtraTickBonus += 0.05f * Talents.ImprovedRejuvenation;
            spells[(int)TreeSpell.Swiftmend].ExtraDirectBonus += 0.05f * Talents.ImprovedRejuvenation;

            // according to Paragon's Anaram posting on ElitistJerks, Efflorescence double-dips Master Shapeshifter and Harmony
            spells[(int)TreeSpell.Swiftmend].TickMultiplier *= 0.04f * Talents.Efflorescence * (1.0f + Talents.MasterShapeshifter * 0.04f) * (1.0f + stats.Harmony);

            spells[(int)TreeSpell.Nourish].ExtraDirectBonus += 0.05f * Talents.EmpoweredTouch;
            spells[(int)TreeSpell.HealingTouch].ExtraDirectBonus += 0.05f * Talents.EmpoweredTouch;
            spells[(int)TreeSpell.Regrowth].ExtraDirectBonus += 0.05f * Talents.EmpoweredTouch;

            // formula from TreeCalcs
            // TODO: test this in-game
            rejuvenationInstantTicks = Talents.GiftOfTheEarthmother * 0.05f * Math.Floor(4.0f * (1 + StatConversion.GetSpellHasteFromRating((float)stats.Haste.HasteRating)) + 0.5f) * 1.0135f;
            spells[(int)TreeSpell.Lifebloom].DirectMultiplier *= 1 + Talents.GiftOfTheEarthmother * 0.05f;

            if (Talents.SwiftRejuvenation > 0)
                spells[(int)TreeSpell.Rejuvenation].TimeReductionMS = 500;
            #endregion

            #region Glyphs
            if (Talents.GlyphOfRejuvination)
                spells[(int)TreeSpell.Rejuvenation].ExtraTickBonus += 0.1f;

            if (Talents.GlyphOfRegrowth)
                spells[(int)TreeSpell.Regrowth].ExtraDurationMS += (Talents.GlyphOfRegrowth ? (int)(Math.Min(opts.GlyphOfRegrowthExtraDuration, calc.FightLength) * 1000.0) : 0);
            #endregion

            for (int i = 0; i < (int)TreeSpell.Count; ++i)
            {
                if (i != (int)TreeSpell.HealingTouch && i != (int)TreeSpell.WildGrowth)
                    spells[i].ComputeTiming();
            }

            if (T13Count >= 4)
            {
                // here we assume that the tick structure is computed as if the spell just had double duration
                // this is NOT the same as doubling the amount of ticks, due to rounding

                // also we assume that overhealing ratio doesn't depend on duration in our model
                // if the model is changed to do that, then this averaging will need to be done much later

                for (int i = 0; i < CalculationsTree.T13Spells.Length; ++i)
                {
                    ComputedSpell extspell = new ComputedSpell(CalculationsTree.T13SpellData[i], stats);
                    extspell.ComputeTiming();

                    ComputedSpell spell = spells[(int)CalculationsTree.T13Spells[i]];
                    spell.Ticks = 0.9 * spell.Ticks + 0.1 * extspell.Ticks;
                    spell.TPS = 0.9 * spell.TPS + 0.1 * extspell.TPS;
                    spell.Duration = 0.9 * spell.Duration + 0.1 * extspell.Duration;
                }
            }

            // optimization to avoid duplicating computations
            spells[(int)TreeSpell.HealingTouch].Action.Time = spells[(int)TreeSpell.Nourish].Action.Time;
            spells[(int)TreeSpell.WildGrowth].Action.Time = spells[(int)TreeSpell.Swiftmend].Action.Time;
            spells[(int)TreeSpell.WildGrowth].Ticks = spells[(int)TreeSpell.Swiftmend].Ticks;
            spells[(int)TreeSpell.WildGrowth].Duration = spells[(int)TreeSpell.Swiftmend].Duration;
            spells[(int)TreeSpell.WildGrowth].TPS = spells[(int)TreeSpell.Swiftmend].TPS;

            for (int i = 0; i < (int)TreeSpell.Count; ++i)
                spells[i].ComputeRest();

            if (rejuvenationInstantTicks > 0)
            {
                spells[(int)TreeSpell.Rejuvenation].Action.Direct += rejuvenationInstantTicks * spells[(int)TreeSpell.Rejuvenation].Tick;
                ++spells[(int)TreeSpell.Rejuvenation].Action.Ticks;
            }

            #region Cooldowns
            spells[(int)TreeSpell.WildGrowth].Action.Cooldown = 8 + opts.WildGrowthCastDelay;
            spells[(int)TreeSpell.Tranquility].Action.Cooldown = 8 * 60 - (150 * Talents.MalfurionsGift) + opts.TranquilityCastDelay;
            spells[(int)TreeSpell.Swiftmend].Action.Cooldown = 15 + opts.SwiftmendCastDelay;

            if (opts.GlyphOfWildGrowthCDIncrease && character.DruidTalents.GlyphOfWildGrowth)
                spells[(int)TreeSpell.WildGrowth].Action.Cooldown += 2;
            #endregion

            return spells;
        }