Example #1
0
        public bool hasEmpower(BlueprintAbility spell, UnitEntityData caster, UnitEntityData target)
        {
            bool is_ok = false;

            foreach (var b in buffs)
            {
                b.CallComponents <HealingMetamagic>(h => is_ok = h.worksOnEmpower(spell, caster, target));
                if (is_ok)
                {
                    return(true);
                }
            }

            return(false);
        }
Example #2
0
        internal static void FixBloodlineSpell(BlueprintAbility spell, String bloodlineId, String addSpellId)
        {
            var addSpellFeat = library.Get <BlueprintFeature>(addSpellId);
            var prefix       = "At 3rd level, and every two levels thereafter, a sorcerer learns an additional spell, derived from her bloodline. These spells are in addition to the number of spells given at new levels.\n";

            addSpellFeat.SetNameDescriptionIcon(spell.Name, $"{prefix}{spell.Description}", spell.Icon);

            // Fix the spell, and the spell recommendations.
            var addSpell = addSpellFeat.GetComponent <AddKnownSpell>();
            var oldSpell = addSpell.Spell;

            oldSpell.RemoveRecommendNoFeatureGroup(bloodlineId);
            spell.AddRecommendNoFeature(addSpellFeat);
            addSpell.Spell = spell;
        }
 public static BlueprintAbility[] getDuplicates(BlueprintAbility original)
 {
     if (original == null)
     {
         return(new BlueprintAbility[0]);
     }
     if (duplicate_spells.ContainsKey(original.AssetGuid))
     {
         return(duplicate_spells[original.AssetGuid].ToArray());
     }
     else
     {
         return(new BlueprintAbility[] { original });
     }
 }
Example #4
0
        public static bool Prefix(AbilityData __instance, ref UnitCommand.CommandType __result)
        {
            BlueprintAbility abl  = __instance.Blueprint;
            UnitDescriptor   unit = __instance.Caster;

            if (ConsumeSpells.ablList.Contains(abl) || abl == ConsumeItem.abl)
            {
                if (unit.HasFact(SwiftConsume.exploit))
                {
                    __result = UnitCommand.CommandType.Swift;
                    return(false);
                }
            }
            return(true);
        }
Example #5
0
        static internal void updateItemsForChannelDerivative(BlueprintAbility original_ability, BlueprintAbility derived_ability)
        {
            var config = derived_ability.GetComponent <ContextRankConfig>();

            ContextRankProgression progression = Helpers.GetField <ContextRankProgression>(config, "m_Progression");
            int step        = Helpers.GetField <int>(config, "m_StepLevel");
            int level_scale = (progression == ContextRankProgression.OnePlusDivStep || progression == ContextRankProgression.DivStep || progression == ContextRankProgression.StartPlusDivStep)
                                    ? step : 2;

            //phylacteries bonuses
            BlueprintEquipmentEnchantment[] enchants = new BlueprintEquipmentEnchantment[] { library.Get <Kingmaker.Blueprints.Items.Ecnchantments.BlueprintEquipmentEnchantment>("60f06749fa4729c49bc3eb2eb7e3b316"),
                                                                                             library.Get <Kingmaker.Blueprints.Items.Ecnchantments.BlueprintEquipmentEnchantment>("f5d0bf8c1b4574848acb8d1fbb544807"),
                                                                                             library.Get <Kingmaker.Blueprints.Items.Ecnchantments.BlueprintEquipmentEnchantment>("cb4a39044b59f5e47ad5bc08ff9d6669"),
                                                                                             library.Get <Kingmaker.Blueprints.Items.Ecnchantments.BlueprintEquipmentEnchantment>("e988cf802d403d941b2ed8b6016de68f"), };

            foreach (var e in enchants)
            {
                var boni = e.GetComponents <AddCasterLevelEquipment>().ToArray();
                foreach (var b in boni)
                {
                    if (b.Spell == original_ability)
                    {
                        var b2 = b.CreateCopy();
                        b2.Spell = derived_ability;
                        b2.Bonus = boni[0].Bonus / 2 * level_scale;
                        e.AddComponent(b2);
                    }
                }
            }


            BlueprintBuff[] buffs = new BlueprintBuff[] { library.Get <BlueprintBuff>("b5ebb94df76531c4ca4f13bfd91efd4e") };// camp dish buff

            foreach (var buff in buffs)
            {
                var boni = buff.GetComponents <AddCasterLevelForAbility>().ToArray();
                foreach (var b in boni)
                {
                    if (b.Spell == original_ability)
                    {
                        var b2 = b.CreateCopy();
                        b2.Spell = derived_ability;
                        b2.Bonus = boni[0].Bonus / 2 * level_scale;
                        buff.AddComponent(b2);
                    }
                }
            }
        }
