public static bool Prefix(LanceOverride __instance, Contract contract, LanceDef lanceDef)
        {
            if (contract != null)
            {
                if (LanceOverride_RunMadLibs.teamOverrides.ContainsKey(__instance.GetHashCode()))
                {
                    // Setup CurrentTeam before running the madlibs
                    TeamOverride teamOverride = LanceOverride_RunMadLibs.teamOverrides[__instance.GetHashCode()];
                    IRBT14MadlibsFix.Logger.Log($"LO:RMLOLD using teamOverride:[{teamOverride.GetHashCode()}] for lanceOverride:[{__instance?.GetHashCode()}]");
                    contract.GameContext.SetObject(GameContextObjectTagEnum.CurrentTeam, teamOverride);
                }
                else
                {
                    IRBT14MadlibsFix.Logger.Log($"LO:RMLOLD COULD NOT LOAD teamOverride using lanceOverride:[{__instance.GetHashCode()}]! MadLibs may break!");
                }

                contract.RunMadLib(lanceDef.LanceTags);

                foreach (LanceDef.Unit unit in lanceDef.LanceUnits)
                {
                    Traverse ensureTagSetsT = Traverse.Create(unit).Method("EnsureTagSets");
                    ensureTagSetsT.GetValue();

                    IRBT14MadlibsFix.Logger.Log($"LO:RMLOLD BEFORE madlibs lanceTagSet is:[{unit.unitTagSet}]");
                    contract.RunMadLib(unit.unitTagSet);
                    IRBT14MadlibsFix.Logger.Log($"LO:RMLOLD AFTER madlibs lanceTagSet is:[{unit.unitTagSet}]");

                    contract.RunMadLib(unit.excludedUnitTagSet);
                    contract.RunMadLib(unit.pilotTagSet);
                    contract.RunMadLib(unit.excludedPilotTagSet);
                }
            }

            return(false);
        }
        private bool CheckForLanceDefSkips(LanceDef loadedLanceDef, TeamOverride teamOverride, string lanceGUID)
        {
            Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] [{teamOverride.faction}] Checking loaded LanceDef '{loadedLanceDef.Description.Id}' for Lance Override '{lanceGUID}'...");

            if (Main.Settings.ExtendedLances.GetSkipWhenTaggedWithAny().Count > 0 && loadedLanceDef.LanceTags.ContainsAny(Main.Settings.ExtendedLances.GetSkipWhenTaggedWithAny()))
            {
                Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] [{teamOverride.faction}] LanceDef contains a tag set in 'SkipWhenTaggedWithAny'. Skipping '{loadedLanceDef.Description.Id}'");
                lancesToSkip.Add(lanceGUID);
                return(true);
            }

            if (Main.Settings.ExtendedLances.GetSkipWhenTaggedWithAll().Count > 0 && loadedLanceDef.LanceTags.ContainsAll(Main.Settings.ExtendedLances.GetSkipWhenTaggedWithAll()))
            {
                Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] [{teamOverride.faction}] Lance contains a tag set in 'SkipWhenTaggedWithAll'. Skipping '{loadedLanceDef.Description.Id}'");
                lancesToSkip.Add(lanceGUID);
                return(true);
            }

            if (loadedLanceDef.IsATurretLance())
            {
                Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] [{teamOverride.faction}] LanceDef is a turret lance. Skipping '{loadedLanceDef.Description.Id}'");
                lancesToSkip.Add(lanceGUID);
                return(true);
            }

            return(false);
        }
    public static List <int> GetUnresolvedUnitIndexes(this LanceOverride lanceOverride, int startingIndex)
    {
        bool isManualLance = lanceOverride.lanceDefId.ToLower() == "manual";

        Debug.Log($"[ExtendedLances.GetUnresolvedUnitIndexes] Running with Autofill Type '{MissionControl.Main.Settings.ExtendedLances.AutofillType}' and '{(isManualLance ? "Manual" : "Tagged / Direct Reference")} Lance'");
        List <int> unresolvedUnitIndexes = new List <int>();

        if (MissionControl.Main.Settings.ExtendedLances.AutofillType == "RespectEmpty")
        {
            if (isManualLance)
            {
                // RespectEmpty and Manual Lance - Start counting from the original UnitOverride count up to the end
                for (int i = startingIndex; i < lanceOverride.unitSpawnPointOverrideList.Count; i++)
                {
                    UnitSpawnPointOverride unitOverride = lanceOverride.unitSpawnPointOverrideList[i];
                    if (unitOverride.IsUnresolved())
                    {
                        unresolvedUnitIndexes.Add(i);
                    }
                }
            }
            else // Tagged/Direct Lance Reference
            // RespectEmpty and Tagged/Direct Referenced Lance - Start counting from the LanceDef size up to the end
            {
                LanceDef loadedLanceDef = (LanceDef)AccessTools.Field(typeof(LanceOverride), "loadedLanceDef").GetValue(lanceOverride);
                if (loadedLanceDef == null)
                {
                    return(unresolvedUnitIndexes);
                }

                for (int i = loadedLanceDef.LanceUnits.Length; i < lanceOverride.unitSpawnPointOverrideList.Count; i++)
                {
                    UnitSpawnPointOverride unitOverride = lanceOverride.unitSpawnPointOverrideList[i];
                    if (unitOverride.IsUnresolved())
                    {
                        unresolvedUnitIndexes.Add(i);
                    }
                }
            }
        }
        else // FillEmpty
        // FillEmpty and Manual/Tagged/Direct Reference Lance- Start looking at all UnitOverrides and fill empty up to the end
        {
            for (int i = 0; i < lanceOverride.unitSpawnPointOverrideList.Count; i++)
            {
                UnitSpawnPointOverride unitOverride = lanceOverride.unitSpawnPointOverrideList[i];
                if (unitOverride.IsUnresolved())
                {
                    unresolvedUnitIndexes.Add(i);
                }
            }
        }

        return(unresolvedUnitIndexes);
    }
 // Checks if the LanceDef lance unit count should be used to override the Faction lance unit count
 // It does this by checking a set tag. If it's present then it will be forced.
 private bool IsLanceDefForced(LanceDef lanceDef)
 {
     if (lanceDef.LanceTags.GetTagSetSourceFile().Contains(Main.Settings.ExtendedLances.ForceLanceDefSizeWithTag))
     {
         Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] TagSetSourceFile '{lanceDef.LanceTags.GetTagSetSourceFile()}' contains tag '{Main.Settings.ExtendedLances.ForceLanceDefSizeWithTag}'");
         return(true);
     }
     else
     {
         Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] TagSetSourceFile '{lanceDef.LanceTags.GetTagSetSourceFile()}' DOES NOT contain tag '{Main.Settings.ExtendedLances.ForceLanceDefSizeWithTag}'");
     }
     return(false);
 }
