public static void Prefix(AttackStackSequence __instance)
        {
            IsMoraleAttack = __instance.isMoraleAttack;
            Mod.Log.Debug($"AttackStackSequence:OnAdded:prefix - Recording IsMoraleAttack: {IsMoraleAttack}");

            AbstractActor   attacker  = __instance.owningActor;
            ActorInitiative actorInit = ActorInitiativeHolder.GetOrCreate(attacker);

            MoraleAttackMod = actorInit.calledShotMod;
        }
示例#2
0
        public static int CalculateMeleeDelta(ActorInitiative attacker, ActorInitiative target)
        {
            // Always return 1 or more
            int rawDelta = Math.Max(1, attacker.meleeAttackMod - target.meleeDefenseMod);

            Mod.Log.Debug($"Melee rawDelta:{rawDelta} = (attackerMod:{attacker.meleeAttackMod} - targetMod:{target.meleeDefenseMod})");
            int modifiedDelta = Math.Max(1, rawDelta - target.gutsEffectMod);

            Mod.Log.Debug($"MeleeMod reduced to modifiedDelta:{modifiedDelta} = (rawDelta:{rawDelta} - gutsEffectMod:{target.gutsEffectMod})");
            return(modifiedDelta);
        }
示例#3
0
        public static void Postfix(Turret __instance, WeaponHitInfo hitInfo, int hitLocation, Weapon weapon, float damageAmount, int hitIndex, DamageType damageType)
        {
            if (weapon != null && weapon.Category == WeaponCategory.Melee)
            {
                Mod.Log.Debug($"Turret:TakeWeaponDamage:post - Actor:({__instance.DisplayName}_{__instance.GetPilot().Name}) has suffered a melee attack from:{weapon.parent.DisplayName}.");

                ActorInitiative attacker = ActorInitiativeHolder.GetOrCreate(weapon.parent);
                ActorInitiative target   = ActorInitiativeHolder.GetOrCreate(__instance);
                int             deltaMod = ActorInitiative.CalculateMeleeDelta(attacker, target);
                target.ResolveMeleeImpact(__instance, deltaMod);
            }
        }
        public static void Postfix(AbstractActor __instance, string sourceID, int stackItemUID, bool addedBySelf)
        {
            if (InvokeIsKnockdown || InvokeIsCalledShot)
            {
                Mod.Log.Debug($"AbstractActor:ForceUnitOnePhaseDown:Postfix - executing custom logic.");
                ActorInitiative actorInit = ActorInitiativeHolder.GetOrCreate(__instance);

                int penalty = 0;
                if (InvokeIsKnockdown)
                {
                    penalty = Math.Max(0, (-1 * Mod.Config.ProneModifier) - actorInit.pilotingEffectMod);
                }
                else if (InvokeIsCalledShot)
                {
                    int randVal = Mod.Random.Next(0, 2);
                    penalty = Math.Max(0, AttackStackSequence_OnAdded.MoraleAttackMod + randVal - actorInit.pilotingEffectMod);
                    Mod.Log.Debug($"AbstractActor:ForceUnitOnePhaseDown:Postfix - moraleAttackMod:{AttackStackSequence_OnAdded.MoraleAttackMod} pilotingEffect:{actorInit.pilotingEffectMod}");
                }
                Mod.Log.Info($"AbstractActor:ForceUnitOnePhaseDown:Postfix modifying Actor:({__instance.DisplayName}_{__instance.GetPilot().Name}) " +
                             $"initiative by {penalty} due to knockdown:{InvokeIsKnockdown} / calledShot:{InvokeIsCalledShot}!");

                if (__instance.HasActivatedThisRound || __instance.Initiative >= Mod.MaxPhase)
                {
                    Mod.Log.Info($"Penalty {penalty} will apply to Actor:({__instance.DisplayName}_{__instance.GetPilot().Name}) on next activation!");

                    if (InvokeIsCalledShot)
                    {
                        actorInit.deferredCalledShotMod += penalty;
                    }

                    string floatieMsg = InvokeIsKnockdown ? $"GOING DOWN! -{penalty} INITIATIVE NEXT ROUND" : $"CALLED SHOT! -{penalty} INITIATIVE NEXT ROUND";
                    __instance.Combat.MessageCenter.PublishMessage(new FloatieMessage(__instance.GUID, __instance.GUID, floatieMsg, FloatieMessage.MessageNature.Debuff));

                    // Reset their initiative on this round
                    __instance.Initiative = PreInvokeInitiative;
                }
                else
                {
                    Mod.Log.Info($"Penalty {penalty} immediately applies to Actor:({__instance.DisplayName}_{__instance.GetPilot().Name}) with init:{PreInvokeInitiative}");

                    // The prefix call from CompleteKnockdown will have the actual initiative value, do not use the actor initiative
                    __instance.Initiative = PreInvokeInitiative + penalty;
                    if (__instance.Initiative > Mod.MaxPhase)
                    {
                        __instance.Initiative = Mod.MaxPhase;
                    }
                    __instance.Combat.MessageCenter.PublishMessage(new ActorPhaseInfoChanged(__instance.GUID));
                    string floatieMsg = InvokeIsKnockdown ? $"GOING DOWN! -{penalty} INITIATIVE" : $"CALLED SHOT! -{penalty} INITIATIVE";
                    __instance.Combat.MessageCenter.PublishMessage(new FloatieMessage(__instance.GUID, __instance.GUID, floatieMsg, FloatieMessage.MessageNature.Debuff));
                }
            }
        }