Example #6
0
        static void LoadWish()
        {
            var spell = Helpers.CreateAbility("Wish", "Wish",
                                              "Wish is the mightiest spell a wizard or sorcerer can cast. By simply speaking aloud, you can alter reality to better suit you. Even wish, however, has its limits. A wish can produce any one of the following effects.\n" +
                                              "• Duplicate any sorcerer/wizard spell of 8th level or lower, provided the spell does not belong to one of your opposition schools.\n" +
                                              "• Duplicate any non-sorcerer/wizard spell of 7th level or lower, provided the spell does not belong to one of your opposition schools.\n" +
                                              "• Duplicate any sorcerer/wizard spell of 7th level or lower, even if it belongs to one of your opposition schools.\n" +
                                              "• Duplicate any non-sorcerer/wizard spell of 6th level or lower, even if it belongs to one of your opposition schools.\n" +
                                              "• Undo the harmful effects of many other spells, such as geas/quest or insanity.\n" +
                                              "• Grant a creature a +1 inherent bonus to an ability score. Two to five wish spells cast in immediate succession can grant a creature a +2 to +5 inherent bonus to an ability score (two wishes for a +2 inherent bonus, three wishes for a +3 inherent bonus, and so on). Inherent bonuses are instantaneous, so they cannot be dispelled. Note: An inherent bonus may not exceed +5 for a single ability score, and inherent bonuses to a particular ability score do not stack, so only the best one applies.\n" +
                                              "• Remove injuries and afflictions. A single wish can aid one creature per caster level, and all subjects are cured of the same kind of affliction. For example, you could heal all the damage you and your companions have taken, or remove all poison effects from everyone in the party, but not do both with the same wish.\n" +
                                              "• Revive the dead. A wish can bring a dead creature back to life by duplicating a resurrection spell. A wish can revive a dead creature whose body has been destroyed, but the task takes two wishes: one to recreate the body and another to infuse the body with life again. A wish cannot prevent a character who was brought back to life from gaining a permanent negative level.\n" +
                                              //"• Transport travelers. A wish can lift one creature per caster level from anywhere on any plane and place those creatures anywhere else on any plane regardless of local conditions. An unwilling target gets a Will save to negate the effect, and spell resistance (if any) applies.\n" +
                                              //"• Undo misfortune. A wish can undo a single recent event. The wish forces a reroll of any roll made within the last round (including your last turn). Reality reshapes itself to accommodate the new result. For example, a wish could undo an opponent’s successful save, a foe’s successful critical hit (either the attack roll or the critical roll), a friend’s failed save, and so on. The re-roll, however, may be as bad as or worse than the original roll. An unwilling target gets a Will save to negate the effect, and Spell Resistance (if any) applies.\n" +
                                              "Duplicated spells allow saves and Spell Resistance as normal (but save DCs are for 9th-level spells).\n" +
                                              "When a wish duplicates a spell with a material component that costs more than 10,000 gp, you must provide that component (in addition to the 25,000 gp diamond component for this spell).",
                                              "508802d7c0cb452ab7473c2e83c3f535",
                                              Image2Sprite.Create("Mods/EldritchArcana/sprites/wish_spell.png"),
                                              AbilityType.Spell,
                                              CommandType.Standard,
                                              AbilityRange.Personal,
                                              "", "", Helpers.CreateSpellComponent(SpellSchool.Universalist),
                                              Helpers.CreateSpellDescriptor());

            spell.CanTargetSelf      = true;
            spell.AvailableMetamagic = Metamagic.Quicken | Metamagic.Heighten | Metamagic.Empower | Metamagic.Extend | Metamagic.Maximize | Metamagic.Reach;

            var variants = new List <BlueprintAbility>();

            // TODO: add an option to remove injuries and afflictions.
            for (int level = 1; level <= 8; level++)
            {
                variants.Add(CreateWishForSpellLevel(spell, level, 9));
            }
            //variants.AddRange(CreateWishForStatBonus(spell));

            variants.AddRange(CreateWishForStatBonus(spell, spell.AssetGuid));
            spell.AddComponent(spell.CreateAbilityVariants(variants));
            spell.MaterialComponent = variants[0].MaterialComponent;

            spell.AddToSpellList(Helpers.wizardSpellList, 9);
            // Wish Scroll uses 7th level spells to offer the most choice (divine + arcane).
            Wishy = spell;
            Helpers.AddSpellAndScroll(spell, "f948342d6a9f2ce49b6aa5f362569d72", 6);                          // scroll geniekind djinni icon
            // Fix Draconic and Arcane bloodlines to have Wish as their 9th level spell.
            FixBloodlineSpell(spell, "4d491cf9631f7e9429444f4aed629791", "74ab07974fa1c424bbd6fc0e56114db6"); // arcane
            FixBloodlineSpell(spell, "7bd143ead2d6c3a409aad6ee22effe34", "32d443e6a4103d84b9243822c3abec97"); // draconic
        }
            private bool noCastingTimeIncreaseForMetamagicInternal(BlueprintAbility ability, Metamagic metamagic, int additional_free_metamagic)
            {
                if (!prepared_spells_with_metamagic.ContainsKey(ability.AssetGuid))
                {
                    return(false);
                }

                int free_metamagics = additional_free_metamagic;

                if (metamixingEnabled())
                {
                    free_metamagics++;
                }

                return(prepared_spells_with_metamagic[ability.AssetGuid].Any(m => (m | metamagic) == metamagic && Helpers.PopulationCount((int)(metamagic & ~m)) <= free_metamagics));
            }
        public int getAmount(BlueprintAbility spell)
        {
            var amount = 0;

            foreach (var b in buffs)
            {
                var comp = b.Blueprint.GetComponent <ReceiveBonusHpPerDie>();
                if (comp == null)
                {
                    continue;
                }
                b.CallComponents <ReceiveBonusHpPerDie>(a => amount += a.perDieAmount(spell));
            }

            return(amount);
        }
        public int getAmount(BlueprintAbility spell)
        {
            var amount = 0;

            foreach (var b in buffs)
            {
                var comp = b.Blueprint.GetComponent <BonusHealing>();
                if (comp == null)
                {
                    continue;
                }
                b.CallComponents <BonusHealing>(a => amount += a.getBonusHealing(spell));
            }

            return(amount);
        }
 public AreaEffectDismissal()
 {
     dismiss = Helpers.CreateAbility("DismissAreaEffectSpell", "Dismiss Area Effect Spell",
                                     "Some spells can be dismissed at will, others when you are out of combat. You must be within range of the spell’s effect. Dismissing a spell is a standard action that does not provoke attacks of opportunity.\n" +
                                     "A spell that depends on concentration is dismissible by its very nature, and dismissing it does not take an action, since all you have to do to end the spell is to stop concentrating on your turn.\n" +
                                     "(If this ability is enabled, it means you have a currently active effect spell that can be dismissed.)",
                                     "da09c33c33d44be485c5757262923bfb",
                                     Helpers.GetIcon("95f7cdcec94e293489a85afdf5af1fd7"), // dismissal
                                     AbilityType.Extraordinary,                           // (Ex) so it doesn't provoke an attack of opportunity, and works w/ antimagic field.
                                     CommandType.Standard,
                                     AbilityRange.Long,                                   // Note: should be the spell range, but this should be good enough.
                                     "", "",
                                     Helpers.Create <DismissAreaEffectLogic>(),
                                     Helpers.CreateRunActions(Helpers.Create <DismissAreaEffectAction>()));
     dismiss.CanTargetPoint = true;
 }