Пример #5
0
    public static bool ContainsAtLeastOneTurret(this LanceDef lanceDef)
    {
        List <LanceDef.Unit> units = new List <LanceDef.Unit>(lanceDef.LanceUnits);

        for (int i = 0; i < units.Count; i++)
        {
            LanceDef.Unit unit = units[i];
            if (unit.unitType == BattleTech.UnitType.Turret)
            {
                return(true);
            }
        }

        return(false);
    }
Пример #6
0
 static void Prefix(SkirmishMechBayPanel __instance, LanceDef lance)
 {
     try {
         if (CustomUnitsAPI.Detected())
         {
             return;
         }
         int maxUnits = DropManager.DefaultMechSlots + DropManager.MaxAdditionalMechSlots;
         if (lance != null)
         {
             maxUnits = lance.LanceUnits.Length;
         }
         if (__instance.loadoutSlots.Length >= maxUnits)
         {
             return;
         }
         if (__instance.loadoutSlots.Length < 2)
         {
             maxUnits = __instance.loadoutSlots.Length; return;
         }
         ;
         float      ydelta             = __instance.loadoutSlots[1].GetComponent <RectTransform>().localPosition.y - __instance.loadoutSlots[0].GetComponent <RectTransform>().localPosition.y;
         int        addUnits           = maxUnits - __instance.loadoutSlots.Length;
         GameObject srcLayout          = __instance.loadoutSlots[__instance.loadoutSlots.Length - 1].gameObject;
         List <LanceLoadoutSlot> slots = new List <LanceLoadoutSlot>();
         slots.AddRange(__instance.loadoutSlots);
         for (int t = 0; t < addUnits; ++t)
         {
             GameObject    nLayout = GameObject.Instantiate(srcLayout, srcLayout.transform.parent);
             RectTransform rt      = nLayout.GetComponent <RectTransform>();
             Vector3       pos     = rt.localPosition;
             pos.y            = srcLayout.GetComponent <RectTransform>().localPosition.y + (t + 1) * ydelta;
             rt.localPosition = pos;
             slots.Add(nLayout.GetComponent <LanceLoadoutSlot>());
         }
         __instance.loadoutSlots = slots.ToArray();
     } catch (Exception e) {
         Logger.M.TWL(0, e.ToString());
     }
 }