示例#5
0
        public static void Postfix(AbstractActor __instance)
        {
            //SkillBasedInit.Logger.Log($"AbstractActor:DeferUnit:");
            int reservePenalty = Mod.Random.Next(Mod.Config.ReservedPenaltyBounds[0], Mod.Config.ReservedPenaltyBounds[1]);

            Mod.Log.Debug($"  Deferring Actor:({CombatantHelper.LogLabel(__instance)}) " +
                          $"initiative:{__instance.Initiative} by:{reservePenalty} to:{__instance.Initiative + reservePenalty}");
            __instance.Initiative += reservePenalty;
            if (__instance.Initiative > Mod.MaxPhase)
            {
                __instance.Initiative = Mod.MaxPhase;
            }

            // Save some part of the reserve surplus as a penalty for the next round
            ActorInitiative actorInit = ActorInitiativeHolder.GetOrCreate(__instance);

            actorInit.reservedCount++;
            Mod.Log.Debug($"  Actor:({CombatantHelper.LogLabel(__instance)}) reservedCount incremented to:{actorInit.reservedCount}");
        }
        public static void Postfix(AbstractActor __instance, string sourceID, int stackItemUID, bool addedBySelf)
        {
            if (InvokeIsVigilance)
            {
                Mod.Log.Debug($"AbstractActor:ForceUnitOnePhaseUp:Postfix - executing custom logic.");
                ActorInitiative actorInit = ActorInitiativeHolder.GetOrCreate(__instance);

                actorInit.deferredVigilanceMod = actorInit.vigilianceMod + Mod.Random.Next(0, 2);
                Mod.Log.Debug($"AbstractActor:ForceUnitOnePhaseUp:Postfix - actor {__instance.DisplayName}_{__instance.GetPilot().Name} will gain  {actorInit.deferredVigilanceMod} init next round.");
                string floatieMsg = $"VIGILANCE! +{actorInit.vigilianceMod} INITIATIVE NEXT ROUND!";
                __instance.Combat.MessageCenter.PublishMessage(new FloatieMessage(__instance.GUID, __instance.GUID, floatieMsg, FloatieMessage.MessageNature.Debuff));

                // TODO: Test that this eliminates the portrait remaining activated
                __instance.Combat.MessageCenter.PublishMessage(new ActorPhaseInfoChanged(__instance.GUID));

                // Reset the actor's initiative
                Mod.Log.Debug($"AbstractActor:ForceUnitOnePhaseUp:Postfix - actor {__instance.DisplayName}_{__instance.GetPilot().Name} init of {__instance.Initiative} being restored to {PreInvokeInitiative}");
                __instance.Initiative = PreInvokeInitiative;
            }
        }
示例#7
0
        public static void Postfix(Pilot __instance, int __state, string sourceID, int stackItemUID, int dmg, DamageType damageType, Weapon sourceWeapon, AbstractActor sourceActor)
        {
            Mod.Log.Info($"Pilot:InjurePilot:post - Actor:({__instance.ParentActor.DisplayName}_{__instance.Name}) injured with initial bonusHealth:{__state}");

            int currentBonus = 0;

            if (__instance.StatCollection.GetStatistic("BonusHeath") != null)
            {
                currentBonus = __instance.StatCollection.GetStatistic("BonusHeath").Value <int>();
            }
            int bonusDelta  = __state - currentBonus;
            int damageTaken = dmg - bonusDelta;

            Mod.Log.Debug($"Pilot:InjurePilot:post - Actor:({__instance.ParentActor.DisplayName}_{__instance.Name}) lost bonusHealth:{bonusDelta}, while results in damage:{damageTaken} from the attack.");

            // If the attacker took any damage, apply it
            if (damageTaken > 0)
            {
                AbstractActor   parent        = __instance.ParentActor;
                ActorInitiative target        = ActorInitiativeHolder.GetOrCreate(parent);
                int             injuryPenalty = target.CalculateInjuryPenalty(damageTaken, __instance.Injuries);

                if (!parent.HasActivatedThisRound)
                {
                    // Apply penalty in current round. Remember high init -> higher phase
                    parent.Initiative += injuryPenalty;
                    if (parent.Initiative > Mod.MaxPhase)
                    {
                        parent.Initiative = Mod.MaxPhase;
                    }
                    parent.Combat.MessageCenter.PublishMessage(new ActorPhaseInfoChanged(parent.GUID));
                    parent.Combat.MessageCenter.PublishMessage(new FloatieMessage(parent.GUID, parent.GUID, $"OUCH! -{injuryPenalty} INITIATIVE", FloatieMessage.MessageNature.Debuff));
                }
                else
                {
                    // Injuries are cumulative
                    target.deferredInjuryMod += injuryPenalty;
                    parent.Combat.MessageCenter.PublishMessage(new FloatieMessage(parent.GUID, parent.GUID, $"OUCH! -{injuryPenalty} INITIATIVE NEXT ROUND", FloatieMessage.MessageNature.Debuff));
                }
            }
        }