Example #11
0
        private bool hasSpell(UnitDescriptor unit, BlueprintAbility spell)
        {
            var duplicates = SpellDuplicates.getDuplicates(spell);

            foreach (var sb in unit.Spellbooks)
            {
                foreach (var d in duplicates)
                {
                    if (sb.CanSpend(d))
                    {
                        return(true);
                    }
                }
            }
            return(false);
        }
Example #12
0
        static void createSanctuary()
        {
            var lesser_restoration = library.Get <BlueprintAbility>("e84fc922ccf952943b5240293669b171");
            var sancturay_logic    = Helpers.Create <NewMechanics.Sanctuary>(c =>
            {
                c.save_type = SavingThrowType.Will;
                c.offensive_action_effect = NewMechanics.Sanctuary.OffensiveActionEffect.REMOVE_FROM_OWNER;
            }
                                                                             );

            sanctuary_buff = library.CopyAndAdd <BlueprintBuff>("525f980cb29bc2240b93e953974cb325", "SanctuaryBuff", "");//invisibility

            sanctuary_buff.ComponentsArray = new BlueprintComponent[] { sancturay_logic };

            var apply_buff = Common.createContextActionApplyBuff(sanctuary_buff,
                                                                 Helpers.CreateContextDuration(bonus: Helpers.CreateContextValue(AbilityRankType.Default), rate: DurationRate.Rounds),
                                                                 is_from_spell: true);

            sanctuary = Helpers.CreateAbility("SanctuaryAbility",
                                              "Sanctuary",
                                              "Any opponent attempting to directly attack the warded creature, even with a targeted spell, must attempt a Will save. If the save succeeds, the opponent can attack normally and is unaffected by that casting of the spell. If the save fails, the opponent can’t follow through with the attack, that part of its action is lost, and it can’t directly attack the warded creature for the duration of the spell. Those not attempting to attack the subject remain unaffected. This spell does not prevent the warded creature from being attacked or affected by area of effect spells. The subject cannot attack without breaking the spell but may use non-attack spells or otherwise act.",
                                              "",
                                              lesser_restoration.Icon,
                                              AbilityType.Spell,
                                              Kingmaker.UnitLogic.Commands.Base.UnitCommand.CommandType.Standard,
                                              AbilityRange.Touch,
                                              Helpers.roundsPerLevelDuration,
                                              "Will negates",
                                              Helpers.CreateSpellComponent(SpellSchool.Abjuration),
                                              Helpers.CreateRunActions(apply_buff)
                                              );

            sanctuary_buff.SetDescription(sanctuary.Description);
            sanctuary_buff.SetIcon(sanctuary.Icon);

            sanctuary.CanTargetSelf      = true;
            sanctuary.CanTargetPoint     = false;
            sanctuary.CanTargetFriends   = true;
            sanctuary.CanTargetEnemies   = false;
            sanctuary.Animation          = Kingmaker.Visual.Animation.Kingmaker.Actions.UnitAnimationActionCastSpell.CastAnimationStyle.Touch;
            sanctuary.AnimationStyle     = Kingmaker.View.Animation.CastAnimationStyle.CastActionTouch;
            sanctuary.AvailableMetamagic = Kingmaker.UnitLogic.Abilities.Metamagic.Extend | Kingmaker.UnitLogic.Abilities.Metamagic.Quicken | Kingmaker.UnitLogic.Abilities.Metamagic.Heighten;
            sanctuary.AddToSpellList(Helpers.clericSpellList, 1);
            sanctuary.AddToSpellList(Helpers.inquisitorSpellList, 1);

            sanctuary.AddSpellAndScroll("c0af0b5277e91e347ade3aa8994b0d17"); //invisibility
        }
        static BlueprintAbility CreateWishForSpellLevel(BlueprintAbility wishSpell, int level, int wishLevel, bool isMiracle = false)
        {
            //make shure the ids are different becouse doublicate ids would overwrite each outher
            string MiracleID = isMiracle ? "6db719c91bcc4f31b997904ef1f873c9" : "7db719c91bcc4f31b997904ef1f873c8";

            var wishText = isMiracle ? RES.MiracleSpells_info : RES.WishSpells_info;
            var spell    = Helpers.CreateAbility($"{wishSpell.name}{level}",
                                                 string.Format(RES.WishLevelSpellName_info, wishSpell.Name, level),
                                                 string.Format(RES.WishSpellDescription_info, wishText, wishSpell.Description),
                                                 Helpers.MergeIds(wishSpell.AssetGuid, MiracleID, FavoredClassBonus.spellLevelGuids[level - 1]),
                                                 wishSpell.Icon, wishSpell.Type, wishSpell.ActionType, wishSpell.Range,
                                                 wishSpell.LocalizedDuration, wishSpell.LocalizedSavingThrow);

            spell.AvailableMetamagic = wishSpell.AvailableMetamagic;
            spell.CanTargetSelf      = true;
            if (!isMiracle)
            {
                spell.MaterialComponent.Item  = wishLevel < 9 ? diamondDust.Value : diamond.Value;
                spell.MaterialComponent.Count = wishLevel < 9 ? 30 : 5;
            }

            // To keep wish spells from overwhelming the game's UI, they're done as a series of nested selections:
            // - wish spell variant: choose spell level, or other effect
            // - ability menu: group spells by school
            //   (unless the spell has variants, in which case, put it at the top level)
            //
            // That means we only get a maximum of spell schools + variant spells, which keeps the size down.
            //
            // Also, these spells tend to be used for powerful effects, so it's likely they'll select one of the
            // highest spell levels first. That eliminates all of the low-level spell noise (e.g. "cure light wounds").
            //FavoredClassBonus.
            var buff = Helpers.CreateBuff($"{wishSpell.name}{level}Buff", wishSpell.Name, wishSpell.Description,
                                          Helpers.MergeIds(wishSpell.AssetGuid, "5a203cb47d1942058a602da860e435d7", FavoredClassBonus.spellLevelGuids[level - 1]),
                                          wishSpell.Icon,
                                          null);

            buff.SetComponents(CreateWishSpellChoices(spell, buff, level, wishLevel, isMiracle));
            buff.Stacking  = StackingType.Replace;
            buff.Frequency = DurationRate.Rounds;

            // Duration: 2 rounds. Should be enough time to make a wish (as a free action).
            var applyBuff = Helpers.CreateApplyBuff(buff, Helpers.CreateContextDuration(2),
                                                    fromSpell: true, dispellable: false, toCaster: true);

            spell.SetComponents(Helpers.CreateRunActions(applyBuff), wishSpell.GetComponent <SpellDescriptorComponent>(), wishSpell.GetComponent <SpellComponent>());
            return(spell);
        }