Пример #7
0
        public MLanceOverride(LanceDef lanceDef)
        {
            this.lanceDefId  = lanceDef.Description.Id;
            this.lanceTagSet = lanceDef.LanceTags;

            List <UnitSpawnPointOverride> unitSpawnPointOverrides = new List <UnitSpawnPointOverride>();

            foreach (LanceDef.Unit unit in lanceDef.LanceUnits)
            {
                UnitSpawnPointOverride unitSpawnOverride = new UnitSpawnPointOverride();
                unitSpawnOverride.unitType            = unit.unitType;
                unitSpawnOverride.unitDefId           = unit.unitId;
                unitSpawnOverride.pilotDefId          = unit.pilotId;
                unitSpawnOverride.unitTagSet          = unit.unitTagSet;
                unitSpawnOverride.unitExcludedTagSet  = unit.excludedUnitTagSet;
                unitSpawnOverride.pilotTagSet         = unit.pilotTagSet;
                unitSpawnOverride.pilotExcludedTagSet = unit.excludedPilotTagSet;
                unitSpawnPointOverrides.Add(unitSpawnOverride);
            }

            this.unitSpawnPointOverrideList = unitSpawnPointOverrides;
        }
Пример #8
0
        public MLanceOverride GetLanceOverride(string key)
        {
            IDataItemStore <string, LanceDef> lanceDefs = UnityGameInstance.BattleTechGame.DataManager.LanceDefs;

            if (LanceOverrides.ContainsKey(key))
            {
                Main.Logger.Log($"[GetLanceOverride] Found a lance override for '{key}'");
                return(LanceOverrides[key].Copy());
            }

            LanceDef lanceDef = null;

            lanceDefs.TryGet(key, out lanceDef);
            if (lanceDef != null)
            {
                MLanceOverride lanceOverride = new MLanceOverride(lanceDef);
                LanceOverrides.Add(lanceOverride.lanceDefId, lanceOverride);
                Main.Logger.Log($"[GetLanceOverride] Found a lance def for '{key}', creating and caching a lance override for it. Using defaults of 'adjustedDifficulty' of '0' and no 'spawnEffectTags'");
                return(lanceOverride.Copy());
            }
            else
            {
                Main.Logger.Log($"[GetLanceOverride] No loaded LanceDef was found for '{key}'. Attempting to load the LanceDef.");
                lanceDef = BattleTechResourceLoader.LoadDefFromId <LanceDef>(key, BattleTechResourceType.LanceDef);
                DataManager.Instance.RequestResourcesAndProcess(BattleTechResourceType.LanceDef, key);

                if (lanceDef != null)
                {
                    MLanceOverride lanceOverride = new MLanceOverride(lanceDef);
                    LanceOverrides.Add(lanceOverride.lanceDefId, lanceOverride);
                    Main.Logger.Log($"[GetLanceOverride] Load succeeded. Found a lance def for '{key}', creating and caching a lance override for it. Using defaults of 'adjustedDifficulty' of '0' and no 'spawnEffectTags'");
                    return(lanceOverride.Copy());
                }
            }

            Main.Logger.LogError($"[GetLanceOverride] No MC Lance or LanceDef found with key '{key}'. This is a case sensitive search.'");
            return(null);
        }
Пример #9
0
        public MLanceOverride GetLanceOverride(string key)
        {
            IDataItemStore <string, LanceDef> lanceDefs = UnityGameInstance.BattleTechGame.DataManager.LanceDefs;

            if (LanceOverrides.ContainsKey(key))
            {
                Main.Logger.Log($"[GetLanceOverride] Found a lance override for '{key}'");
                return(LanceOverrides[key]);
            }

            LanceDef lanceDef = null;

            lanceDefs.TryGet(key, out lanceDef);
            if (lanceDef != null)
            {
                MLanceOverride lanceOverride = new MLanceOverride(lanceDef);
                LanceOverrides.Add(lanceOverride.lanceDefId, lanceOverride);
                Main.Logger.Log($"[GetLanceOverride] Found a lance def for '{key}', creating and caching a lance override for it. Using defaults of 'adjustedDifficulty - 0' and no 'spawnEffectTags'");
                return(lanceOverride);
            }

            return(null);
        }
