Decompiled source of AutoQueueTech v0.0.6

AutoQueueTech.dll

Decompiled 2 months ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: AssemblyCompany("AutoQueueTech")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+90bf6ca5e304a9a469ae5cfbc24d0c8ab9a64ee1")]
[assembly: AssemblyProduct("AutoQueueTech")]
[assembly: AssemblyTitle("AutoQueueTech")]
[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 DysonSphereProgram.Modding.AutoQueueTech
{
	[BepInPlugin("dev.raptor.dsp.AutoQueueTech", "AutoQueueTech", "0.0.6")]
	public class Plugin : BaseUnityPlugin
	{
		public const string GUID = "dev.raptor.dsp.AutoQueueTech";

		public const string NAME = "AutoQueueTech";

		public const string VERSION = "0.0.6";

		private Harmony _harmony;

		internal static ManualLogSource Log;

		private void Awake()
		{
			//IL_0011: Unknown result type (might be due to invalid IL or missing references)
			//IL_001b: Expected O, but got Unknown
			Log = ((BaseUnityPlugin)this).Logger;
			_harmony = new Harmony("dev.raptor.dsp.AutoQueueTech");
			AutoQueueTech.InitConfig(((BaseUnityPlugin)this).Config);
			_harmony.PatchAll(typeof(AutoQueueTech));
			((BaseUnityPlugin)this).Logger.LogInfo((object)"AutoQueueTech Awake() called");
		}

		private void OnDestroy()
		{
			((BaseUnityPlugin)this).Logger.LogInfo((object)"AutoQueueTech OnDestroy() called");
			Harmony harmony = _harmony;
			if (harmony != null)
			{
				harmony.UnpatchSelf();
			}
			Log = null;
		}
	}
	public enum AutoQueueMode
	{
		LeastHashesRequired,
		LastResearchedTech,
		LeastHashesRequiredTechAware
	}
	internal class AutoQueueTech
	{
		private static ConfigEntry<AutoQueueMode> QueueMode;

		private static int lastResearchedTechId;

		public static void InitConfig(ConfigFile configFile)
		{
			QueueMode = configFile.Bind<AutoQueueMode>("AutoQueueMode", "Auto-Queue Mode", AutoQueueMode.LeastHashesRequiredTechAware, (ConfigDescription)null);
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(GameHistoryData), "NotifyTechUnlock")]
		private static void CaptureLastResearchedTech(ref GameHistoryData __instance, int _techId)
		{
			if (__instance.techQueue != null && __instance.techQueueLength <= 1)
			{
				lastResearchedTechId = _techId;
			}
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(GameMain), "FixedUpdate")]
		public static void AutoQueueNext()
		{
			//IL_005a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0159: Unknown result type (might be due to invalid IL or missing references)
			//IL_0160: Expected O, but got Unknown
			//IL_00b4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ce: 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_0189: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ff: Unknown result type (might be due to invalid IL or missing references)
			if (DSPGame.IsMenuDemo || lastResearchedTechId == 0 || QueueMode == null)
			{
				return;
			}
			GameHistoryData history = GameMain.history;
			if (history.techQueue == null || history.techQueueLength > 0)
			{
				return;
			}
			Dictionary<int, TechState> techStates = history.techStates;
			if (QueueMode.Value == AutoQueueMode.LastResearchedTech)
			{
				if (techStates.ContainsKey(lastResearchedTechId) && !techStates[lastResearchedTechId].unlocked)
				{
					history.EnqueueTech(lastResearchedTechId);
					lastResearchedTechId = 0;
				}
			}
			else if (QueueMode.Value == AutoQueueMode.LeastHashesRequired)
			{
				int num = 0;
				long num2 = long.MaxValue;
				foreach (KeyValuePair<int, TechState> item in techStates)
				{
					if (item.Key == 0)
					{
						continue;
					}
					TechState value = item.Value;
					TechProto val = ((ProtoSet<TechProto>)(object)LDB.techs).Select(item.Key);
					if (!value.unlocked && !val.IsObsolete && !val.IsHiddenTech && history.CanEnqueueTechIgnoreFull(item.Key))
					{
						long num3 = value.hashNeeded - value.hashUploaded;
						if (num3 < num2)
						{
							num2 = num3;
							num = item.Key;
						}
					}
				}
				if (num != 0)
				{
					history.EnqueueTech(num);
				}
				lastResearchedTechId = 0;
			}
			else
			{
				if (QueueMode.Value != AutoQueueMode.LeastHashesRequiredTechAware)
				{
					return;
				}
				int num4 = 0;
				TechProto val2 = new TechProto();
				foreach (KeyValuePair<int, TechState> item2 in techStates)
				{
					if (item2.Key == 0)
					{
						continue;
					}
					TechState value2 = item2.Value;
					TechProto val3 = ((ProtoSet<TechProto>)(object)LDB.techs).Select(item2.Key);
					if (val3 == null || value2.unlocked || val3.IsObsolete || val3.IsHiddenTech || !history.CanEnqueueTechIgnoreFull(item2.Key) || num4 == item2.Key)
					{
						continue;
					}
					if (num4 == 0)
					{
						val2 = ((ProtoSet<TechProto>)(object)LDB.techs).Select(item2.Key);
						if (val2 != null)
						{
							num4 = item2.Key;
						}
						continue;
					}
					int num5 = CompareTechs(val2, val3, techStates);
					if (num5 == 0 || num5 == 1)
					{
						val2 = val3;
						num4 = item2.Key;
					}
				}
				if (num4 != 0)
				{
					history.EnqueueTech(num4);
				}
				lastResearchedTechId = 0;
			}
		}

		public static int GetHighestTechID(TechProto tech)
		{
			for (int num = TechProto.matrixIds.Length - 1; num >= 0; num--)
			{
				int[] items = tech.Items;
				for (int i = 0; i < items.Length; i++)
				{
					if (items[i] == TechProto.matrixIds[num])
					{
						return TechProto.matrixIds[num];
					}
				}
			}
			return 0;
		}

		public static int CompareTechs(TechProto t1, TechProto t2, Dictionary<int, TechState> techStates)
		{
			//IL_001b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0058: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			int highestTechID = GetHighestTechID(t1);
			int highestTechID2 = GetHighestTechID(t2);
			if (highestTechID == 0 && highestTechID2 == 0)
			{
				TechState ts = techStates[((Proto)t1).ID];
				TechState ts2 = techStates[((Proto)t2).ID];
				return CompareHashNeeded(in ts, in ts2);
			}
			if (highestTechID != 0 && highestTechID2 != 0)
			{
				if (highestTechID == highestTechID2)
				{
					TechState ts = techStates[((Proto)t1).ID];
					TechState ts2 = techStates[((Proto)t2).ID];
					return CompareHashNeeded(in ts, in ts2);
				}
				if (highestTechID > highestTechID2)
				{
					return 1;
				}
				return -1;
			}
			if (highestTechID == 0)
			{
				if (t1.HashNeeded <= 18000)
				{
					return -1;
				}
				return 1;
			}
			if (t2.HashNeeded <= 18000)
			{
				return 1;
			}
			return -1;
		}

		public static int CompareHashNeeded(in TechState ts1, in TechState ts2)
		{
			long num = ts1.hashNeeded - ts1.hashUploaded;
			long num2 = ts2.hashNeeded - ts1.hashUploaded;
			return Math.Sign(num - num2);
		}
	}
}