Example #14
0
        static void LoadMiracle()
        {
            var spell = Helpers.CreateAbility("Miracle", "Miracle",
                                              "You don’t so much cast a miracle as request one. You state what you would like to have happen and request that your deity (or the power you pray to for spells) intercede.\n" +
                                              "A miracle can do any of the following things.\n" +
                                              "• Duplicate any cleric spell of 8th level or lower.\n" +
                                              "• Duplicate any other spell of 7th level or lower.\n" +
                                              "• Undo the harmful effects of certain spells, such as feeblemind or insanity.\n" +
                                              "• Have any effect whose power level is in line with the above effects.\n" +
                                              "Alternatively, a cleric can make a very powerful request. Casting such a miracle costs the cleric 25,000 gp in powdered diamond because of the powerful divine energies involved. Examples of especially powerful miracles of this sort could include the following:\n" +
                                              "• Swinging the tide of a battle in your favor by raising fallen allies to continue fighting.\n" +
                                              "• Moving you and your allies, with all your and their gear, from one plane to a specific locale through planar barriers with no chance of error.\n" +
                                              "• Protecting a city from an earthquake, volcanic eruption, flood, or other major natural disaster.\n" +
                                              "In any event, a request that is out of line with the deity’s (or alignment’s) nature is refused.\n" +
                                              "A duplicated spell allows saving throws and spell resistance as normal, but the save DCs are as for a 9th-level spell.When a miracle spell duplicates a spell with a material component that costs more than 100 gp, you must provide that component.",
                                              "8ce2676c93de461b91596ef7e4e04c09",
                                              Helpers.GetIcon("fafd77c6bfa85c04ba31fdc1c962c914"), // restoration greater
                                              AbilityType.Spell,
                                              CommandType.Standard,
                                              AbilityRange.Personal,
                                              "", "",
                                              Helpers.CreateSpellComponent(SpellSchool.Evocation),
                                              Helpers.CreateSpellDescriptor());

            spell.CanTargetSelf      = true;
            spell.AvailableMetamagic = Metamagic.Quicken | Metamagic.Heighten | Metamagic.Empower | Metamagic.Extend | Metamagic.Maximize | Metamagic.Reach;

            var variants = new List <BlueprintAbility>();

            for (int level = 1; level <= 8; level++)
            {
                variants.Add(CreateWishForSpellLevel(spell, level, 9, isMiracle: true));
            }
            spell.AddComponent(spell.CreateAbilityVariants(variants));
            spell.MaterialComponent = variants[0].MaterialComponent;

            // TODO: variant for mass Resurrection (cost 25,000)
            // TODO: variant for protection from natural disasters (cost 25,000)
            // Perhaps it should prevent some of the bad kingdom effects that can happen,
            // or other quest related effects (e.g. become immune to Kingdom penalties for a time)?
            spell.AddToSpellList(Helpers.clericSpellList, 9);
            miracle = spell;

            // Miracle Scroll uses 7th level spells to offer the most choice (divine + arcane).
            Helpers.AddSpellAndScroll(spell, "d441dfae9c6b21e47ae24eb13d8b4c4b", 6); // restoration greater.
        }
