Decompiled source of LazyOutposting v1.4.5

LazyOutposting.dll

Decompiled a month ago
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Threading;
using BepInEx;
using BepInEx.Bootstrap;
using BepInEx.Configuration;
using BepInEx.Logging;
using Eirshy.DSP.LazyOutposting.Bugfix;
using Eirshy.DSP.LazyOutposting.Components;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyCompany("LazyOutposting")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("My first plugin")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+e9dcce8a3ad30c4bc33fcbc76c3b676de875a798")]
[assembly: AssemblyProduct("LazyOutposting")]
[assembly: AssemblyTitle("LazyOutposting")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace Eirshy.DSP.LazyOutposting
{
	internal static class Extensions
	{
		public static void Reop(this CodeInstruction ci, OpCode op, object operand = null)
		{
			ci.opcode = op;
			ci.operand = operand;
		}
	}
	[BepInPlugin("eirshy.dsp.LazyOutposting", "Lazy Outposting", "1.4.5")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	public class LazyOutposting : BaseUnityPlugin
	{
		public const string MODID = "LazyOutposting";

		public const string ROOT = "eirshy.dsp.";

		public const string GUID = "eirshy.dsp.LazyOutposting";

		public const string VERSION = "1.4.5";

		public const string NAME = "Lazy Outposting";

		internal const string OTHERMOD_BPTWEEKS = "org.kremnev8.plugin.BlueprintTweaks";

		internal const string OTHERMOD_VEINITYPROJECT = "eirshy.dsp.VeinityProject";

		private static readonly Lazy<Harmony> _harmony = new Lazy<Harmony>((Func<Harmony>)(() => new Harmony("eirshy.dsp.LazyOutposting")));

		private static bool _GiveDwarvesBuckets = true;

		internal static readonly Lazy<bool> VeinityProjectExists = new Lazy<bool>(() => Chainloader.PluginInfos.ContainsKey("eirshy.dsp.VeinityProject"), LazyThreadSafetyMode.PublicationOnly);

		public static uint OnKey = 0u;

		private static Lazy<FieldInfo[]> _cloner = new Lazy<FieldInfo[]>(() => typeof(PrefabDesc).GetFields(BindingFlags.Instance | BindingFlags.Public), LazyThreadSafetyMode.PublicationOnly);

		internal static Harmony Harmony => _harmony.Value;

		internal static ManualLogSource Logs { get; private set; }

		internal static bool EnableVaporCollection { get; private set; } = true;


		internal static bool EnableOptimizationsOnly { get; private set; } = false;


		internal static bool GiveDwarvesHaulers { get; private set; } = true;


		internal static bool GiveDwarvesBuckets
		{
			get
			{
				if (_GiveDwarvesBuckets)
				{
					return VeinityProjectExists.Value;
				}
				return false;
			}
			set
			{
				_GiveDwarvesBuckets = value;
			}
		}

		internal static bool GiveDwarvesShovels { get; private set; } = false;


		internal static bool GiveDwarvesLongPicks { get; private set; } = false;


		private void Awake()
		{
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Expected O, but got Unknown
			//IL_027f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0289: Expected O, but got Unknown
			//IL_02b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02bd: Expected O, but got Unknown
			//IL_02e7: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f1: Expected O, but got Unknown
			//IL_031b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0325: Expected O, but got Unknown
			//IL_034f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0359: Expected O, but got Unknown
			//IL_0383: Unknown result type (might be due to invalid IL or missing references)
			//IL_038d: Expected O, but got Unknown
			//IL_0068: Unknown result type (might be due to invalid IL or missing references)
			//IL_006e: Expected O, but got Unknown
			//IL_03d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_03e1: Expected O, but got Unknown
			Logs = ((BaseUnityPlugin)this).Logger;
			((BaseUnityPlugin)this).Logger.LogMessage((object)"Lazy Outposting - For anywhere but Hoxxes IV!");
			ConfigEntry<string> val = ((BaseUnityPlugin)this).Config.Bind<string>("LazyOutposting", "ConfigVersion", "0.0.0", new ConfigDescription("Internal value used to migrate settings.", (AcceptableValueBase)null, Array.Empty<object>()));
			bool flag = val.Value != "1.4.5";
			if (flag)
			{
				ConfigDescription val2 = new ConfigDescription("Legacy setting name. Should be removed.", (AcceptableValueBase)null, Array.Empty<object>());
				List<ConfigDefinition> list = new List<ConfigDefinition>();
				Dictionary<string, bool> dictionary = new Dictionary<string, bool>(2)
				{
					{ "true", true },
					{ "false", false }
				};
				int result;
				List<int> list2 = (from x in val.Value.Split(new char[1] { '.' })
					select int.TryParse(x, out result) ? result : 0).ToList();
				int num = ((list2.Count >= 3) ? ((list2[0] == 1 && list2[1] < 3) ? 1 : 2) : 0);
				if (num < 1)
				{
					ConfigEntry<string> val3 = ((BaseUnityPlugin)this).Config.Bind<string>("LazyOutposting", "EnableDwarvenCommute", "", val2);
					if (dictionary.TryGetValue(val3.Value.ToLower(), out var value))
					{
						GiveDwarvesHaulers = value;
					}
					list.Add(((ConfigEntryBase)val3).Definition);
				}
				if (num < 1)
				{
					ConfigEntry<string> val3 = ((BaseUnityPlugin)this).Config.Bind<string>("LazyOutposting", "GiveDwarvesBuckets", "", val2);
					if (dictionary.TryGetValue(val3.Value.ToLower(), out var value2))
					{
						GiveDwarvesBuckets = value2;
					}
					list.Add(((ConfigEntryBase)val3).Definition);
				}
				if (num < 2)
				{
					ConfigEntry<string> val3 = ((BaseUnityPlugin)this).Config.Bind<string>("LazyOutposting.DwarvenContract", "GiveTechDwarvesLongPicks", "", val2);
					if (dictionary.TryGetValue(val3.Value.ToLower(), out var value3))
					{
						GiveDwarvesLongPicks = value3;
					}
					list.Add(((ConfigEntryBase)val3).Definition);
				}
				val.Value = "1.4.5";
				Logs.LogWarning((object)$"Removed: ${(from b in ((IEnumerable<ConfigDefinition>)list).Select((Func<ConfigDefinition, bool>)((BaseUnityPlugin)this).Config.Remove)
					where b
					select b).Count()}/{list.Count}");
			}
			EnableVaporCollection = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting", "EnableVaporCollection", EnableVaporCollection, new ConfigDescription("If we should enable ocean collection regardless of said ocean being accessible.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			EnableOptimizationsOnly = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.DwarvenContract", "EnableOptimizationsOnly", EnableOptimizationsOnly, new ConfigDescription("If enabled, we'll run only the optimization components of our miner changes, and ignnore any non-vanilla-like settings under this header.\nMostly, this fixes the memory thrashing caused by Miner Mk2s.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			GiveDwarvesHaulers = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.DwarvenContract", "GiveDwarvesHaulers", GiveDwarvesHaulers, new ConfigDescription("If we should enable planet-wide mining. Usable by both regular miners and mk2 miners.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			GiveDwarvesBuckets = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.DwarvenContract", "GiveDwarvesBuckets", GiveDwarvesBuckets, new ConfigDescription("Requires the mod VeinityProject, otherwise will be ignored.\nIf we should allow miners to collect oil. Note that only Tech Dwarves (Mk2 Miners (Miner Collectors)) can perform this action without Haulers.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			GiveDwarvesLongPicks = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.DwarvenContract", "GiveDwarvesLongPicks", GiveDwarvesLongPicks, new ConfigDescription("If we should change the way mines pick veins to be \"fuzzy\".\nIf set, still requires *a* vein to be in the machine's target zone, but will grab any vein of the same type within the scanning zone. Additionally, enables Shovels, as testing height in this mode is difficult.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			GiveDwarvesShovels = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.DwarvenContract", "GiveDwarvesShovels", GiveDwarvesShovels, new ConfigDescription("If we should ignore vein height (ie, whether the vein's been burried).\nNote that this is implied by Long Picks, due to a difficulty in implementing Long Picks without Shovels.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			bool num2 = EnableOptimizationsOnly || GiveDwarvesBuckets || GiveDwarvesHaulers || GiveDwarvesLongPicks || GiveDwarvesShovels;
			bool value4 = ((BaseUnityPlugin)this).Config.Bind<bool>("LazyOutposting.zz.BugFixes", "Fix Issues: v1.3.0-v1.3.2", false, new ConfigDescription("If we should run the on-game-load fixes for save game issues created by v1.3.0 through v1.3.2 of this mod.\nRequires us to iterate through all stations on all planets to reconnect parents. Note that deconstructing and reconstructing an affected VeinCollector (speed slider is broken) will also fix this issue.", (AcceptableValueBase)null, Array.Empty<object>())).Value;
			if (flag)
			{
				((BaseUnityPlugin)this).Config.Save();
			}
			if (num2)
			{
				DwarvenContract.SetUp();
			}
			if (EnableVaporCollection)
			{
				VaporCollection.SetUp();
			}
			if (value4)
			{
				Harmony.PatchAll(typeof(Bugfix_v1_3_lt3));
			}
		}

		private void Update()
		{
			if (Input.GetKeyDown((KeyCode)281))
			{
				OnKey--;
			}
			if (Input.GetKeyDown((KeyCode)280))
			{
				OnKey++;
			}
		}

		internal static PrefabDesc ClonePrefab(PrefabDesc from)
		{
			//IL_0000: Unknown result type (might be due to invalid IL or missing references)
			//IL_0006: Expected O, but got Unknown
			PrefabDesc val = new PrefabDesc();
			FieldInfo[] value = _cloner.Value;
			foreach (FieldInfo fieldInfo in value)
			{
				fieldInfo.SetValue(val, fieldInfo.GetValue(from));
			}
			return val;
		}
	}
	public static class PluginInfo
	{
		public const string PLUGIN_GUID = "LazyOutposting";

		public const string PLUGIN_NAME = "LazyOutposting";

		public const string PLUGIN_VERSION = "1.0.0";
	}
}
namespace Eirshy.DSP.LazyOutposting.Components
{
	internal static class DwarvenContract
	{
		private readonly struct DwarfMission
		{
			[Flags]
			internal enum EGear
			{
				StandardOnly = 0,
				Buckets = 1,
				Haulers = 2,
				LongPicks = 4,
				Shovels = 8
			}

			public readonly EGear Equipment;

			public readonly bool HasBuckets;

			public readonly bool HasLongPicks;

			public readonly bool HasShovels;

			private readonly EVeinType[] _hauling;

			private readonly bool[] _dwarfTargets;

			public EVeinType CommuteVein => _hauling[LazyOutposting.OnKey % _hauling.Length];

			public bool HaulersNotActive => (int)CommuteVein == 0;

			public bool CanTarget(EVeinType veinType)
			{
				//IL_0006: Unknown result type (might be due to invalid IL or missing references)
				return _dwarfTargets[veinType];
			}

			public DwarfMission(EGear withGear)
			{
				//IL_0107: Unknown result type (might be due to invalid IL or missing references)
				//IL_010d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0129: Unknown result type (might be due to invalid IL or missing references)
				Equipment = withGear;
				EVeinType[] source = (EVeinType[])Enum.GetValues(typeof(EVeinType));
				HashSet<EVeinType> stdBan = new HashSet<EVeinType>(3)
				{
					(EVeinType)0,
					(EVeinType)15,
					(EVeinType)7
				};
				List<EVeinType> list = source.Where((EVeinType evt) => !stdBan.Contains(evt)).ToList();
				HasBuckets = Equipment.HasFlag(EGear.Buckets);
				if (HasBuckets)
				{
					list.Add((EVeinType)7);
				}
				HasLongPicks = Equipment.HasFlag(EGear.LongPicks);
				HasShovels = HasLongPicks || Equipment.HasFlag(EGear.Shovels);
				if (Equipment.HasFlag(EGear.Haulers))
				{
					_hauling = list.Prepend((EVeinType)0).ToArray();
				}
				else
				{
					_hauling = (EVeinType[])(object)new EVeinType[1];
				}
				_dwarfTargets = new bool[source.Max() + 1];
				int count = list.Count;
				while (count-- > 0)
				{
					_dwarfTargets[list[count]] = true;
				}
			}
		}

		private static DwarfMission Mission;

		private static readonly Lazy<MethodInfo> MinerIsVeinInRange = new Lazy<MethodInfo>(() => typeof(MinerComponent).GetMethod("IsTargetVeinInRange", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic), LazyThreadSafetyMode.PublicationOnly);

		private static readonly ConcurrentDictionary<int, PrefabDesc> ForgeriesNonMiner = new ConcurrentDictionary<int, PrefabDesc>();

		private static int[] VC_NULL_PARAMS => Array.Empty<int>();

		public static void SetUp()
		{
			DwarfMission.EGear withGear = DwarfMission.EGear.StandardOnly | (LazyOutposting.GiveDwarvesHaulers ? DwarfMission.EGear.Haulers : DwarfMission.EGear.StandardOnly) | (LazyOutposting.GiveDwarvesBuckets ? DwarfMission.EGear.Buckets : DwarfMission.EGear.StandardOnly) | (LazyOutposting.GiveDwarvesLongPicks ? DwarfMission.EGear.LongPicks : DwarfMission.EGear.StandardOnly) | (LazyOutposting.GiveDwarvesShovels ? DwarfMission.EGear.Shovels : DwarfMission.EGear.StandardOnly);
			if (LazyOutposting.EnableOptimizationsOnly)
			{
				withGear = DwarfMission.EGear.StandardOnly;
			}
			Mission = new DwarfMission(withGear);
			LazyOutposting.Harmony.PatchAll(typeof(DwarvenContract));
		}

		private static PrefabDesc GetForgeryNonMiner(PrefabDesc pd)
		{
			return ForgeriesNonMiner.GetOrAdd(pd.modelIndex, (Func<int, PrefabDesc>)ForgeAsNonMiner);
		}

		private static PrefabDesc ForgeAsNonMiner(int id)
		{
			//IL_001e: Unknown result type (might be due to invalid IL or missing references)
			PrefabDesc obj = LazyOutposting.ClonePrefab(((ProtoSet<ModelProto>)(object)LDB.models).Select(id).prefabDesc);
			obj.veinMiner = false;
			obj.minerType = (EMinerType)0;
			return obj;
		}

		private static PrefabDesc GetOriginal(PrefabDesc pd)
		{
			return ((ProtoSet<ModelProto>)(object)LDB.models).Select(pd.modelIndex).prefabDesc;
		}

		[HarmonyPrefix]
		[HarmonyPatch(typeof(BuildTool_Click), "CheckBuildConditions")]
		private static void PresentForgedPapers(BuildTool_Click __instance, ref int[] ____tmp_ids, ref List<BuildPreview> __state, ref bool __runOriginal, ref bool __result)
		{
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0063: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f9: Unknown result type (might be due to invalid IL or missing references)
			//IL_0105: Unknown result type (might be due to invalid IL or missing references)
			//IL_010a: Unknown result type (might be due to invalid IL or missing references)
			//IL_013d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0157: Unknown result type (might be due to invalid IL or missing references)
			//IL_015c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0160: Unknown result type (might be due to invalid IL or missing references)
			//IL_0165: Unknown result type (might be due to invalid IL or missing references)
			//IL_016a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0177: Unknown result type (might be due to invalid IL or missing references)
			//IL_0184: Unknown result type (might be due to invalid IL or missing references)
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0204: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_01d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e4: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_025b: Unknown result type (might be due to invalid IL or missing references)
			//IL_025f: Unknown result type (might be due to invalid IL or missing references)
			//IL_026c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0271: Unknown result type (might be due to invalid IL or missing references)
			if (!__runOriginal)
			{
				return;
			}
			EVeinType commuteVein = Mission.CommuteVein;
			VeinData[] veinPool = ((BuildTool)__instance).factory.veinPool;
			Pose val = default(Pose);
			foreach (BuildPreview buildPreview in ((BuildTool)__instance).buildPreviews)
			{
				BuildPreview pv = buildPreview;
				if (!pv.desc.veinMiner || (pv.desc.waterPoints != null && pv.desc.waterPoints.Length != 0))
				{
					continue;
				}
				if ((int)commuteVein != 0)
				{
					int[] array = null;
					if (array == null)
					{
						List<int> list = new List<int>();
						int num = veinPool.Length;
						while (num-- > 0)
						{
							if (veinPool[num].type == commuteVein)
							{
								list.Add(veinPool[num].id);
							}
						}
						array = list.ToArray();
					}
					if (array.Length != 0)
					{
						pv.parameters = array;
						pv.paramCount = array.Length;
						pv.filterId = veinPool[array[0]].productId;
						SwapToForged(in __instance, in pv, ref __state);
						continue;
					}
				}
				((Pose)(ref val))..ctor(pv.lpos, pv.lrot);
				Vector3 forward = ((Pose)(ref val)).forward;
				float num2;
				float num3;
				if (pv.desc.isVeinCollector)
				{
					num2 = -10f;
					num3 = 18f;
				}
				else
				{
					num2 = -1.2f;
					num3 = 12f;
				}
				Vector3 val2 = ((Vector3)(ref pv.lpos)).normalized * ((Vector3)(ref ((BuildTool)__instance).controller.cmd.test)).magnitude + forward * num2;
				int veinsInAreaNonAlloc = ((BuildTool)__instance).actionBuild.nearcdLogic.GetVeinsInAreaNonAlloc(val2, num3, ref ____tmp_ids);
				EVeinType val3 = (EVeinType)0;
				bool hasLongPicks = Mission.HasLongPicks;
				int num4 = veinsInAreaNonAlloc;
				while (num4-- > 0)
				{
					int num5 = ____tmp_ids[num4];
					if (num5 > 0)
					{
						ref VeinData reference = ref veinPool[num5];
						if (reference.id == num5 && Mission.CanTarget(reference.type) && MinerComponent.IsTargetVeinInRange(reference.pos, val, pv.desc))
						{
							val3 = reference.type;
							pv.filterId = reference.productId;
							break;
						}
					}
				}
				if ((int)val3 == 0)
				{
					pv.parameters = VC_NULL_PARAMS;
					pv.paramCount = 0;
					ConditionFail((EBuildCondition)26, in __instance, ref __runOriginal, ref __result);
					break;
				}
				List<int> list2 = new List<int>(veinsInAreaNonAlloc);
				int num6 = veinsInAreaNonAlloc;
				while (num6-- > 0)
				{
					int num7 = ____tmp_ids[num6];
					if (num7 > 0)
					{
						ref VeinData reference2 = ref veinPool[num7];
						if (reference2.id == num7 && val3 == reference2.type && (hasLongPicks || MinerComponent.IsTargetVeinInRange(reference2.pos, val, pv.desc)))
						{
							list2.Add(num7);
						}
					}
				}
				if (pv.parameters == VC_NULL_PARAMS)
				{
					pv.parameters = new int[veinsInAreaNonAlloc];
				}
				else
				{
					Array.Resize(ref pv.parameters, list2.Count);
				}
				list2.CopyTo(pv.parameters);
				pv.paramCount = list2.Count;
				SwapToForged(in __instance, in pv, ref __state);
			}
		}

		[MethodImpl(MethodImplOptions.AggressiveInlining)]
		private static void ConditionFail(EBuildCondition condition, in BuildTool_Click __instance, ref bool __runOriginal, ref bool __result)
		{
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			__runOriginal = false;
			__result = false;
			((BuildTool)__instance).actionBuild.model.cursorState = -1;
			((BuildTool)__instance).actionBuild.model.cursorText = BuildPreview.GetConditionText(condition);
		}

		[MethodImpl(MethodImplOptions.AggressiveInlining)]
		private static void SwapToForged(in BuildTool_Click __instance, in BuildPreview pv, ref List<BuildPreview> __state)
		{
			if (__state == null)
			{
				__state = new List<BuildPreview>(((BuildTool)__instance).buildPreviews.Count);
			}
			pv.desc = GetForgeryNonMiner(pv.desc);
			__state.Add(pv);
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(BuildTool_Click), "CheckBuildConditions")]
		private static void SwitchBackToRealPapers(ref List<BuildPreview> __state)
		{
			if (__state == null)
			{
				return;
			}
			foreach (BuildPreview item in __state)
			{
				item.desc = GetOriginal(item.desc);
			}
		}

		[HarmonyPrefix]
		[HarmonyPatch(typeof(PlanetFactory), "CreateEntityLogicComponents")]
		private static void ForgePlanetFactoryHandling(int entityId, ref PrefabDesc desc, int prebuildId, in PlanetFactory __instance, ref int __state)
		{
			//IL_0002: Unknown result type (might be due to invalid IL or missing references)
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_001c: Invalid comparison between Unknown and I4
			//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b9: Invalid comparison between Unknown and I4
			//IL_011a: Unknown result type (might be due to invalid IL or missing references)
			//IL_011f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0156: Unknown result type (might be due to invalid IL or missing references)
			//IL_0158: Unknown result type (might be due to invalid IL or missing references)
			//IL_013e: Unknown result type (might be due to invalid IL or missing references)
			//IL_014f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0154: Unknown result type (might be due to invalid IL or missing references)
			//IL_01fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0202: Invalid comparison between Unknown and I4
			//IL_0285: Unknown result type (might be due to invalid IL or missing references)
			//IL_028b: Invalid comparison between Unknown and I4
			if ((int)desc.minerType == 0 || desc.minerPeriod <= 0 || (int)desc.minerType == 1 || prebuildId <= 0)
			{
				return;
			}
			ref PrebuildData reference = ref __instance.prebuildPool[prebuildId];
			if (reference.id != prebuildId)
			{
				return;
			}
			int num = __instance.factorySystem.NewMinerComponent(entityId, desc);
			if (num == 0)
			{
				return;
			}
			ref MinerComponent reference2 = ref __instance.factorySystem.minerPool[num];
			ref SignData reference3 = ref __instance.entitySignPool[entityId];
			int num2 = ((desc.isVeinCollector && reference.paramCount >= 2048) ? 2048 : 0);
			bool flag = reference.isDestroyed || Mission.HasShovels || (!Mission.HaulersNotActive && (int)desc.minerType == 2);
			List<int> list = new List<int>(reference.paramCount);
			Pose val = default(Pose);
			((Pose)(ref val))..ctor(reference.pos, reference.rot);
			int paramCount = reference.paramCount;
			while (paramCount-- > num2)
			{
				int num3 = reference.parameters[paramCount];
				if (num3 <= 0)
				{
					continue;
				}
				if (flag)
				{
					list.Add(num3);
					continue;
				}
				Vector3 val2 = __instance.veinPool[num3].pos;
				if (((Vector3)(ref val2)).magnitude < __instance.planet.realRadius - 40f)
				{
					val2 = ((Vector3)(ref val2)).normalized * __instance.planet.realRadius;
				}
				if (MinerComponent.IsTargetVeinInRange(val2, val, desc))
				{
					list.Add(num3);
				}
			}
			reference2.veins = list.ToArray();
			reference2.veinCount = reference2.veins.Length;
			if (reference.filterId <= 0 && reference2.veinCount >= 0)
			{
				reference.filterId = __instance.veinPool[reference2.veins[0]].productId;
			}
			int veinCount = reference2.veinCount;
			while (veinCount-- > 0)
			{
				__instance.RefreshVeinMiningDisplay(reference2.veins[veinCount], entityId, 0);
			}
			((MinerComponent)(ref reference2)).GetMinimumVeinAmount(__instance, __instance.veinPool);
			if ((int)reference2.type == 1)
			{
				reference3.iconId0 = (uint)__instance.planet.waterItemId;
				if (reference3.iconId0 > 12000)
				{
					reference3.iconId0 = 0u;
				}
				reference3.iconType = ((reference3.iconId0 != 0) ? 1u : 0u);
			}
			else
			{
				int num4 = ((reference2.veinCount != 0) ? reference2.veins[0] : 0);
				reference3.iconId0 = (uint)((num4 == 0) ? reference.filterId : __instance.veinPool[num4].productId);
				reference3.iconType = ((reference3.iconId0 != 0) ? 1u : 0u);
			}
			if ((int)reference2.type == 2 && !__instance.gameData.gameDesc.isInfiniteResource)
			{
				((MinerComponent)(ref reference2)).GetTotalVeinAmount(__instance.veinPool);
			}
			desc = GetForgeryNonMiner(desc);
			__state = entityId;
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(PlanetFactory), "CreateEntityLogicComponents")]
		private static void RehookMinerFeatures(int entityId, ref PrefabDesc desc, int prebuildId, in PlanetFactory __instance, ref int __state)
		{
			if (__state > 0)
			{
				ref EntityData reference = ref __instance.entityPool[entityId];
				ref MinerComponent reference2 = ref __instance.factorySystem.minerPool[reference.minerId];
				reference2.pcId = reference.powerConId;
				if (desc.isVeinCollector)
				{
					__instance.transport.GetStationComponent(reference.stationId).minerId = reference2.id;
				}
			}
		}

		[HarmonyTranspiler]
		[HarmonyPatch(typeof(BuildingGizmo), "Update")]
		[HarmonyPatch(typeof(BuildTool_Click), "UpdateGizmos")]
		private static IEnumerable<CodeInstruction> Lazy2048Fix(IEnumerable<CodeInstruction> raw)
		{
			List<CodeInstruction> list = raw.ToList();
			for (int i = 0; i < list.Count; i++)
			{
				CodeInstruction val = list[i];
				if (val.opcode == OpCodes.Ldc_I4 && (int)val.operand == 2048)
				{
					list[i].Reop(OpCodes.Ldc_I4_0);
				}
			}
			return list;
		}

		[HarmonyTranspiler]
		[HarmonyPatch(typeof(PlayerControlGizmo), "OnOutlineDraw")]
		private static IEnumerable<CodeInstruction> PlayerControlGizmo_OOD(IEnumerable<CodeInstruction> raw)
		{
			List<CodeInstruction> list = raw.ToList();
			bool flag = false;
			for (int i = 0; i < list.Count; i++)
			{
				CodeInstruction val = list[i];
				if (!flag && val.opcode == OpCodes.Ldc_I4 && (int)val.operand == 2048)
				{
					CodeInstruction val2 = list[i - 1];
					CodeInstruction val3 = list[i - 2];
					CodeInstruction val4 = list[i - 3];
					CodeInstruction ci = list[i - 4];
					CodeInstruction val5 = list[i - 7];
					LazyOutposting.Logs.LogWarning((object)"... Player Gizmo Outlines, lookaround for 2048 offset...");
					if ((val2.opcode != OpCodes.Brfalse && val2.opcode != OpCodes.Brfalse_S) || val3.opcode != OpCodes.Ldfld || val4.opcode != OpCodes.Ldfld || (val5.opcode != OpCodes.Stloc && val5.opcode != OpCodes.Stloc_S))
					{
						continue;
					}
					ci.Reop(OpCodes.Nop);
					val4.Reop((val5.opcode == OpCodes.Stloc) ? OpCodes.Ldloc : OpCodes.Ldloc_S, val5.operand);
					val3.Reop(OpCodes.Ldc_I4, 2048);
					val2.Reop((val2.opcode == OpCodes.Brfalse) ? OpCodes.Blt : OpCodes.Blt_S, val2.operand);
					LazyOutposting.Logs.LogWarning((object)"... Lookaround Success!");
					flag = true;
				}
				if (val.opcode == OpCodes.Call && val.operand is MethodInfo methodInfo && methodInfo == MinerIsVeinInRange.Value && !(list[i - 1].opcode != OpCodes.Ldfld))
				{
					list[i - 4].Reop(OpCodes.Nop);
					list[i - 3].Reop(OpCodes.Nop);
					list[i - 2].Reop(OpCodes.Nop);
					list[i - 1].Reop(OpCodes.Nop);
					list[i].Reop(OpCodes.Ldc_I4_1);
				}
			}
			if (!flag)
			{
				LazyOutposting.Logs.LogError((object)"... Player Gizmo Outlines could not find 2048 with expected context.");
			}
			return list;
		}
	}
	internal static class VaporCollection
	{
		private static readonly ConcurrentDictionary<int, PrefabDesc> Forgeries = new ConcurrentDictionary<int, PrefabDesc>();

		public static void SetUp()
		{
			LazyOutposting.Harmony.PatchAll(typeof(VaporCollection));
		}

		private static PrefabDesc GetForgery(BuildPreview pv)
		{
			return Forgeries.GetOrAdd(pv.desc.modelIndex, (Func<int, PrefabDesc>)ForgePrefabDesc);
		}

		private static PrefabDesc GetOriginal(BuildPreview pv)
		{
			return ((ProtoSet<ModelProto>)(object)LDB.models).Select(pv.desc.modelIndex).prefabDesc;
		}

		private static PrefabDesc ForgePrefabDesc(int id)
		{
			PrefabDesc obj = LazyOutposting.ClonePrefab(((ProtoSet<ModelProto>)(object)LDB.models).Select(id).prefabDesc);
			obj.waterPoints = Array.Empty<Vector3>();
			return obj;
		}

		[HarmonyPrefix]
		[HarmonyPatch(typeof(BuildTool_Click), "CheckBuildConditions")]
		private static void PresentForgedPapers(BuildTool_Click __instance, ref List<BuildPreview> __state)
		{
			foreach (BuildPreview buildPreview in ((BuildTool)__instance).buildPreviews)
			{
				if (buildPreview != null && buildPreview.desc.waterPoints != null && buildPreview.desc.waterPoints.Length != 0 && !buildPreview.desc.geothermal)
				{
					if (__state == null)
					{
						__state = new List<BuildPreview>(((BuildTool)__instance).buildPreviews.Count);
					}
					buildPreview.desc = GetForgery(buildPreview);
					__state.Add(buildPreview);
				}
			}
		}

		[HarmonyPrefix]
		[HarmonyPatch(typeof(BuildTool_BlueprintPaste), "CheckBuildConditions")]
		private static void PresentForgedPapers(BuildTool_BlueprintPaste __instance, ref List<BuildPreview> __state)
		{
			BuildPreview[] bpPool = __instance.bpPool;
			foreach (BuildPreview val in bpPool)
			{
				if (val != null && val.desc != null && val.desc.waterPoints != null && val.desc.waterPoints.Length != 0 && !val.desc.geothermal)
				{
					if (__state == null)
					{
						__state = new List<BuildPreview>(__instance.bpPool.Length / 2);
					}
					val.desc = GetForgery(val);
					__state.Add(val);
				}
			}
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(BuildTool_Click), "CheckBuildConditions")]
		[HarmonyPatch(typeof(BuildTool_BlueprintPaste), "CheckBuildConditions")]
		private static void SwiatchBackToRealPapers(ref List<BuildPreview> __state)
		{
			if (__state == null)
			{
				return;
			}
			foreach (BuildPreview item in __state)
			{
				item.desc = GetOriginal(item);
			}
		}
	}
}
namespace Eirshy.DSP.LazyOutposting.Bugfix
{
	internal static class Bugfix_v1_3_lt3
	{
		[HarmonyPostfix]
		[HarmonyPatch(typeof(GameSave), "LoadCurrentGame", new Type[] { typeof(string) })]
		private static void FixDisconnectedMinerStations()
		{
			if (DSPGame.IsMenuDemo)
			{
				return;
			}
			LazyOutposting.Logs.LogWarning((object)"Looking for Disconnected Vein Collectors...");
			GameData data = GameMain.data;
			int found = 0;
			List<PlanetFactory> list = data.factories.Where((PlanetFactory pf) => pf != null && pf.transport != null && pf.transport.stationPool != null).ToList();
			list.AsParallel().ForAll(delegate(PlanetFactory pf)
			{
				StationComponent[] stationPool = pf.transport.stationPool;
				foreach (StationComponent val in stationPool)
				{
					if (val != null && val.isVeinCollector && val.entityId != 0 && val.minerId == 0)
					{
						val.minerId = pf.entityPool[val.entityId].minerId;
						Interlocked.Increment(ref found);
					}
				}
			});
			LazyOutposting.Logs.LogWarning((object)$"...Found and re-linked {found} Vein Collectors across {list.Count} factories!");
		}
	}
}