Пример #10
0
 static void Postfix(LanceDef __instance, LanceDef __result)
 {
     __result.LanceTags.SetTagSetSourceFile(cachedTagSetSourceFile);
     cachedTagSetSourceFile = null;
 }
Пример #11
0
 static void Prefix(LanceDef __instance)
 {
     cachedTagSetSourceFile = __instance.LanceTags.GetTagSetSourceFile();
 }
        public override void Run(RunPayload payload)
        {
            Main.Logger.Log($"[AddExtraLanceMembersIndividualSecondPass] Running second pass after LanceDef has resolved, if required");
            ContractOverride contractOverride = ((ContractAndLanceOverridePayload)payload).ContractOverride;
            LanceOverride    lanceOverride    = ((ContractAndLanceOverridePayload)payload).LanceOverride;
            bool             isManualLance    = lanceOverride.lanceDefId == "Manual";
            int currentLanceSize = lanceOverride.unitSpawnPointOverrideList.Count;

            TeamOverride teamOverride = contractOverride.GetTeamOverrideLanceBelongsTo(lanceOverride.GUID);

            Main.Logger.Log($"[AddExtraLanceMembersIndividualSecondPass] Team Override for lance '{lanceOverride.name} - {lanceOverride.GUID}' is: {teamOverride.teamName}");

            // GUARD: Don't process factions that aren't allowed
            if (!IsTeamAllowedExtendedLances(contractOverride, teamOverride))
            {
                Main.Logger.Log($"[AddExtraLanceMembersIndividualSecondPass] Ignoring lance '{lanceOverride.name} - {lanceOverride.GUID}' is: {teamOverride.teamName}. Team is not allowed to be extended.");
                return;
            }

            lancesToSkip = (List <string>)state.GetObject("LancesToSkip");

            // Check first pass LanceOverride skips and check LanceDef skips in this second pass, if one exists, and check tags for skipping or override
            if (!isManualLance)
            {
                LanceDef loadedLanceDef = (LanceDef)AccessTools.Field(typeof(LanceOverride), "loadedLanceDef").GetValue(lanceOverride);
                Main.Logger.Log($"[AddExtraLanceMembersIndividualSecondPass] Loaded LanceDef is '{loadedLanceDef.Description.Id}'");

                bool skip = CheckForLanceOverrideSkips(lanceOverride, teamOverride, lanceOverride.GUID);
                if (!skip)
                {
                    skip = CheckForLanceDefSkips(loadedLanceDef, teamOverride, lanceOverride.GUID);
                }

                if (skip)
                {
                    return;
                }


                Main.Logger.Log($"[AddExtraLanceMembersIndividualSecondPass] No Skips Detected. Processing second pass.");

                // Check for LanceDef tags to force LanceDef to override the EL lance unit count
                if (IsLanceDefForced(loadedLanceDef))
                {
                    this.state.Set($"LANCE_DEF_FORCED_{lanceOverride.GUID}", true);

                    int newLanceSize = loadedLanceDef.LanceUnits.Length;
                    Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] Force overriding lance def '{lanceOverride.name}' from faction size of '{currentLanceSize}' to '{newLanceSize}'");

                    if (newLanceSize < currentLanceSize)
                    {
                        // Remove UnitOverrides. Last to First. This is because the override in the LanceDef has fewer units that the EL faction size, or forced Contract Override size
                        for (int i = currentLanceSize - 1; i >= newLanceSize; i--)
                        {
                            Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] Removing UnitOverride '{i + 1}' from LanceOverride");
                            lanceOverride.unitSpawnPointOverrideList.RemoveAt(i);
                        }
                    }
                    else if (newLanceSize > currentLanceSize)
                    {
                        // Add UnitOverrides. This is because the override in the LanceDef has more units that the EL faction size, or forced Contract Override size
                        // This allows the LanceOverride to allocated the correct LanceDef units to the right UnitOverride slots
                        UnitSpawnPointOverride emptyUnitSpawnPointOverride = new UnitSpawnPointOverride();
                        emptyUnitSpawnPointOverride.unitDefId = UnitSpawnPointOverride.UseLance;

                        for (int i = currentLanceSize; i < newLanceSize; i++)
                        {
                            Main.LogDebug($"[AddExtraLanceMembersIndividualSecondPass] Adding UnitOverride '{i + 1}' to LanceOverride");
                            lanceOverride.unitSpawnPointOverrideList.Add(emptyUnitSpawnPointOverride.DeepCopy());
                        }
                    }
                }
            }
        }
        private void ReplaceUnresolvedUnitOverride(List <string> unitSpawnPointGameLogicGUIDs, TeamOverride teamOverride, LanceOverride lanceOverride, LanceDef loadedLanceDef, List <int> unresolvedIndexes)
        {
            // Get all UnitSpawnPointGameLogic GUIDs
            List <string>  availableUnitSpawnPointGameLogicGUIDsList = new List <string>(unitSpawnPointGameLogicGUIDs);
            Stack <string> availableUnitSpawnPointGameLogicGUIDsStack;

            // Ensure no duplicates exist. If so, modder error in their set up.
            if (unitSpawnPointGameLogicGUIDs.Distinct().ToList().Count != unitSpawnPointGameLogicGUIDs.Count())
            {
                Main.Logger.LogError($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] The lance '{lanceOverride.GUID}' has duplicate UnitSpawnPointOverride GUIDs. This is incorrect and will cause some units not to spawn! This is not a problem with MC. Please fix this in the contract override data!");
            }

            // Remove any available UnitSpawnPointGameLogicGUIDs that are correctly set in the UnitSpawnPointOverrides
            // The remaining GUIDs are from unassigned UnitSpawnPointGameLogics and they can be assigned below
            foreach (UnitSpawnPointOverride unitSpawnPointOverride in lanceOverride.unitSpawnPointOverrideList)
            {
                if (availableUnitSpawnPointGameLogicGUIDsList.Contains(unitSpawnPointOverride.GUID))
                {
                    availableUnitSpawnPointGameLogicGUIDsList.Remove(unitSpawnPointOverride.GUID);
                }
            }

            Main.Logger.LogDebug($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] AvailableUnitSpawnPointGameLogicGUIDs will contain Game Logic GUID: '{string.Join(", ", unitSpawnPointGameLogicGUIDs)}'");
            availableUnitSpawnPointGameLogicGUIDsStack = new Stack <string>(availableUnitSpawnPointGameLogicGUIDsList);

            foreach (int index in unresolvedIndexes)
            {
                UnitSpawnPointOverride originalUnitSpawnPointOverride = lanceOverride.GetUnitToCopy();
                UnitSpawnPointOverride unitSpawnPointOverride         = originalUnitSpawnPointOverride.DeepCopy();

                if (unitSpawnPointGameLogicGUIDs.Count < index)
                {
                    Main.Logger.LogError($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] There are more unit overrides in lance '{lanceOverride.name} - {lanceOverride.GUID}' than unit spawn points in LanceSpawner. This should never happen.");
                }

                string indexUnitSpawnPointOverrideGUID = lanceOverride.unitSpawnPointOverrideList[index].GUID;
                Main.Logger.LogDebug($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] [Unit{index + 1}] Unit GUID is '{indexUnitSpawnPointOverrideGUID}'");
                if (unitSpawnPointGameLogicGUIDs.Contains(indexUnitSpawnPointOverrideGUID))
                {
                    unitSpawnPointOverride.unitSpawnPoint.EncounterObjectGuid = indexUnitSpawnPointOverrideGUID; // If force resolving - then ensure GUIDs for spawner unit spawns are maintained
                }
                else
                {
                    if (availableUnitSpawnPointGameLogicGUIDsStack.Count > 0)
                    {
                        string guid = availableUnitSpawnPointGameLogicGUIDsStack.Pop();
                        Main.Logger.LogDebug($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] [Unit{index + 1}] GUID '{unitSpawnPointOverride.unitSpawnPoint.EncounterObjectGuid}' does not exist for a UnitSpawnerGameLogic object. Reassigning with GUID '{guid}'");
                        unitSpawnPointOverride.unitSpawnPoint.EncounterObjectGuid = guid; // If force resolving - then ensure GUIDs for spawner unit spawns are maintained
                    }
                    else
                    {
                        Main.Logger.LogError($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] [Faction:{teamOverride.faction}] [Unit{index + 1}] No avaiable spare unit spawner guids to assign to unit override. This should never happen!");
                    }
                }

                unitSpawnPointOverride.customUnitName = "";
                TagSet companyTags = new TagSet(UnityGameInstance.BattleTechGame.Simulation.CompanyTags);

                Main.LogDebug($"[AddExtraLanceSpawnPoints.ReplaceUnresolvedUnitOverride] Generating unresolved unit '{index + 1}'");
                unitSpawnPointOverride.GenerateUnit(MetadataDatabase.Instance, UnityGameInstance.Instance.Game.DataManager, lanceOverride.selectedLanceDifficulty, lanceOverride.name, loadedLanceDef == null ? null : loadedLanceDef.Description.Id, index, DataManager.Instance.GetSimGameCurrentDate(), companyTags);
                lanceOverride.unitSpawnPointOverrideList[index] = unitSpawnPointOverride;
            }
        }