Example #15
0
        static BlueprintAiCastSpell createCastSpellAction(string name, BlueprintAbility spell, Consideration[] actor_consideration, Consideration[] target_consideration,
                                                          float base_score = 1f, BlueprintAbility variant = null, int combat_count = 0, int cooldown_rounds = 0, string guid = "")
        {
            var action = CallOfTheWild.Helpers.Create <BlueprintAiCastSpell>();

            action.Ability              = spell;
            action.Variant              = variant;
            action.ActorConsiderations  = actor_consideration;
            action.TargetConsiderations = target_consideration;
            action.name           = name;
            action.BaseScore      = base_score;
            action.CombatCount    = combat_count;
            action.CooldownRounds = cooldown_rounds;
            library.AddAsset(action, guid);

            return(action);
        }
        public bool hasEmpower(BlueprintAbility spell)
        {
            foreach (var b in buffs)
            {
                var comp = b.Blueprint.GetComponent <SelfHealingMetamagic>();
                if (comp == null)
                {
                    continue;
                }
                if (comp.empower && comp.worksOn(spell))
                {
                    return(true);
                }
            }

            return(false);
        }
Example #17
0
        public static BlueprintFeature createExtraChannelFeat(BlueprintAbility ability, BlueprintFeature parent_feature, string name, string display_name, string guid)
        {
            var extra_channel = library.CopyAndAdd <BlueprintFeature>("cd9f19775bd9d3343a31a065e93f0c47", name, guid);

            extra_channel.ReplaceComponent <Kingmaker.Blueprints.Classes.Prerequisites.PrerequisiteFeature>(Helpers.PrerequisiteFeature(parent_feature));
            extra_channel.SetName(display_name);

            var resource_logic = ability.GetComponent <AbilityResourceLogic>();
            var resource       = resource_logic.RequiredResource;
            var amount         = resource_logic.Amount;

            extra_channel.ReplaceComponent <IncreaseResourceAmount>(c => { c.Value = amount * 2; c.Resource = resource; });
            extra_channel.ReplaceComponent <PrerequisiteFeature>(c => { c.Feature = parent_feature; });

            library.AddFeats(extra_channel);
            return(extra_channel);
        }
        private static void CreateAbilityMoveActions()
        {
            BlueprintAbility persuasionUseAbility     = library.Get <BlueprintAbility>("7d2233c3b7a0b984ba058a83b736e6ac");
            BlueprintAbility persuasionUseAbilityMove = Main.library.CopyAndAdd(persuasionUseAbility, "DemoralizeMove", "3af0e87e92a348daad1ec1934a7f811c");

            persuasionUseAbilityMove.ActionType = UnitCommand.CommandType.Move;
            Traverse traverse = Traverse.Create(persuasionUseAbilityMove);

            traverse.Field("m_AssetGuid").SetValue("3af0e87e92a348daad1ec1934a7f811c");

            BlueprintAbility dazzlingDisplayAction     = Main.library.Get <BlueprintAbility>("5f3126d4120b2b244a95cb2ec23d69fb");
            BlueprintAbility dazzlingDisplayActionMove = Main.library.CopyAndAdd(dazzlingDisplayAction, "DazzlingDisplayAction", "545b0811f3c24a518c02f749509623c4");

            dazzlingDisplayActionMove.ActionType = UnitCommand.CommandType.Move;
            traverse = Traverse.Create(dazzlingDisplayActionMove);
            traverse.Field("m_AssetGuid").SetValue("545b0811f3c24a518c02f749509623c4");
        }
Example #19
0
        static List <BlueprintItemEquipment> FindItemBlueprintForSpell(BlueprintAbility spell, UsableItemType itemType)
        {
            if (!spellIdToItem.ContainsKey(itemType))
            {
                BlueprintItemEquipmentUsable[] allUsableItems = Resources.FindObjectsOfTypeAll <BlueprintItemEquipmentUsable>();
                foreach (BlueprintItemEquipmentUsable item in allUsableItems)
                {
                    if (item.Type == itemType)
                    {
                        AddItemBlueprintForSpell(spell, itemType, item);
                    }
                }
            }
            string spellId = spell.AssetGuid;

            return((spellIdToItem[itemType].ContainsKey(spellId)) ? spellIdToItem[itemType][spellId] : null);
        }
Example #20
0
        public static void AddToSpellList(this BlueprintAbility spell, BlueprintSpellList spellList, int level)
        {
            var comp = Helpers.Create <SpellListComponent>();

            comp.SpellLevel = level;
            comp.SpellList  = spellList;
            spell.AddComponent(comp);
            spellList.SpellsByLevel[level].Spells.Add(spell);
            if (spellList == Main.objects.wizardSpellList)
            {
                var school         = spell.School;
                var specialistList = specialistSchoolList.Value[(int)school];
                specialistList?.SpellsByLevel[level].Spells.Add(spell);
                var thassilonianList = thassilonianSchoolList.Value[(int)school];
                thassilonianList?.SpellsByLevel[level].Spells.Add(spell);
            }
        }
        static void fixWingsBuff()
        {
            var airborne = library.Get <BlueprintFeature>("70cffb448c132fa409e49156d013b175");

            var wing_buffs = library.GetAllBlueprints().Where(b => b.name.Contains("BuffWings") && b is BlueprintBuff).Cast <BlueprintBuff>().ToList();

            wing_buffs.Add(library.Get <BlueprintBuff>("25699a90ed3299e438b6fd5548930809")); //angel wings
            wing_buffs.Add(library.Get <BlueprintBuff>("a19cda073f4c2b64ca1f8bf8fe285ece")); //black angel wings
            wing_buffs.Add(library.Get <BlueprintBuff>("4113178a8d5bf4841b8f15b1b39e004f")); //diabolic wings
            wing_buffs.Add(library.Get <BlueprintBuff>("775df52784e1d454cba0da8df5f4f59a")); //deva wings
            foreach (var wb in wing_buffs)
            {
                wb.ReplaceComponent <ACBonusAgainstAttacks>(Helpers.CreateAddFact(airborne));
            }

            var fiery_body = library.Get <BlueprintBuff>("b574e1583768798468335d8cdb77e94c");

            fiery_body.AddComponent(Helpers.CreateAddFact(airborne));

            fiery_body.SetDescription(fiery_body.Description + " You are also able to fly.");

            var fiery_body_spell = library.Get <BlueprintAbility>("08ccad78cac525040919d51963f9ac39");

            fiery_body_spell.SetDescription(fiery_body_spell.Description + " You also gain ability to fly.");


            var buffs_to_add_flying = new BlueprintBuff[]
            { library.Get <BlueprintBuff>("b33f44fecadb3ca48b438dacac6454c2"), //angelic aspect
              library.Get <BlueprintBuff>("87fcda72043d20840b4cdc2adcc69c63")  //angelic aspect greater
            };

            foreach (var b in buffs_to_add_flying)
            {
                b.AddComponent(Helpers.CreateAddFact(airborne));
            }

            var abilities_to_add_flying_description = new BlueprintAbility[]
            { library.Get <BlueprintAbility>("75a10d5a635986641bfbcceceec87217"), //angelic aspect
              library.Get <BlueprintAbility>("b1c7576bd06812b42bda3f09ab202f14")  //angelic aspect greater
            };

            foreach (var a in abilities_to_add_flying_description)
            {
                a.SetDescription(a.Description + " You also sprout white feathered wings allowing you to fly.");
            }
        }
            public override void OnEventAboutToTrigger(RuleSavingThrow evt)
            {
                BlueprintAbility sourceAbility = evt.Reason.Context?.SourceAbility;

                int bonus = this.Value.Calculate(this.Context);

                foreach (var s in Spells)
                {
                    if (SpellDuplicates.isDuplicate(s, evt.Reason.Context?.SourceAbility))
                    {
                        evt.AddTemporaryModifier(evt.Initiator.Stats.SaveWill.AddModifier(bonus, (GameLogicComponent)this, this.ModifierDescriptor));
                        evt.AddTemporaryModifier(evt.Initiator.Stats.SaveReflex.AddModifier(bonus, (GameLogicComponent)this, this.ModifierDescriptor));
                        evt.AddTemporaryModifier(evt.Initiator.Stats.SaveFortitude.AddModifier(bonus, (GameLogicComponent)this, this.ModifierDescriptor));
                        return;
                    }
                }
            }
Example #23
0
            static void Postfix([NotNull] BlueprintAbility spell, [NotNull] Spellbook spellbook, ref bool __result)
            {
                if (spellbook.IsKnown(spell))
                {
                    __result = false;
                    return;
                }
                bool spellListContainsSpell = spellbook.Blueprint.SpellList.Contains(spell);

                if ((settings.toggleSpontaneousCopyScrolls) && spellbook.Blueprint.Spontaneous && spellListContainsSpell)
                {
                    __result = true;
                    return;
                }

                __result = spellbook.Blueprint.CanCopyScrolls && spellListContainsSpell;
            }
Example #24
0
        public BlueprintFeature createEnergyRay()
        {
            var rays = new BlueprintAbility[]
            {
                library.Get <BlueprintAbility>("435222be97067a447b2b40d3c58a058e"), //acid
                library.Get <BlueprintAbility>("7ef096fdc8394e149a9e8dced7576fee"), //cold
                library.Get <BlueprintAbility>("96ca3143601d6b242802655336620d91"), //electricity
                library.Get <BlueprintAbility>("cdb106d53c65bbc4086183d54c3b97c7")  //fire
            };

            var names = new string[] { "Acid", "Cold", "Electricity", "Fire" };

            var abilities = new BlueprintAbility[rays.Length];

            for (int i = 0; i < abilities.Length; i++)
            {
                var dmg_type = (rays[i].GetComponent <AbilityEffectRunAction>().Actions.Actions[0] as ContextActionDealDamage).DamageType.Energy;
                var ability  = Helpers.CreateAbility(prefix + names[i] + "EnergyRayAbility",
                                                     "Energy Ray: " + names[i],
                                                     $"As a standard action that provokes attacks of opportunity, you can expend 1 point of mental focus to unleash a ray of pure energy as a ranged touch attack. This ray has a range of 25 feet. The ray deals an amount of energy damage equal to 1d{BalanceFixes.getDamageDieString(DiceType.D6)} points + 1d{BalanceFixes.getDamageDieString(DiceType.D6)} points for every 2 occultist levels you possess beyond 1st (2d{BalanceFixes.getDamageDieString(DiceType.D6)} at 3rd level, 3d{BalanceFixes.getDamageDieString(DiceType.D6)} at 5th, and so on, to a maximum of 10d{BalanceFixes.getDamageDieString(DiceType.D6)} at 19th level). When you unleash an energy ray, you must decide what type of damage it deals (acid, cold, electricity, or fire).",
                                                     "",
                                                     rays[i].Icon,
                                                     AbilityType.SpellLike,
                                                     CommandType.Standard,
                                                     AbilityRange.Close,
                                                     "",
                                                     "",
                                                     Helpers.CreateRunActions(Helpers.CreateActionDealDamage(dmg_type, Helpers.CreateContextDiceValue(BalanceFixes.getDamageDie(DiceType.D6), Helpers.CreateContextValue(AbilityRankType.Default), 0))),
                                                     rays[i].GetComponent <AbilityDeliverProjectile>().CreateCopy(a => { a.Projectiles = new BlueprintProjectile[] { a.Projectiles[0] }; a.UseMaxProjectilesCount = false; }),
                                                     Helpers.CreateSpellComponent(SpellSchool.Evocation),
                                                     rays[i].GetComponent <SpellDescriptorComponent>(),
                                                     createClassScalingConfig(ContextRankProgression.StartPlusDivStep, stepLevel: 2, startLevel: 1),
                                                     resource.CreateResourceLogic()
                                                     );
                ability.SpellResistance = true;
                ability.setMiscAbilityParametersSingleTargetRangedHarmful(true);
                abilities[i] = ability;
            }

            var wrapper = Common.createVariantWrapper(prefix + "EnergyRayAbilityBase", "", abilities);

            wrapper.SetName("Energy Ray");
            addFocusInvestmentCheck(wrapper, SpellSchool.Evocation);
            return(Common.AbilityToFeature(wrapper, false));
        }