Пример #14
0
 public static bool IsATurretLance(this LanceDef lanceDef)
 {
     return(lanceDef.ContainsTurretTag() || lanceDef.ContainsAtLeastOneTurret());
 }
Пример #15
0
 public static bool ContainsTurretTag(this LanceDef lanceDef)
 {
     return(lanceDef.LanceTags.Contains("lance_type_turret"));
 }
Пример #16
0
 static void Postfix(LanceConfiguratorPanel __instance, string lanceId, ref LanceDef __result)
 {
     LanceLoadoutSlot[] loadoutSlots = (LanceLoadoutSlot[])AccessTools.Field(typeof(LanceConfiguratorPanel), "loadoutSlots").GetValue(__instance);
     Logger.M.TWL(0, "LanceConfiguratorPanel.CreateLanceDef result:", true);
     Logger.M.WL(0, __result.ToJSON());
 }
Пример #17
0
 static void Prefix(LancePreviewPanel __instance, LanceDef lanceToSave)
 {
     Logger.M.TWL(0, "LancePreviewPanel.SaveLance", true);
     Logger.M.WL(0, lanceToSave.ToJSON(), true);
 }
        private void IncreaseLanceSpawnPoints(ContractOverride contractOverride, TeamOverride teamOverride)
        {
            List <LanceOverride> lanceOverrides = teamOverride.lanceOverrideList;
            List <string>        lancesToDelete = new List <string>();

            for (int i = 0; i < lanceOverrides.Count; i++)
            {
                LanceOverride lanceOverride = lanceOverrides[i];
                bool          isManualLance = lanceOverride.lanceDefId == "Manual";

                if (lanceOverride.IsATurretLance())
                {
                    Main.Logger.LogDebug($"[AddExtraLanceSpawnPoints] Detected a turret lance. Skipping.");
                    continue;
                }

                // At this point the number of units in a lance should be the expected amount.
                // The unitSpawnPointOverrides will be up to the EL limit set. They will be either:
                //  - Empty, Null, MechDef_None, Vehicle_None, Turret_None (Because they were a non-inheriting unit, manually entered as such or the LanceDef didn't have enough units to fill up the UnitOverride slots)
                //  - Filled resolved units (Because they were resolved by the LanceOverride LanceDef, or manually entered into the Contract Override)
                //  - 'Tagged', 'UseLance' or 'Manual' slots (Because they were not filled up by the LanceOverride LanceDef selection or Autofilled in Pass 1)
                int numberOfUnitsInLance = lanceOverride.unitSpawnPointOverrideList.Count;

                if (CheckForLanceSkips(teamOverride, lanceOverride))
                {
                    Main.Logger.LogDebug($"[AddExtraLanceSpawnPoints] Detected a skip for this Lance. Skipping.");
                    continue;
                }

                LanceSpawnerGameLogic lanceSpawner = lanceSpawners.Find(spawner => spawner.GUID == lanceOverride.lanceSpawner.EncounterObjectGuid);
                if (lanceSpawner != null)
                {
                    AddSpawnPoints(lanceSpawner, teamOverride, lanceOverride, numberOfUnitsInLance);
                }
                else
                {
                    Main.Logger.LogWarning($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Spawner is null for {lanceOverride.lanceSpawner.EncounterObjectGuid}. This is probably data from a restarted contract that hasn't been cleared up. It can be safely ignored.");
                    lancesToDelete.Add(lanceOverride.lanceSpawner.EncounterObjectGuid);
                }


                if (Main.Settings.ExtendedLances.IsAutofillAllowed(contractOverride))
                {
                    // GUARD: If an AdditionalLance lance config has been set to 'supportAutoFill' false, then don't autofill
                    if (lanceOverride is MLanceOverride)
                    {
                        MLanceOverride mLanceOverride = (MLanceOverride)lanceOverride;
                        if (!mLanceOverride.SupportAutofill)
                        {
                            Main.LogDebug($"[AddExtraLanceSpawnPoints] Lance Override '{lanceOverride.name} - {mLanceOverride.GUID}' has 'autofill' explicitly turned off in MC lance '{mLanceOverride.LanceKey}'");
                            continue;
                        }
                    }

                    bool lanceOverrideForced = this.state.GetBool($"LANCE_OVERRIDE_FORCED_{lanceOverride.GUID}");
                    bool lanceDefForced      = this.state.GetBool($"LANCE_DEF_FORCED_{lanceOverride.GUID}");
                    if (lanceOverrideForced || lanceDefForced)
                    {
                        Main.LogDebug($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Detected that lance '{lanceOverride.name} - {lanceOverride.GUID}' was forced using a LanceOverride or LanceDef EL enforcement. Skipping autofill.");
                        continue;
                    }

                    List <GameObject> unitSpawnPoints = lanceSpawner.gameObject.FindAllContains("UnitSpawnPoint");

                    if (unitSpawnPoints.Count <= 0)
                    {
                        Main.Logger.LogError($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Lance '{lanceOverride.name} - {lanceOverride.GUID}' has no UnitSpawnPoints. A Lance must have at least one unit spawn point to be valid");
                    }

                    List <string> unitSpawnPointGameLogicGUIDs = (List <string>)unitSpawnPoints.Select(unitSpawnPointGO => unitSpawnPointGO.GetComponent <UnitSpawnPointGameLogic>().GUID).ToList();

                    // Only replace unresolved unit overrides if autofill is on
                    int        originalLanceOverrideSize = this.state.GetInt($"LANCE_ORIGINAL_UNIT_OVERRIDE_COUNT_{lanceOverride.GUID}");
                    List <int> unresolvedIndexes         = lanceOverride.GetUnresolvedUnitIndexes(originalLanceOverrideSize);
                    Main.LogDebug($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Detected '{unresolvedIndexes.Count}' unresolved unit spawn overrides. Will resolve them before building spawn points.");
                    if (unresolvedIndexes.Count > 0)
                    {
                        LanceDef loadedLanceDef = null;

                        if (!isManualLance)
                        {
                            loadedLanceDef = (LanceDef)AccessTools.Field(typeof(LanceOverride), "loadedLanceDef").GetValue(lanceOverride);
                            Main.LogDebug($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Loaded LanceDef is '{loadedLanceDef.Description.Id}'");
                        }

                        ReplaceUnresolvedUnitOverride(unitSpawnPointGameLogicGUIDs, teamOverride, lanceOverride, loadedLanceDef, unresolvedIndexes);
                    }

                    // Fix any unmatching UnitSpawnPointOverrideGUIDs-to-UnitSpawnPointGameLogicGUIDs
                    FixMisMatchedGUIDs(unitSpawnPointGameLogicGUIDs, teamOverride, lanceOverride);
                }
            }

            for (int i = (lanceOverrides.Count - 1); i >= 0; i--)
            {
                LanceOverride lanceOverride = lanceOverrides[i];

                foreach (string lanceToDeleteByGuid in lancesToDelete)
                {
                    if (lanceOverride.lanceSpawner.EncounterObjectGuid == lanceToDeleteByGuid)
                    {
                        Main.Logger.LogWarning($"[AddExtraLanceSpawnPoints] [Faction:{teamOverride.faction}] Removing old lance data from contract. Deleting lance '{lanceToDeleteByGuid}'");
                        lanceOverrides.Remove(lanceOverride);
                    }
                }
            }
        }