Example #25
0
        // static readonly Lazy<BlueprintItem> bone = new Lazy<BlueprintItem>(() => library.Get<BlueprintItem>("6a7cdeb14fc6ef44580cf639c5cdc113"));


        static void LoadMiracle()
        {
            var spell = Helpers.CreateAbility("Miracle", RES.MiracleSpellName_info,
                                              RES.MiracleAbilityDescription_info,
                                              "8ce2676c93de461b91596ef7e4e04c09",
                                              Helpers.GetIcon("fafd77c6bfa85c04ba31fdc1c962c914"), // restoration greater
                                              AbilityType.Spell,
                                              CommandType.Standard,
                                              AbilityRange.Personal,
                                              "", "",
                                              Helpers.CreateSpellComponent(SpellSchool.Evocation),
                                              Helpers.CreateSpellDescriptor());

            spell.CanTargetSelf      = true;
            spell.AvailableMetamagic = Metamagic.Quicken | Metamagic.Heighten | Metamagic.Empower | Metamagic.Extend | Metamagic.Maximize | Metamagic.Reach;

            var variants = new List <BlueprintAbility>();

            for (int level = 1; level <= 8; level++)
            {
                variants.Add(CreateWishForSpellLevel(spell, level, 9, isMiracle: true));
            }
            // 添加奇迹术用的完全复生术
            var wishTrueResurrection = Library.CopyAndAdd(Spells.TrueResurrection,
                                                          "WishTrueResurrection", Spells.TrueResurrectionId, "361fc62d90dc4e75b4c7858fcc0072b0");

            wishTrueResurrection.SetName(string.Format(RES.MiracleUseSpellName_info, RES.TrueResurrectionSpells_info));
            wishTrueResurrection.SetIcon(Helpers.GetIcon("fafd77c6bfa85c04ba31fdc1c962c914")); // restoration greater
            wishTrueResurrection.MaterialComponent = variants[0].MaterialComponent;
            variants.Add(wishTrueResurrection);
            spell.AddComponent(spell.CreateAbilityVariants(variants));
            spell.MaterialComponent = variants[0].MaterialComponent;

            // TODO: variant for protection from natural disasters (cost 25,000)
            // Perhaps it should prevent some of the bad kingdom effects that can happen,
            // or other quest related effects (e.g. become immune to Kingdom penalties for a time)?
            spell.AddToSpellList(Helpers.clericSpellList, 9);
            // 修正为幸运,联盟领域9级法术
            spell.FixDomainSpell(9, Helpers.communityDomainSpellList.AssetGuid);
            spell.FixDomainSpell(9, Helpers.luckDomainSpellList.AssetGuid);
            miracle = spell;

            // Miracle Scroll uses 7th level spells to offer the most choice (divine + arcane).
            Helpers.AddSpellAndScroll(spell, "d441dfae9c6b21e47ae24eb13d8b4c4b", 6); // restoration greater.
        }
Example #26
0
            void createSpiritAbility()
            {
                var resource = Helpers.CreateAbilityResource(prefix + "ChannelResource", "", "", "", null);

                resource.SetIncreasedByStat(1, hex_engine.hex_secondary_stat);

                var positive_energy_feature = library.Get <BlueprintFeature>("a79013ff4bcd4864cb669622a29ddafb");
                var context_rank_config     = Helpers.CreateContextRankConfig(baseValueType: ContextRankBaseValueType.ClassLevel, progression: ContextRankProgression.StartPlusDivStep,
                                                                              type: AbilityRankType.Default, classes: hex_engine.hex_classes, startLevel: 1, stepLevel: 2);
                var dc_scaling = Common.createContextCalculateAbilityParamsBasedOnClasses(hex_engine.hex_classes, hex_engine.hex_secondary_stat);

                spirit_ability = Helpers.CreateFeature(prefix + "LifeSpiritChannelPositiveEnergyFeature",
                                                       "Channel Positive Energy",
                                                       "Shaman channels positive energy and can choose to deal damage to undead creatures or to heal living creatures.\nChanneling energy causes a burst that either heals all living creatures or damages all undead creatures in a 30-foot radius centered on the shaman. The amount of damage dealt or healed is equal to 1d6 points of damage plus 1d6 points of damage for every two shaman levels beyond 1st (2d6 at 3rd, 3d6 at 5th, and so on). Creatures that take damage from channeled energy receive a Will save to halve the damage. The DC of this save is equal to 10 + 1/2 the shaman's level + the shaman's Charisma modifier. Creatures healed by channel energy cannot exceed their maximum hit point total—all excess healing is lost. A shaman may channel energy a number of times per day equal to 1 + her Charisma modifier. This is a standard action that does not provoke an attack of opportunity. A shaman can choose whether or not to include herself in this effect.",
                                                       "",
                                                       positive_energy_feature.Icon,
                                                       FeatureGroup.None);

                heal_living = ChannelEnergyEngine.createChannelEnergy(ChannelEnergyEngine.ChannelType.PositiveHeal,
                                                                      prefix + "LifeSpiritChannelEnergyHealLiving",
                                                                      "",
                                                                      "Channeling positive energy causes a burst that heals all living creatures in a 30 - foot radius centered on the shaman. The amount of damage healed is equal to 1d6 plus 1d6 for every two shaman levels beyond first.",
                                                                      "",
                                                                      context_rank_config,
                                                                      dc_scaling,
                                                                      Helpers.CreateResourceLogic(resource));
                harm_undead = ChannelEnergyEngine.createChannelEnergy(ChannelEnergyEngine.ChannelType.PositiveHarm,
                                                                      prefix + "LifeSpiritChannelEnergyHarmUndead",
                                                                      "",
                                                                      "Channeling energy causes a burst that damages all undead creatures in a 30 - foot radius centered on the shaman. The amount of damage dealt is equal to 1d6 plus 1d6 for every two shaman levels beyond first. Creatures that take damage from channeled energy receive a Will save to halve the damage. The DC of this save is equal to 10 + 1 / 2 the shaman's level + the shaman's Charisma modifier.",
                                                                      "",
                                                                      context_rank_config,
                                                                      dc_scaling,
                                                                      Helpers.CreateResourceLogic(resource));

                var heal_living_base = Common.createVariantWrapper(prefix + "LifeSpiritPositiveHealBase", "", heal_living);
                var harm_undead_base = Common.createVariantWrapper(prefix + "LifeSpiritPositiveHarmBase", "", harm_undead);

                ChannelEnergyEngine.storeChannel(heal_living, spirit_ability, ChannelEnergyEngine.ChannelType.PositiveHeal);
                ChannelEnergyEngine.storeChannel(harm_undead, spirit_ability, ChannelEnergyEngine.ChannelType.PositiveHarm);

                spirit_ability.AddComponent(Helpers.CreateAddFacts(heal_living_base, harm_undead_base));
                spirit_ability.AddComponent(Helpers.CreateAddAbilityResource(resource));
                extra_channel = ChannelEnergyEngine.createExtraChannelFeat(heal_living, spirit_ability, extra_channel_prefix + "ExtraChannelShamanLifeSpirit", extra_channel_name, "");
            }
            public void OnEventAboutToTrigger(RuleCalculateAbilityParams evt)
            {
                spell_level = -1;
                int cost = 1 + evt.SpellLevel;

                if (this.resource == null || this.Owner.Resources.GetResourceAmount((BlueprintScriptableObject)this.resource) < cost)
                {
                    return;
                }
                if (evt.Spell == null || evt.Spellbook == null || evt.Spell.Type != AbilityType.Spell)
                {
                    return;
                }
                evt.AddBonusCasterLevel(bonus);
                evt.AddBonusDC(bonus);
                current_spell = evt.Spell;
                spell_level   = evt.SpellLevel;
            }
            public bool isUsedWithMetamixing(BlueprintAbility ability, Metamagic metamagic)
            {
                if (!metamixingEnabled())
                {
                    return(false);
                }

                if (ability.Parent != null)
                {
                    return(prepared_spells_with_metamagic[ability.Parent.AssetGuid].Any(m => (m | metamagic) == metamagic && Helpers.PopulationCount((int)(metamagic & ~m)) == 1) &&
                           !prepared_spells_with_metamagic[ability.Parent.AssetGuid].Any(m => (m | metamagic) == metamagic && Helpers.PopulationCount((int)(metamagic & ~m)) == 0));
                }
                else
                {
                    return(prepared_spells_with_metamagic[ability.AssetGuid].Any(m => (m | metamagic) == metamagic && Helpers.PopulationCount((int)(metamagic & ~m)) == 1) &&
                           !prepared_spells_with_metamagic[ability.AssetGuid].Any(m => (m | metamagic) == metamagic && Helpers.PopulationCount((int)(metamagic & ~m)) == 0));
                }
            }
Example #29
0
 // Token: 0x06000025 RID: 37 RVA: 0x00002918 File Offset: 0x00000B18
 public static void modSlumber()
 {
     try
     {
         foreach (string assetId in RemoveSlumberHD.guids)
         {
             BlueprintAbility blueprintAbility = RemoveSlumberHD.library.Get <BlueprintAbility>(assetId);
             if (blueprintAbility != null)
             {
                 blueprintAbility.RemoveComponents <AbilityTargetCasterHDDifference>();
             }
         }
     }
     catch (Exception ex)
     {
         return;
     }
 }
        public bool active(BlueprintAbility spell)
        {
            //Main.logger.Log("Checking UnitPartExtendHpBonusToCasterLevel " + spell.AssetGuid + " " + spell.name);
            foreach (var b in buffs)
            {
                var comp = b.Blueprint.GetComponent <ExtendHpBonusToCasterLevel>();
                if (comp == null)
                {
                    continue;
                }
                if (comp.worksOn(spell))
                {
                    return(true);
                }
            }

            return(false);
        }