Decompiled source of DSPEasy Buildings v0.2.37

DSPEasy.Buildings.dll

Decompiled 13 hours ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using DSPEasy.Buildings.Blueprint;
using DSPEasy.Buildings.Buildings;
using DSPEasy.Buildings.Config;
using DSPEasy.Buildings.Persistence;
using DSPEasy.Buildings.Protos;
using DSPEasy.Framework.Abnormal;
using DSPEasy.Framework.Blueprint;
using DSPEasy.Framework.Diagnostics;
using DSPEasy.Framework.Items;
using DSPEasy.Framework.Recipes;
using DSPEasy.Framework.Save;
using DSPEasy.Framework.UI;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("DSPEasy.Buildings")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("0.2.37.0")]
[assembly: AssemblyInformationalVersion("0.2.37+8d07755fdac77ea113d82f799a4e08686c89e363")]
[assembly: AssemblyProduct("DSPEasy.Buildings")]
[assembly: AssemblyTitle("DSPEasy.Buildings")]
[assembly: AssemblyVersion("0.2.37.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[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 DSPEasy.Buildings
{
	[BepInPlugin("DSPEasy.Buildings", "DSPEasy.Buildings", "0.2.37")]
	public class Plugin : BaseUnityPlugin
	{
		public const string PluginGuid = "DSPEasy.Buildings";

		internal static ManualLogSource Log;

		private void Awake()
		{
			//IL_00c1: Unknown result type (might be due to invalid IL or missing references)
			Log = ((BaseUnityPlugin)this).Logger;
			BuildingsConfig.Load(((BaseUnityPlugin)this).Logger);
			((BaseUnityPlugin)this).Logger.LogInfo((object)("[EasyBuildings] 框架程序集:" + typeof(ModSave).Assembly.Location));
			ModSave.LogInfo = delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogInfo((object)m);
			};
			ModSave.LogWarn = delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogWarning((object)m);
			};
			BlueprintChannel.LogWarn = delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogWarning((object)m);
			};
			AbnormalityGuard.Bind((Action<string>)delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogInfo((object)m);
			}, (Action<string>)delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogWarning((object)m);
			});
			GameState.Initialize();
			ModBlueprints.Register();
			BuildingStats.Initialize();
			ModProfiler.Install((Action<string>)delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogInfo((object)m);
			}, (Action<string>)delegate(string m)
			{
				((BaseUnityPlugin)this).Logger.LogWarning((object)m);
			});
			new Harmony("DSPEasy.Buildings").PatchAll();
			((BaseUnityPlugin)this).Logger.LogInfo((object)"[EasyBuildings] 插件已加载(等待原型注入)");
		}
	}
}
namespace DSPEasy.Buildings.UI
{
	internal class BlackboxPanel : MonoBehaviour
	{
		private static readonly Color HintColor = new Color(0.65f, 0.72f, 0.78f, 1f);

		private static readonly Color ButtonOnColor = new Color(0.25f, 0.45f, 0.3f, 0.98f);

		private static readonly Color WarnColor = new Color(1f, 0.72f, 0.35f, 1f);

		private static readonly Color BarBackColor = new Color(0.05f, 0.07f, 0.09f, 0.95f);

		private static readonly Color BarFillColor = new Color(0.25f, 0.62f, 0.85f, 1f);

		private const float PanelWidth = 620f;

		private const float PanelHeight = 352f;

		private const float RecipeHeight = 620f;

		private const float RowHeight = 38f;

		private const float ViewTop = 374f;

		private const float ViewHeight = 228f;

		private GameObject root;

		private Text targetText;

		private Text recipeText;

		private Text stateText;

		private Text machineText;

		private Text progressText;

		private Text logiText;

		private Text workText;

		private Text foldText;

		private Image progressFill;

		private RectTransform progressFillRt;

		private GameObject foldBox;

		private RectTransform content;

		private float barWidth;

		private bool built;

		private bool expanded;

		private int lastTarget;

		private readonly List<GameObject> rows = new List<GameObject>();

		private PlanetFactory factory;

		private int entityId;

		public static BlackboxPanel Instance { get; private set; }

		public bool Opened
		{
			get
			{
				if ((Object)(object)root != (Object)null)
				{
					return root.activeSelf;
				}
				return false;
			}
		}

		public static BlackboxPanel Ensure()
		{
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)Instance != (Object)null)
			{
				return Instance;
			}
			if ((Object)(object)UIRoot.instance == (Object)null || (Object)(object)UIRoot.instance.uiGame == (Object)null)
			{
				return null;
			}
			GameObject val = new GameObject("DSPEasyBlackboxPanel");
			val.transform.SetParent(((Component)UIRoot.instance.uiGame).transform, false);
			Instance = val.AddComponent<BlackboxPanel>();
			return Instance;
		}

		public void Open(PlanetFactory f, int id)
		{
			factory = f;
			entityId = id;
			if (!built)
			{
				Build();
			}
			if (!((Object)(object)root == (Object)null))
			{
				if (lastTarget != BuildingLogic.GetBlackboxTarget(f, id))
				{
					expanded = true;
				}
				Refresh();
				ApplyHeight();
				root.SetActive(true);
				UiFocus.BringToFront(root);
			}
		}

		public void Close()
		{
			factory = null;
			entityId = 0;
			if ((Object)(object)root != (Object)null)
			{
				root.SetActive(false);
			}
		}

		private void Update()
		{
			if (Opened)
			{
				Refresh();
				UiFocus.Poll(root);
			}
		}

		private void Build()
		{
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Expected O, but got Unknown
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Expected O, but got Unknown
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a1: 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_00c8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_031f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0375: Unknown result type (might be due to invalid IL or missing references)
			//IL_038f: Unknown result type (might be due to invalid IL or missing references)
			//IL_03a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_03b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_03d3: Unknown result type (might be due to invalid IL or missing references)
			//IL_03f9: Unknown result type (might be due to invalid IL or missing references)
			//IL_0444: Unknown result type (might be due to invalid IL or missing references)
			//IL_044f: Unknown result type (might be due to invalid IL or missing references)
			//IL_045a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0464: Unknown result type (might be due to invalid IL or missing references)
			//IL_04b6: Unknown result type (might be due to invalid IL or missing references)
			//IL_0516: Unknown result type (might be due to invalid IL or missing references)
			//IL_0558: Unknown result type (might be due to invalid IL or missing references)
			//IL_05b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_05db: Unknown result type (might be due to invalid IL or missing references)
			//IL_05e5: Expected O, but got Unknown
			//IL_05f0: Unknown result type (might be due to invalid IL or missing references)
			//IL_05f7: Expected O, but got Unknown
			//IL_064a: Unknown result type (might be due to invalid IL or missing references)
			//IL_06b0: Unknown result type (might be due to invalid IL or missing references)
			//IL_06ff: Unknown result type (might be due to invalid IL or missing references)
			//IL_0704: Unknown result type (might be due to invalid IL or missing references)
			//IL_0705: Unknown result type (might be due to invalid IL or missing references)
			//IL_070c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0723: Unknown result type (might be due to invalid IL or missing references)
			//IL_0733: Unknown result type (might be due to invalid IL or missing references)
			//IL_074d: Unknown result type (might be due to invalid IL or missing references)
			built = true;
			try
			{
				UIGame val = (((Object)(object)UIRoot.instance != (Object)null) ? UIRoot.instance.uiGame : null);
				if ((Object)(object)val == (Object)null)
				{
					Plugin.Log.LogWarning((object)"[EasyBuildings] UIGame 尚未创建,无法构建黑箱超市面板");
					return;
				}
				UiFactory.EnsureFont();
				GameObject val2 = new GameObject("DSPEasyBlackboxPanelBody", new Type[2]
				{
					typeof(RectTransform),
					typeof(Image)
				});
				RectTransform val3 = (RectTransform)val2.transform;
				((Transform)val3).SetParent(((Component)val).transform, false);
				Vector2 anchorMin = (val3.anchorMax = new Vector2(0f, 0.5f));
				val3.anchorMin = anchorMin;
				val3.pivot = new Vector2(0f, 0.5f);
				val3.anchoredPosition = new Vector2(8f, 0f);
				val3.sizeDelta = new Vector2(620f, 352f);
				root = val2;
				Image component = val2.GetComponent<Image>();
				((Graphic)component).raycastTarget = true;
				((Graphic)component).color = UiFactory.PanelColor;
				component.sprite = null;
				Text obj = UiFactory.MakeText("Title", root.transform, 14f, -10f, 240f, 26f, 18, (TextAnchor)3);
				obj.text = "超级黑箱超市";
				((Graphic)obj).raycastTarget = true;
				((Component)obj).gameObject.AddComponent<UiDrag>().target = val3;
				UiFactory.MakeButton("Close", root.transform, 536f, -10f, 70f, 26f, "关闭", (Action)Close);
				UiFactory.MakeButton("Pick", root.transform, 14f, -44f, 110f, 28f, "选择产物", (Action)OnPickClick);
				logiText = UiFactory.MakeButton("Logistics", root.transform, 130f, -44f, 92f, 28f, "物流:开", (Action)OnToggleLogistics);
				workText = UiFactory.MakeButton("Work", root.transform, 228f, -44f, 92f, 28f, "制造:开", (Action)OnToggleWork);
				UiFactory.MakeButton("Reset", root.transform, 326f, -44f, 92f, 28f, "恢复默认", (Action)OnReset);
				targetText = UiFactory.MakeText("Target", root.transform, 426f, -44f, 180f, 28f, 13, (TextAnchor)3);
				targetText.text = "未选择产物";
				barWidth = 592f;
				RectTransform val5 = UiFactory.Place(UiFactory.NewRect("Progress", root.transform, barWidth, 24f), 14f, -80f, barWidth, 24f);
				Image obj2 = ((Component)val5).gameObject.AddComponent<Image>();
				((Graphic)obj2).color = BarBackColor;
				((Graphic)obj2).raycastTarget = false;
				progressFillRt = UiFactory.Place(UiFactory.NewRect("Fill", (Transform)(object)val5, barWidth, 24f), 0f, 0f, barWidth, 24f);
				progressFillRt.anchorMin = new Vector2(0f, 0f);
				progressFillRt.anchorMax = new Vector2(0f, 1f);
				progressFillRt.pivot = new Vector2(0f, 0.5f);
				progressFillRt.anchoredPosition = Vector2.zero;
				progressFillRt.sizeDelta = new Vector2(0f, 0f);
				progressFill = ((Component)progressFillRt).gameObject.AddComponent<Image>();
				((Graphic)progressFill).color = BarFillColor;
				((Graphic)progressFill).raycastTarget = false;
				progressText = UiFactory.MakeText("ProgressText", (Transform)(object)val5, 0f, 0f, barWidth, 24f, 12, (TextAnchor)4);
				RectTransform rectTransform = ((Graphic)progressText).rectTransform;
				rectTransform.anchorMin = Vector2.zero;
				rectTransform.anchorMax = Vector2.one;
				rectTransform.offsetMin = Vector2.zero;
				rectTransform.offsetMax = Vector2.zero;
				progressText.text = "";
				recipeText = UiFactory.MakeText("Recipe", root.transform, 14f, -110f, 592f, 56f, 13, (TextAnchor)0);
				((Graphic)recipeText).color = UiFactory.TextColor;
				recipeText.text = "";
				machineText = UiFactory.MakeButton("MachineSlot", root.transform, 14f, -170f, 592f, 30f, "制造机槽:空", (Action)OnMachineClick);
				((Graphic)machineText).color = UiFactory.TextColor;
				stateText = UiFactory.MakeText("State", root.transform, 14f, -206f, 592f, 56f, 12, (TextAnchor)0);
				((Graphic)stateText).color = HintColor;
				stateText.text = "";
				foldText = UiFactory.MakeButton("Fold", root.transform, 14f, -270f, 592f, 28f, "配方示意 ▼", (Action)ToggleFold);
				((Graphic)foldText).color = UiFactory.TextColor;
				foldBox = new GameObject("FoldBox", new Type[1] { typeof(RectTransform) });
				RectTransform val6 = (RectTransform)foldBox.transform;
				((Transform)val6).SetParent(root.transform, false);
				UiFactory.Place(val6, 0f, 0f, 620f, 620f);
				Text obj3 = UiFactory.MakeText("ListHead", (Transform)(object)val6, 14f, -304f, 592f, 66f, 12, (TextAnchor)0);
				((Graphic)obj3).color = HintColor;
				obj3.text = "「配方」循环切换该中间产物用哪条配方;「原矿」切换是否自己造。所有设置随建筑存档。\n★ 目标产物\u3000◆ 视为原矿的输入\u3000↳ 副产物(无人取走会顶满)。净副产物为 0 的中间产物不占格。";
				RectTransform val7 = UiFactory.Place(UiFactory.NewRect("Viewport", (Transform)(object)val6, 592f, 228f), 14f, -374f, 592f, 228f);
				Image obj4 = ((Component)val7).gameObject.AddComponent<Image>();
				((Graphic)obj4).color = new Color(0f, 0f, 0f, 0.18f);
				((Graphic)obj4).raycastTarget = true;
				((Component)val7).gameObject.AddComponent<RectMask2D>();
				content = UiFactory.NewRect("Content", (Transform)(object)val7, 592f, 1f);
				RectTransform obj5 = content;
				anchorMin = (content.anchorMax = new Vector2(0f, 1f));
				obj5.anchorMin = anchorMin;
				content.pivot = new Vector2(0f, 1f);
				content.anchoredPosition = Vector2.zero;
				content.sizeDelta = new Vector2(592f, 1f);
				ScrollRect obj6 = ((Component)val7).gameObject.AddComponent<ScrollRect>();
				obj6.content = content;
				obj6.viewport = val7;
				obj6.horizontal = false;
				obj6.vertical = true;
				obj6.movementType = (MovementType)2;
				obj6.scrollSensitivity = 30f;
				foldBox.SetActive(false);
				root.SetActive(false);
				Plugin.Log.LogInfo((object)("[EasyBuildings] 黑箱超市面板已创建(font=" + ((Object)(object)UiFactory.DefaultFont != (Object)null) + ")"));
			}
			catch (Exception ex)
			{
				Plugin.Log.LogError((object)("[EasyBuildings] 构建黑箱超市面板失败:" + ex));
				root = null;
			}
		}

		private void RebuildList()
		{
			//IL_0097: Unknown result type (might be due to invalid IL or missing references)
			//IL_009c: Unknown result type (might be due to invalid IL or missing references)
			//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ee: 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_0101: Unknown result type (might be due to invalid IL or missing references)
			//IL_0112: Unknown result type (might be due to invalid IL or missing references)
			//IL_0117: Unknown result type (might be due to invalid IL or missing references)
			//IL_0167: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)content == (Object)null)
			{
				return;
			}
			for (int i = 0; i < rows.Count; i++)
			{
				if ((Object)(object)rows[i] != (Object)null)
				{
					Object.Destroy((Object)(object)rows[i]);
				}
			}
			rows.Clear();
			if (factory == null || entityId <= 0)
			{
				return;
			}
			Rect rect;
			if (BuildingLogic.GetBlackboxTarget(factory, entityId) <= 0)
			{
				AddInfoRow("先选一个目标产物,这里会列出它的整条配方链。", 0f);
				RectTransform obj = content;
				rect = content.rect;
				obj.sizeDelta = new Vector2(((Rect)(ref rect)).width, 40f);
				return;
			}
			List<BuildingLogic.BlackboxLine> list = BuildingLogic.DescribeTree(factory, entityId);
			if (list == null || list.Count == 0)
			{
				AddInfoRow("这条链 12 格装不下(或没有配方)。\n可以往下勾「视为原矿」,或换一条更短/更省的配方。", 0f);
				RectTransform obj2 = content;
				rect = content.rect;
				obj2.sizeDelta = new Vector2(((Rect)(ref rect)).width, 70f);
				return;
			}
			rect = content.rect;
			float width = ((Rect)(ref rect)).width;
			float num = 0f;
			for (int j = 0; j < list.Count; j++)
			{
				MakeRow(list[j], num, width);
				num -= 38f;
			}
			content.sizeDelta = new Vector2(width, Mathf.Max(1f, 0f - num));
		}

		private void AddInfoRow(string text, float y)
		{
			//IL_0011: 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_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			RectTransform obj = content;
			Rect rect = content.rect;
			RectTransform obj2 = UiFactory.NewRect("Info", (Transform)(object)obj, ((Rect)(ref rect)).width, 64f);
			rect = content.rect;
			RectTransform val = UiFactory.Place(obj2, 6f, y, ((Rect)(ref rect)).width - 12f, 64f);
			Text obj3 = ((Component)val).gameObject.AddComponent<Text>();
			obj3.font = UiFactory.DefaultFont;
			obj3.fontSize = 13;
			((Graphic)obj3).color = HintColor;
			obj3.alignment = (TextAnchor)0;
			((Graphic)obj3).raycastTarget = false;
			obj3.horizontalOverflow = (HorizontalWrapMode)0;
			obj3.text = text;
			rows.Add(((Component)val).gameObject);
		}

		private void MakeRow(BuildingLogic.BlackboxLine line, float y, float w)
		{
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ae: 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_019b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cd: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d2: Unknown result type (might be due to invalid IL or missing references)
			//IL_0447: Unknown result type (might be due to invalid IL or missing references)
			//IL_03fe: Unknown result type (might be due to invalid IL or missing references)
			//IL_03e3: Unknown result type (might be due to invalid IL or missing references)
			ItemProto val = ((ProtoSet<ItemProto>)(object)LDB.items).Select(line.ItemId);
			string text = ((val != null) ? ((Proto)val).Name : line.ItemId.ToString());
			string text2 = "";
			Color color = UiFactory.TextColor;
			string text3 = "";
			if (line.Role == 0)
			{
				text2 = "★ ";
				((Color)(ref color))..ctor(1f, 0.85f, 0.45f, 1f);
			}
			else if (line.Role == 3)
			{
				text2 = "↳ ";
				((Color)(ref color))..ctor(0.55f, 0.78f, 1f, 1f);
			}
			else if (line.IsRaw)
			{
				text2 = "◆ ";
				color = HintColor;
				text3 = "(视为原矿)";
			}
			else if (line.Blocked > 0)
			{
				text2 = "⚠ ";
				color = WarnColor;
				text3 = "(12 格放不下)";
			}
			RectTransform val2 = UiFactory.Place(UiFactory.NewRect("Row", (Transform)(object)content, w, 38f), 0f, y, w, 38f);
			rows.Add(((Component)val2).gameObject);
			Image val3 = ((Component)UiFactory.Place(UiFactory.NewRect("Icon", (Transform)(object)val2, 28f, 28f), 6f, -5f, 28f, 28f)).gameObject.AddComponent<Image>();
			if (val != null)
			{
				val3.sprite = val.iconSprite;
			}
			((Graphic)val3).raycastTarget = false;
			Text obj = UiFactory.MakeText("Name", (Transform)(object)val2, 40f, 0f, 140f, 38f, 13, (TextAnchor)3);
			obj.text = text2 + text + text3;
			((Graphic)obj).color = color;
			Text val4 = UiFactory.MakeText("Count", (Transform)(object)val2, 184f, 0f, 88f, 38f, 12, (TextAnchor)5);
			if (line.Role == 0)
			{
				val4.text = "×" + line.Count;
			}
			else if (line.Role == 3)
			{
				val4.text = "副产 ×" + line.Count;
			}
			else if (line.Role == 1)
			{
				val4.text = "需 " + line.Consume + "/产 " + line.Produce;
			}
			else
			{
				val4.text = "需 ×" + line.Count;
			}
			if (line.Producers != null && line.Producers.Count > 0)
			{
				string text4 = ((line.Producers.Count != 1) ? ("配方:" + ((Proto)line.Producers[Mathf.Clamp(line.Chosen, 0, line.Producers.Count - 1)]).Name + " (" + (line.Chosen + 1) + "/" + line.Producers.Count + ")") : ("配方:" + ((Proto)line.Producers[0]).Name));
				int itemId = line.ItemId;
				int count = line.Producers.Count;
				int shown = line.Chosen;
				UiFactory.MakeButton("Recipe", (Transform)(object)val2, 276f, -5f, 216f, 28f, text4, (Action)delegate
				{
					OnCycleRecipe(itemId, count, shown);
				});
				int rawId = line.ItemId;
				((Graphic)UiFactory.MakeButton("Raw", (Transform)(object)val2, 496f, -5f, 90f, 28f, line.IsRaw ? "原矿:是" : "原矿:否", (Action)delegate
				{
					OnToggleRaw(rawId);
				})).color = (Color)(line.IsRaw ? new Color(1f, 0.85f, 0.45f, 1f) : HintColor);
			}
			else
			{
				Text obj2 = UiFactory.MakeText("Fixed", (Transform)(object)val2, 276f, 0f, 310f, 38f, 12, (TextAnchor)3);
				obj2.text = ((line.Role == 3) ? "副产物(等物流机或分拣器拉走)" : "无配方(外部输入)");
				((Graphic)obj2).color = HintColor;
			}
		}

		private void ApplyHeight()
		{
			//IL_001a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			if (!((Object)(object)root == (Object)null))
			{
				((RectTransform)root.transform).sizeDelta = new Vector2(620f, expanded ? 620f : 352f);
				if ((Object)(object)foldBox != (Object)null)
				{
					foldBox.SetActive(expanded);
				}
				if ((Object)(object)foldText != (Object)null)
				{
					foldText.text = (expanded ? "配方示意 ▲(点击折叠)" : "配方示意 ▼(点开可切配方 / 勾原矿)");
				}
			}
		}

		private void Refresh()
		{
			//IL_0161: Unknown result type (might be due to invalid IL or missing references)
			//IL_0279: Unknown result type (might be due to invalid IL or missing references)
			//IL_027e: Unknown result type (might be due to invalid IL or missing references)
			//IL_033f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0344: Unknown result type (might be due to invalid IL or missing references)
			//IL_0312: Unknown result type (might be due to invalid IL or missing references)
			//IL_0317: Unknown result type (might be due to invalid IL or missing references)
			//IL_032f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0334: Unknown result type (might be due to invalid IL or missing references)
			//IL_0355: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)targetText == (Object)null)
			{
				return;
			}
			if (factory == null || entityId <= 0 || factory.entityPool == null || entityId >= factory.entityPool.Length || factory.entityPool[entityId].id != entityId)
			{
				Close();
				return;
			}
			BuildingLogic.BlackboxSettings settings = BuildingLogic.GetSettings(factory, entityId);
			if ((Object)(object)logiText != (Object)null)
			{
				SetToggle(logiText, "物流:" + (settings.LogisticsOn ? "开" : "关"), settings.LogisticsOn);
			}
			if ((Object)(object)workText != (Object)null)
			{
				SetToggle(workText, "制造:" + (settings.WorkOn ? "开" : "关"), settings.WorkOn);
			}
			int blackboxTarget = BuildingLogic.GetBlackboxTarget(factory, entityId);
			if (blackboxTarget != lastTarget)
			{
				lastTarget = blackboxTarget;
				RebuildList();
			}
			if (blackboxTarget <= 0)
			{
				targetText.text = "未选择产物";
				recipeText.text = "点「选择产物」挑一个要生产的东西,本建筑会自动把它的整条配方链拆成原矿或中间产物。";
				stateText.text = "";
				SetProgress(0f, "", HintColor);
				machineText.text = "制造机槽:空";
				return;
			}
			ItemProto val = ((ProtoSet<ItemProto>)(object)LDB.items).Select(blackboxTarget);
			targetText.text = "目标:" + ((val != null) ? ((Proto)val).Name : blackboxTarget.ToString());
			recipeText.text = BuildingLogic.DescribeBlackbox(factory, entityId);
			float ratio;
			int periodTicks;
			int remainTicks;
			string reason;
			int blackboxProgress = BuildingLogic.GetBlackboxProgress(factory, entityId, out ratio, out periodTicks, out remainTicks, out reason);
			string label;
			Color color;
			switch (blackboxProgress)
			{
			case 3:
				label = "生产中 · " + Mathf.RoundToInt(ratio * 100f) + "% · 剩余 " + ((float)remainTicks / 60f).ToString("0.0") + "s(本批 " + ((float)periodTicks / 60f).ToString("0.0") + "s)";
				color = UiFactory.TextColor;
				break;
			case 1:
				label = ((remainTicks > 0 || ratio > 0f) ? ("已暂停 · " + Mathf.RoundToInt(ratio * 100f) + "% · 剩余 " + ((float)remainTicks / 60f).ToString("0.0") + "s(本批 " + ((float)periodTicks / 60f).ToString("0.0") + "s)") : "制造已关闭(产物与原料都不会动)");
				color = HintColor;
				break;
			case 2:
				label = (string.IsNullOrEmpty(reason) ? "等待中" : reason);
				color = WarnColor;
				break;
			default:
				label = "";
				color = HintColor;
				break;
			}
			SetProgress((blackboxProgress == 0) ? 0f : ratio, label, color);
			int machineItem = BuildingLogic.GetMachineItem(factory, entityId);
			int machineCount = BuildingLogic.GetMachineCount(factory, entityId);
			ItemProto val2 = ((machineItem > 0) ? ((ProtoSet<ItemProto>)(object)LDB.items).Select(machineItem) : null);
			machineText.text = ((machineCount > 0 && val2 != null) ? ("制造机槽:" + ((Proto)val2).Name + " × " + machineCount + "(点此全部取出)") : "制造机槽:空(手上拿着制造台,点此放入)");
			stateText.text = BuildingLogic.DescribeBoost(factory, entityId);
		}

		private void SetProgress(float ratio, string label, Color color)
		{
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			if (ratio < 0f)
			{
				ratio = 0f;
			}
			if (ratio > 1f)
			{
				ratio = 1f;
			}
			if ((Object)(object)progressFillRt != (Object)null)
			{
				progressFillRt.sizeDelta = new Vector2(barWidth * ratio, 0f);
			}
			if ((Object)(object)progressText != (Object)null)
			{
				progressText.text = label;
				((Graphic)progressText).color = color;
			}
		}

		private void SetToggle(Text t, string label, bool on)
		{
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			//IL_003b: Unknown result type (might be due to invalid IL or missing references)
			t.text = label;
			Image val = (((Object)(object)((Component)t).transform.parent != (Object)null) ? ((Component)((Component)t).transform.parent).GetComponent<Image>() : null);
			if ((Object)(object)val != (Object)null)
			{
				((Graphic)val).color = (on ? ButtonOnColor : UiFactory.ButtonColor);
			}
		}

		private void ToggleFold()
		{
			expanded = !expanded;
			ApplyHeight();
		}

		private void OnMachineClick()
		{
			if (factory == null || entityId <= 0)
			{
				return;
			}
			try
			{
				Player mainPlayer = GameMain.mainPlayer;
				if (mainPlayer == null)
				{
					return;
				}
				int machineCount = BuildingLogic.GetMachineCount(factory, entityId);
				int machineItem = BuildingLogic.GetMachineItem(factory, entityId);
				if (mainPlayer.inhandItemId > 0 && mainPlayer.inhandItemCount > 0)
				{
					int num = BuildingLogic.AddMachines(factory, entityId, mainPlayer.inhandItemId, mainPlayer.inhandItemCount);
					if (num <= 0)
					{
						UIRealtimeTip.Popup((machineCount > 0) ? "槽里已放满,或只能放同一种制造台" : ("只能放入制造台(最多 " + 100 + " 台)"), true, 0);
						return;
					}
					ItemStack.TakeFromHand(mainPlayer, num);
					Refresh();
				}
				else if (machineCount > 0 && machineItem > 0)
				{
					int num3 = default(int);
					int num2 = mainPlayer.package.AddItemStacked(machineItem, machineCount, 0, ref num3);
					if (num2 > 0)
					{
						mainPlayer.NotifyPackageAddItem(machineItem, num2, 0);
					}
					int num4 = machineCount - num2;
					BuildingLogic.SetMachine(factory, entityId, machineItem, num4);
					Refresh();
					if (num2 > 0)
					{
						UIItemup.Up(machineItem, num2);
					}
					if (num4 > 0)
					{
						UIRealtimeTip.Popup("背包空间不够,剩下 " + num4 + " 台留在槽里", true, 0);
					}
				}
				else
				{
					UIRealtimeTip.Popup("先把制造台拿在手上,再点这里放入", true, 0);
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 制造机槽操作失败:" + ex.Message));
			}
		}

		private void OnPickClick()
		{
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			if (factory == null || entityId <= 0)
			{
				return;
			}
			try
			{
				UIItemPicker val = (((Object)(object)UIRoot.instance != (Object)null && (Object)(object)UIRoot.instance.uiGame != (Object)null) ? UIRoot.instance.uiGame.itemPicker : null);
				if ((Object)(object)val != (Object)null && ((ManualBehaviour)val).active)
				{
					UIItemPicker.Close();
					return;
				}
				Patch_MinerItemFilter.Pending = ProducingItems();
				UIItemPicker.Popup(Vector2.zero, (Action<ItemProto>)OnPicked);
				if ((Object)(object)val != (Object)null && ((ManualBehaviour)val).active)
				{
					((Component)val).transform.SetAsLastSibling();
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 打开产物选择器失败:" + ex.Message));
			}
		}

		private static HashSet<int> ProducingItems()
		{
			HashSet<int> hashSet = new HashSet<int>();
			RecipeProto[] dataArray = ((ProtoSet<RecipeProto>)(object)LDB.recipes).dataArray;
			foreach (RecipeProto val in dataArray)
			{
				if (val == null || val.Results == null || val.Results.Length == 0)
				{
					continue;
				}
				for (int j = 0; j < val.Results.Length; j++)
				{
					int num = val.Results[j];
					if (num > 0 && ((ProtoSet<ItemProto>)(object)LDB.items).Select(num) != null)
					{
						hashSet.Add(num);
					}
				}
			}
			return hashSet;
		}

		private void OnPicked(ItemProto proto)
		{
			if (factory != null && entityId > 0 && proto != null)
			{
				BuildingLogic.SetBlackboxTarget(factory, entityId, ((Proto)proto).ID);
				lastTarget = ((Proto)proto).ID;
				expanded = true;
				Refresh();
				ApplyHeight();
				RebuildList();
			}
		}

		private void OnToggleWork()
		{
			if (factory != null && entityId > 0)
			{
				BuildingLogic.BlackboxSettings settings = BuildingLogic.GetSettings(factory, entityId);
				BuildingLogic.SetWorkOn(factory, entityId, !settings.WorkOn);
				Refresh();
			}
		}

		private void OnToggleLogistics()
		{
			if (factory != null && entityId > 0)
			{
				BuildingLogic.BlackboxSettings settings = BuildingLogic.GetSettings(factory, entityId);
				BuildingLogic.SetLogisticsOn(factory, entityId, !settings.LogisticsOn);
				Refresh();
			}
		}

		private void OnReset()
		{
			if (factory != null && entityId > 0)
			{
				BuildingLogic.ResetSettings(factory, entityId);
				Refresh();
				RebuildList();
			}
		}

		private void OnCycleRecipe(int itemId, int count, int shown)
		{
			if (factory != null && entityId > 0 && count > 0)
			{
				BuildingLogic.SetRecipeChoice(factory, entityId, itemId, (shown + 1) % count);
				RebuildList();
			}
		}

		private void OnToggleRaw(int itemId)
		{
			if (factory != null && entityId > 0)
			{
				BuildingLogic.ToggleRaw(factory, entityId, itemId);
				RebuildList();
			}
		}
	}
	[HarmonyPatch(typeof(UIGame), "OnPlayerInspecteeChange")]
	internal static class Patch_BlackboxInspectWindow
	{
		private static void Postfix(UIGame __instance, EObjectType objType, int objId)
		{
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				BlackboxPanel blackboxPanel = BlackboxPanel.Ensure();
				if (!((Object)(object)blackboxPanel == (Object)null))
				{
					PlanetFactory val = ((GameMain.mainPlayer != null) ? GameMain.mainPlayer.factory : null);
					if ((int)objType == 0 && val != null && BuildingLogic.IsBlackbox(val, objId))
					{
						blackboxPanel.Open(val, objId);
					}
					else if (blackboxPanel.Opened)
					{
						blackboxPanel.Close();
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 黑箱超市面板切换失败:" + ex));
			}
		}
	}
	internal class EjectorPanel : MonoBehaviour
	{
		private static readonly Color HintColor = new Color(0.65f, 0.72f, 0.78f, 1f);

		private static readonly Color OnColor = new Color(0.2f, 0.42f, 0.32f, 0.98f);

		private const float PanelWidth = 360f;

		private const float PanelHeight = 196f;

		private GameObject root;

		private Text sailText;

		private Text rocketText;

		private Text stateText;

		private Image sailImg;

		private Image rocketImg;

		private bool built;

		private PlanetFactory factory;

		private int entityId;

		public static EjectorPanel Instance { get; private set; }

		public bool Opened
		{
			get
			{
				if ((Object)(object)root != (Object)null)
				{
					return root.activeSelf;
				}
				return false;
			}
		}

		public static EjectorPanel Ensure()
		{
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)Instance != (Object)null)
			{
				return Instance;
			}
			if ((Object)(object)UIRoot.instance == (Object)null || (Object)(object)UIRoot.instance.uiGame == (Object)null)
			{
				return null;
			}
			GameObject val = new GameObject("DSPEasyEjectorPanel");
			val.transform.SetParent(((Component)UIRoot.instance.uiGame).transform, false);
			Instance = val.AddComponent<EjectorPanel>();
			return Instance;
		}

		public void Open(PlanetFactory f, int id)
		{
			factory = f;
			entityId = id;
			if (!built)
			{
				Build();
			}
			if (!((Object)(object)root == (Object)null))
			{
				Refresh();
				root.SetActive(true);
				UiFocus.BringToFront(root);
			}
		}

		public void Close()
		{
			factory = null;
			entityId = 0;
			if ((Object)(object)root != (Object)null)
			{
				root.SetActive(false);
			}
		}

		private void Update()
		{
			if (Opened)
			{
				Refresh();
				UiFocus.Poll(root);
			}
		}

		private void Refresh()
		{
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
			//IL_0104: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fd: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)sailText == (Object)null)
			{
				return;
			}
			if (factory == null || entityId <= 0 || factory.entityPool == null || entityId >= factory.entityPool.Length || factory.entityPool[entityId].id != entityId)
			{
				Close();
				return;
			}
			int ejectorSwitches = BuildingLogic.GetEjectorSwitches(factory, entityId);
			bool flag = (ejectorSwitches & 1) != 0;
			bool flag2 = (ejectorSwitches & 2) != 0;
			sailText.text = (flag ? "发射太阳帆:开" : "发射太阳帆:关");
			rocketText.text = (flag2 ? "发射运载火箭:开" : "发射运载火箭:关");
			if ((Object)(object)sailImg != (Object)null)
			{
				((Graphic)sailImg).color = (flag ? OnColor : UiFactory.ButtonColor);
			}
			if ((Object)(object)rocketImg != (Object)null)
			{
				((Graphic)rocketImg).color = (flag2 ? OnColor : UiFactory.ButtonColor);
			}
			if (!flag && !flag2)
			{
				stateText.text = "两项都关:发射器不消耗任何物品,仓储格照常接收送货。";
			}
			else if (!flag)
			{
				stateText.text = "只发射运载火箭;太阳帆留在仓储里(分拣器/物流机仍可拉走)。";
			}
			else if (!flag2)
			{
				stateText.text = "只发射太阳帆;小型运载火箭留在仓储里(分拣器/物流机仍可拉走)。";
			}
			else
			{
				stateText.text = "两项都开:按 120 帆/分、60 火箭/分的节奏消耗仓储里的太阳帆与火箭。";
			}
		}

		private void ToggleSail()
		{
			if (factory != null && entityId > 0)
			{
				int ejectorSwitches = BuildingLogic.GetEjectorSwitches(factory, entityId);
				ejectorSwitches ^= 1;
				BuildingLogic.SetEjectorSwitches(factory, entityId, ejectorSwitches);
				Refresh();
			}
		}

		private void ToggleRocket()
		{
			if (factory != null && entityId > 0)
			{
				int ejectorSwitches = BuildingLogic.GetEjectorSwitches(factory, entityId);
				ejectorSwitches ^= 2;
				BuildingLogic.SetEjectorSwitches(factory, entityId, ejectorSwitches);
				Refresh();
			}
		}

		private void Build()
		{
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Expected O, but got Unknown
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Expected O, but got Unknown
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00db: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
			//IL_0281: Unknown result type (might be due to invalid IL or missing references)
			built = true;
			try
			{
				UIGame val = (((Object)(object)UIRoot.instance != (Object)null) ? UIRoot.instance.uiGame : null);
				if ((Object)(object)val == (Object)null)
				{
					Plugin.Log.LogWarning((object)"[EasyBuildings] UIGame 尚未创建,无法构建发射器面板");
					return;
				}
				UiFactory.EnsureFont();
				GameObject val2 = new GameObject("DSPEasyEjectorPanelBody", new Type[2]
				{
					typeof(RectTransform),
					typeof(Image)
				});
				RectTransform val3 = (RectTransform)val2.transform;
				((Transform)val3).SetParent(((Component)val).transform, false);
				Vector2 anchorMin = (val3.anchorMax = new Vector2(0f, 0.5f));
				val3.anchorMin = anchorMin;
				val3.pivot = new Vector2(0f, 0.5f);
				val3.anchoredPosition = new Vector2(8f, 0f);
				val3.sizeDelta = new Vector2(360f, 196f);
				root = val2;
				Image component = val2.GetComponent<Image>();
				((Graphic)component).raycastTarget = true;
				((Graphic)component).color = UiFactory.PanelColor;
				component.sprite = null;
				Text obj = UiFactory.MakeText("Title", root.transform, 14f, -10f, 240f, 26f, 18, (TextAnchor)3);
				obj.text = "超级电磁-火箭发射器";
				((Graphic)obj).raycastTarget = true;
				((Component)obj).gameObject.AddComponent<UiDrag>().target = val3;
				UiFactory.MakeButton("Close", root.transform, 276f, -10f, 70f, 26f, "关闭", (Action)Close);
				sailText = UiFactory.MakeButton("SailToggle", root.transform, 14f, -48f, 332f, 32f, "发射太阳帆:开", (Action)ToggleSail);
				sailImg = ((Component)((Component)sailText).transform.parent).GetComponent<Image>();
				rocketText = UiFactory.MakeButton("RocketToggle", root.transform, 14f, -90f, 332f, 32f, "发射运载火箭:开", (Action)ToggleRocket);
				rocketImg = ((Component)((Component)rocketText).transform.parent).GetComponent<Image>();
				stateText = UiFactory.MakeText("State", root.transform, 14f, -132f, 332f, 54f, 12, (TextAnchor)0);
				((Graphic)stateText).color = HintColor;
				stateText.text = "";
				root.SetActive(false);
				Plugin.Log.LogInfo((object)("[EasyBuildings] 发射器面板已创建(font=" + ((Object)(object)UiFactory.DefaultFont != (Object)null) + ")"));
			}
			catch (Exception ex)
			{
				Plugin.Log.LogError((object)("[EasyBuildings] 构建发射器面板失败:" + ex));
				root = null;
			}
		}
	}
	[HarmonyPatch(typeof(UIGame), "OnPlayerInspecteeChange")]
	internal static class Patch_EjectorInspectWindow
	{
		private static void Postfix(UIGame __instance, EObjectType objType, int objId)
		{
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				EjectorPanel ejectorPanel = EjectorPanel.Ensure();
				if (!((Object)(object)ejectorPanel == (Object)null))
				{
					PlanetFactory val = ((GameMain.mainPlayer != null) ? GameMain.mainPlayer.factory : null);
					if ((int)objType == 0 && val != null && BuildingLogic.IsEjector(val, objId))
					{
						ejectorPanel.Open(val, objId);
					}
					else if (ejectorPanel.Opened)
					{
						ejectorPanel.Close();
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 发射器面板切换失败:" + ex));
			}
		}
	}
	internal class MinerPanel : MonoBehaviour
	{
		private static readonly Color HintColor = new Color(0.65f, 0.72f, 0.78f, 1f);

		private const float PanelWidth = 320f;

		private const float PanelHeight = 158f;

		private GameObject root;

		private Slider rateSlider;

		private Text rateValue;

		private Text stateText;

		private bool built;

		private PlanetFactory factory;

		private int entityId;

		public static MinerPanel Instance { get; private set; }

		public bool Opened
		{
			get
			{
				if ((Object)(object)root != (Object)null)
				{
					return root.activeSelf;
				}
				return false;
			}
		}

		public static MinerPanel Ensure()
		{
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)Instance != (Object)null)
			{
				return Instance;
			}
			if ((Object)(object)UIRoot.instance == (Object)null || (Object)(object)UIRoot.instance.uiGame == (Object)null)
			{
				return null;
			}
			GameObject val = new GameObject("DSPEasyMinerPanel");
			val.transform.SetParent(((Component)UIRoot.instance.uiGame).transform, false);
			Instance = val.AddComponent<MinerPanel>();
			return Instance;
		}

		public void Open(PlanetFactory f, int id)
		{
			factory = f;
			entityId = id;
			if (!built)
			{
				Build();
			}
			if (!((Object)(object)root == (Object)null))
			{
				int minerRate = BuildingLogic.GetMinerRate(f, id);
				if ((Object)(object)rateSlider != (Object)null)
				{
					rateSlider.SetValueWithoutNotify((float)minerRate);
				}
				if ((Object)(object)rateValue != (Object)null)
				{
					rateValue.text = minerRate + "%";
				}
				RefreshState();
				root.SetActive(true);
				UiFocus.BringToFront(root);
			}
		}

		public void Close()
		{
			factory = null;
			entityId = 0;
			if ((Object)(object)root != (Object)null)
			{
				root.SetActive(false);
			}
		}

		private void Update()
		{
			if (Opened)
			{
				RefreshState();
				UiFocus.Poll(root);
			}
		}

		private void Build()
		{
			//IL_0069: Unknown result type (might be due to invalid IL or missing references)
			//IL_006f: Expected O, but got Unknown
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Expected O, but got Unknown
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
			//IL_00db: Unknown result type (might be due to invalid IL or missing references)
			//IL_0100: Unknown result type (might be due to invalid IL or missing references)
			//IL_0293: Unknown result type (might be due to invalid IL or missing references)
			built = true;
			try
			{
				UIGame val = (((Object)(object)UIRoot.instance != (Object)null) ? UIRoot.instance.uiGame : null);
				if ((Object)(object)val == (Object)null)
				{
					Plugin.Log.LogWarning((object)"[EasyBuildings] UIGame 尚未创建,无法构建采矿机面板");
					return;
				}
				UiFactory.EnsureFont();
				GameObject val2 = new GameObject("DSPEasyMinerPanelBody", new Type[2]
				{
					typeof(RectTransform),
					typeof(Image)
				});
				RectTransform val3 = (RectTransform)val2.transform;
				((Transform)val3).SetParent(((Component)val).transform, false);
				Vector2 anchorMin = (val3.anchorMax = new Vector2(0f, 0.5f));
				val3.anchorMin = anchorMin;
				val3.pivot = new Vector2(0f, 0.5f);
				val3.anchoredPosition = new Vector2(8f, 0f);
				val3.sizeDelta = new Vector2(320f, 158f);
				root = val2;
				Image component = val2.GetComponent<Image>();
				((Graphic)component).raycastTarget = true;
				component.sprite = null;
				((Graphic)component).color = UiFactory.PanelColor;
				Text obj = UiFactory.MakeText("Title", root.transform, 14f, -10f, 180f, 26f, 18, (TextAnchor)3);
				obj.text = "超级采矿机";
				((Graphic)obj).raycastTarget = true;
				((Component)obj).gameObject.AddComponent<UiDrag>().target = val3;
				UiFactory.MakeButton("Close", root.transform, 236f, -10f, 70f, 26f, "关闭", (Action)Close);
				UiFactory.MakeText("RateLabel", root.transform, 14f, -48f, 120f, 20f, 14, (TextAnchor)3).text = "采集功率";
				rateValue = UiFactory.MakeText("RateValue", root.transform, 160f, -48f, 146f, 20f, 14, (TextAnchor)5);
				rateValue.text = 100 + "%";
				rateSlider = UiFactory.MakeSlider(root.transform, "RateSlider", 14f, -74f, 292f, 20f, 50f, 300f, true, 100f, (Action<float>)OnRateChanged);
				Text obj2 = UiFactory.MakeText("Hint", root.transform, 14f, -100f, 292f, 18f, 12, (TextAnchor)3);
				((Graphic)obj2).color = HintColor;
				obj2.text = "50% ~ 300%,线性影响采集速度与运行功耗。";
				stateText = UiFactory.MakeText("State", root.transform, 14f, -122f, 292f, 30f, 12, (TextAnchor)0);
				stateText.horizontalOverflow = (HorizontalWrapMode)0;
				stateText.verticalOverflow = (VerticalWrapMode)1;
				stateText.text = "";
				root.SetActive(false);
				Plugin.Log.LogInfo((object)("[EasyBuildings] 采矿机面板已创建(font=" + ((Object)(object)UiFactory.DefaultFont != (Object)null) + ")"));
			}
			catch (Exception ex)
			{
				Plugin.Log.LogError((object)("[EasyBuildings] 构建采矿机面板失败:" + ex));
				root = null;
			}
		}

		private void OnRateChanged(float v)
		{
			if (factory != null && entityId > 0)
			{
				int rate = Mathf.RoundToInt(v);
				BuildingLogic.SetMinerRate(factory, entityId, rate);
				if ((Object)(object)rateValue != (Object)null)
				{
					rateValue.text = rate + "%";
				}
			}
		}

		private void RefreshState()
		{
			if (!((Object)(object)stateText == (Object)null))
			{
				if (factory == null || entityId <= 0 || factory.entityPool == null || entityId >= factory.entityPool.Length || factory.entityPool[entityId].id != entityId)
				{
					Close();
					return;
				}
				int minerRate = BuildingLogic.GetMinerRate(factory, entityId);
				double num = (float)(12000000L * (long)minerRate) / 100f / 1000000f;
				stateText.text = $"运行功耗 {num:0.#} MW,待机 {120f:0.#} kW;采集速度 {minerRate}%。";
			}
		}
	}
	[HarmonyPatch(typeof(UIGame), "OnPlayerInspecteeChange")]
	internal static class Patch_MinerInspectWindow
	{
		private static void Postfix(UIGame __instance, EObjectType objType, int objId)
		{
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				MinerPanel minerPanel = MinerPanel.Ensure();
				if (!((Object)(object)minerPanel == (Object)null))
				{
					PlanetFactory val = ((GameMain.mainPlayer != null) ? GameMain.mainPlayer.factory : null);
					if ((int)objType == 0 && val != null && BuildingLogic.IsMiner(val, objId))
					{
						minerPanel.Open(val, objId);
					}
					else if (minerPanel.Opened)
					{
						minerPanel.Close();
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 采矿机面板切换失败:" + ex));
			}
		}
	}
	internal class TurretWindow : MonoBehaviour
	{
		private static readonly Color HintColor = new Color(0.65f, 0.72f, 0.78f, 1f);

		private const float PanelWidth = 430f;

		private const float TurretPanelHeight = 292f;

		private const float DefensePanelHeight = 322f;

		private GameObject root;

		private RectTransform rootRt;

		private Text titleText;

		private Text rangeLabel;

		private Text rangeValue;

		private RectTransform sliderRt;

		private Slider rangeSlider;

		private RectTransform relayRt;

		private Text relayText;

		private RectTransform spaceRt;

		private Text spaceText;

		private Text hintText;

		private Text stateText;

		private bool built;

		private PlanetFactory factory;

		private int entityId;

		private bool defense;

		public static TurretWindow Instance { get; private set; }

		public bool Opened
		{
			get
			{
				if ((Object)(object)root != (Object)null)
				{
					return root.activeSelf;
				}
				return false;
			}
		}

		public static TurretWindow Ensure()
		{
			//IL_0039: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)Instance != (Object)null)
			{
				return Instance;
			}
			if ((Object)(object)UIRoot.instance == (Object)null || (Object)(object)UIRoot.instance.uiGame == (Object)null)
			{
				return null;
			}
			GameObject val = new GameObject("DSPEasyTurretWindow");
			val.transform.SetParent(((Component)UIRoot.instance.uiGame).transform, false);
			Instance = val.AddComponent<TurretWindow>();
			return Instance;
		}

		public void Open(PlanetFactory f, int id)
		{
			factory = f;
			entityId = id;
			if (!built)
			{
				Build();
			}
			if ((Object)(object)root == (Object)null)
			{
				return;
			}
			ApplyMode(BuildingLogic.IsDefenseStation(f, id));
			if (defense)
			{
				BuildingLogic.DefenseConfig defenseConfig = BuildingLogic.GetDefenseConfig(f, id);
				if ((Object)(object)rangeValue != (Object)null)
				{
					rangeValue.text = 15f.ToString("0.0") + " AU / 溅射 " + 1f.ToString("0.0") + " AU";
				}
				RefreshToggles(defenseConfig.AttackRelay, defenseConfig.AttackSpace);
			}
			else
			{
				BuildingLogic.TurretConfig turretConfig = BuildingLogic.GetTurretConfig(f, id);
				if ((Object)(object)rangeSlider != (Object)null)
				{
					rangeSlider.SetValueWithoutNotify(turretConfig.RangeAU);
				}
				if ((Object)(object)rangeValue != (Object)null)
				{
					rangeValue.text = turretConfig.RangeAU.ToString("0.0") + " AU";
				}
				RefreshToggles(turretConfig.AttackRelay, space: false);
			}
			RefreshState();
			root.SetActive(true);
			UiFocus.BringToFront(root);
		}

		public void Close()
		{
			factory = null;
			entityId = 0;
			if ((Object)(object)root != (Object)null)
			{
				root.SetActive(false);
			}
		}

		private void Update()
		{
			if (Opened)
			{
				RefreshState();
				UiFocus.Poll(root);
			}
		}

		private void Build()
		{
			//IL_0093: Unknown result type (might be due to invalid IL or missing references)
			//IL_0098: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cf: Unknown result type (might be due to invalid IL or missing references)
			//IL_0103: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ad: Expected O, but got Unknown
			//IL_02fe: Unknown result type (might be due to invalid IL or missing references)
			//IL_0308: Expected O, but got Unknown
			//IL_0359: Unknown result type (might be due to invalid IL or missing references)
			//IL_0363: Expected O, but got Unknown
			//IL_039b: Unknown result type (might be due to invalid IL or missing references)
			built = true;
			try
			{
				UIGame val = (((Object)(object)UIRoot.instance != (Object)null) ? UIRoot.instance.uiGame : null);
				if ((Object)(object)val == (Object)null)
				{
					Plugin.Log.LogWarning((object)"[EasyBuildings] UIGame 尚未创建,无法构建炮台面板");
					return;
				}
				UiFactory.EnsureFont();
				rootRt = UiFactory.Place(UiFactory.NewRect("DSPEasyTurretWindowBody", ((Component)val).transform, 430f, 292f), 365f, 146f, 430f, 292f);
				RectTransform obj = rootRt;
				Vector2 anchorMin = (rootRt.anchorMax = new Vector2(0f, 0.5f));
				obj.anchorMin = anchorMin;
				rootRt.pivot = new Vector2(0f, 0.5f);
				rootRt.anchoredPosition = new Vector2(8f, 0f);
				root = ((Component)rootRt).gameObject;
				Image obj2 = root.AddComponent<Image>();
				((Graphic)obj2).raycastTarget = true;
				obj2.sprite = null;
				((Graphic)obj2).color = UiFactory.PanelColor;
				titleText = UiFactory.MakeText("Title", root.transform, 14f, -10f, 300f, 26f, 18, (TextAnchor)3);
				titleText.text = "超级炮台";
				((Graphic)titleText).raycastTarget = true;
				((Component)titleText).gameObject.AddComponent<UiDrag>().target = rootRt;
				UiFactory.MakeButton("Close", root.transform, 346f, -10f, 70f, 26f, "关闭", (Action)Close);
				rangeLabel = UiFactory.MakeText("RangeLabel", root.transform, 14f, -48f, 140f, 20f, 14, (TextAnchor)3);
				rangeLabel.text = "攻击范围";
				rangeValue = UiFactory.MakeText("RangeValue", root.transform, 220f, -48f, 196f, 20f, 14, (TextAnchor)5);
				rangeValue.text = 3f.ToString("0.0") + " AU";
				rangeSlider = UiFactory.MakeSlider(root.transform, "RangeSlider", 14f, -74f, 402f, 20f, 0f, 15f, false, 3f, (Action<float>)OnRangeChanged);
				sliderRt = (RectTransform)((Component)rangeSlider).transform;
				relayText = UiFactory.MakeButton("RelayToggle", root.transform, 14f, -108f, 190f, 28f, "中继器:关", (Action)ToggleRelay);
				relayRt = (RectTransform)((Component)relayText).transform.parent;
				spaceText = UiFactory.MakeButton("SpaceToggle", root.transform, 226f, -108f, 190f, 28f, "太空目标:关", (Action)ToggleSpace);
				spaceRt = (RectTransform)((Component)spaceText).transform.parent;
				hintText = UiFactory.MakeText("Hint", root.transform, 14f, -144f, 402f, 18f, 12, (TextAnchor)3);
				((Graphic)hintText).color = HintColor;
				hintText.text = "默认只打地面敌人;打开开关才会攻击黑雾中继器。";
				stateText = UiFactory.MakeText("State", root.transform, 14f, -168f, 402f, 110f, 12, (TextAnchor)0);
				stateText.horizontalOverflow = (HorizontalWrapMode)0;
				stateText.verticalOverflow = (VerticalWrapMode)1;
				stateText.text = "";
				root.SetActive(false);
				Plugin.Log.LogInfo((object)("[EasyBuildings] 炮台面板已创建(font=" + ((Object)(object)UiFactory.DefaultFont != (Object)null) + ")"));
			}
			catch (Exception ex)
			{
				Plugin.Log.LogError((object)("[EasyBuildings] 构建炮台面板失败:" + ex));
				root = null;
			}
		}

		private void ApplyMode(bool isDefense)
		{
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			defense = isDefense;
			if ((Object)(object)rootRt != (Object)null)
			{
				rootRt.sizeDelta = new Vector2(430f, isDefense ? 322f : 292f);
			}
			if ((Object)(object)titleText != (Object)null)
			{
				titleText.text = (isDefense ? "太空超级防卫站" : "超级炮台");
			}
			if ((Object)(object)sliderRt != (Object)null)
			{
				((Component)sliderRt).gameObject.SetActive(!isDefense);
			}
			if ((Object)(object)rangeLabel != (Object)null)
			{
				rangeLabel.text = "攻击范围";
			}
			if ((Object)(object)rangeValue != (Object)null)
			{
				UiFactory.Pos(((Graphic)rangeValue).rectTransform, isDefense ? 110f : 220f, -48f, isDefense ? 306f : 196f, 20f);
			}
			if ((Object)(object)relayRt != (Object)null)
			{
				UiFactory.Pos(relayRt, 14f, isDefense ? (-84f) : (-108f), isDefense ? 190f : 402f, 28f);
			}
			if ((Object)(object)spaceRt != (Object)null)
			{
				((Component)spaceRt).gameObject.SetActive(isDefense);
				UiFactory.Pos(spaceRt, 226f, -84f, 190f, 28f);
			}
			if ((Object)(object)hintText != (Object)null)
			{
				UiFactory.Pos(((Graphic)hintText).rectTransform, 14f, isDefense ? (-120f) : (-144f), 402f, 18f);
				hintText.text = (isDefense ? "关闭「太空目标」后不再轮询本星系黑雾;两项都关时停止工作。" : "默认只打地面敌人;打开开关才会攻击黑雾中继器。");
			}
			if ((Object)(object)stateText != (Object)null)
			{
				UiFactory.Pos(((Graphic)stateText).rectTransform, 14f, isDefense ? (-144f) : (-168f), 402f, isDefense ? 168f : 110f);
			}
		}

		private void OnRangeChanged(float v)
		{
			if (factory != null && entityId > 0 && !defense)
			{
				BuildingLogic.TurretConfig turretConfig = BuildingLogic.GetTurretConfig(factory, entityId);
				turretConfig.RangeAU = v;
				BuildingLogic.SetTurretConfig(factory, entityId, turretConfig);
				if ((Object)(object)rangeValue != (Object)null)
				{
					rangeValue.text = v.ToString("0.0") + " AU";
				}
			}
		}

		private void ToggleRelay()
		{
			if (factory != null && entityId > 0)
			{
				if (defense)
				{
					BuildingLogic.DefenseConfig defenseConfig = BuildingLogic.GetDefenseConfig(factory, entityId);
					defenseConfig.AttackRelay = !defenseConfig.AttackRelay;
					BuildingLogic.SetDefenseConfig(factory, entityId, defenseConfig);
					RefreshToggles(defenseConfig.AttackRelay, defenseConfig.AttackSpace);
				}
				else
				{
					BuildingLogic.TurretConfig turretConfig = BuildingLogic.GetTurretConfig(factory, entityId);
					turretConfig.AttackRelay = !turretConfig.AttackRelay;
					BuildingLogic.SetTurretConfig(factory, entityId, turretConfig);
					RefreshToggles(turretConfig.AttackRelay, space: false);
				}
				RefreshState();
			}
		}

		private void ToggleSpace()
		{
			if (factory != null && entityId > 0 && defense)
			{
				BuildingLogic.DefenseConfig defenseConfig = BuildingLogic.GetDefenseConfig(factory, entityId);
				defenseConfig.AttackSpace = !defenseConfig.AttackSpace;
				BuildingLogic.SetDefenseConfig(factory, entityId, defenseConfig);
				RefreshToggles(defenseConfig.AttackRelay, defenseConfig.AttackSpace);
				RefreshState();
			}
		}

		private void RefreshToggles(bool relay, bool space)
		{
			if ((Object)(object)relayText != (Object)null)
			{
				relayText.text = (relay ? "中继器:开" : "中继器:关");
			}
			if ((Object)(object)spaceText != (Object)null)
			{
				spaceText.text = (space ? "太空目标:开" : "太空目标:关");
			}
		}

		private void RefreshState()
		{
			if ((Object)(object)stateText == (Object)null)
			{
				return;
			}
			if (factory == null || entityId <= 0 || factory.planet == null || factory.entityPool == null || entityId >= factory.entityPool.Length || factory.entityPool[entityId].id != entityId)
			{
				Close();
				return;
			}
			ref EntityData reference = ref factory.entityPool[entityId];
			string text = "电网:未连接";
			PowerSystem powerSystem = factory.powerSystem;
			if (powerSystem != null && reference.powerConId > 0 && reference.powerConId < powerSystem.consumerPool.Length)
			{
				ref PowerConsumerComponent reference2 = ref powerSystem.consumerPool[reference.powerConId];
				if (reference2.id == reference.powerConId && reference2.networkId > 0 && reference2.networkId < powerSystem.networkServes.Length)
				{
					float num = powerSystem.networkServes[reference2.networkId];
					float num2 = (float)reference2.requiredEnergy * 60f / 1000f;
					text = $"电网:{num * 100f:0}% 供电,当前需求 {num2:0} kW";
				}
			}
			GameHistoryData history = GameMain.history;
			if (defense)
			{
				BuildingLogic.DefenseConfig defenseConfig = BuildingLogic.GetDefenseConfig(factory, entityId);
				float num3 = ((history != null) ? Math.Max(1f, history.energyDamageScale) : 1f);
				float num4 = ((history != null) ? Math.Max(1f, history.combatShipDamageRatio) : 1f);
				int num5 = (int)(25000.0 * (double)num3 * (double)num4 + 0.5);
				string text2 = ((!defenseConfig.AttackRelay && !defenseConfig.AttackSpace) ? "已停用(两项开关都关)" : (defenseConfig.AttackSpace ? "轮询本星系黑雾;空闲超过 3 秒后每 5 分钟检查一次" : "只打中继器(不轮询星系黑雾)"));
				stateText.text = string.Format("{0}\n{1}\n每 {2:0.##} 秒锁定 {3:0} AU 内最近的太空目标,对它和 {4:0.##} AU 内的所有太空敌人/敌方建筑\n造成 {5} 点能量伤害({10} × 能量 {6:0.##} × 战舰 {7:0.##})。\n运行 {8:0} MW,待机 {9:0} MW。", text, text2, 5f, 15f, 1f, num5, num3, num4, 30f, 2f, 25000);
			}
			else
			{
				float num6 = BuildingLogic.GetTurretConfig(factory, entityId).RangeAU - 1f;
				long num7 = ((num6 > 0f) ? ((long)Math.Ceiling(num6) * 1000000) : 0);
				stateText.text = string.Format("{0}\n运行 {1:0} MW(含超距附加 {2:0} MW),待机 {3:0} kW;超过 1 AU 后每 AU 额外 1 MW。\n每 {4:0.##} 秒造成 {5} 点爆炸伤害(享受爆炸 + 能量科技加成),落点 {6:0} m 内全额伤害。\n只攻击地面敌人与黑雾中继器;太空单位请用「{7}」。\n连续 3 秒检测不到目标后,检测间隔降到 1 分钟一次。", text, 3f, (float)num7 / 1000000f, 100f, 0.25f, 500, 75f, "太空超级防卫站");
			}
		}
	}
	[HarmonyPatch(typeof(UIGame), "OnPlayerInspecteeChange")]
	internal static class Patch_TurretInspectWindow
	{
		private static void Postfix(UIGame __instance, EObjectType objType, int objId)
		{
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			try
			{
				TurretWindow turretWindow = TurretWindow.Ensure();
				if (!((Object)(object)turretWindow == (Object)null))
				{
					PlanetFactory val = ((GameMain.mainPlayer != null) ? GameMain.mainPlayer.factory : null);
					if ((int)objType == 0 && val != null && (BuildingLogic.IsTurret(val, objId) || BuildingLogic.IsDefenseStation(val, objId)))
					{
						turretWindow.Open(val, objId);
					}
					else if (turretWindow.Opened)
					{
						turretWindow.Close();
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 炮台面板切换失败:" + ex));
			}
		}
	}
	internal static class UIPatchesNote
	{
	}
	[HarmonyPatch(typeof(UIStationWindow), "OnDroneIconClick")]
	internal static class Patch_StationWindowLockedDrones
	{
		private const int DroneItemId = 5001;

		private static readonly FieldRef<UIStationWindow, int> StationIdRef = AccessTools.FieldRefAccess<UIStationWindow, int>("_stationId");

		private static bool Prefix(UIStationWindow __instance)
		{
			try
			{
				int num = StationIdRef.Invoke(__instance);
				PlanetFactory factory = __instance.factory;
				PlanetTransport transport = __instance.transport;
				if (num <= 0 || factory == null || transport == null || transport.stationPool == null || num >= transport.stationPool.Length)
				{
					return true;
				}
				StationComponent val = transport.stationPool[num];
				if (val == null || val.id != num || val.isCollector || val.isVeinCollector)
				{
					return true;
				}
				if (!Patch_StationWindowColumns.IsOurStation(__instance, val, ProtoInjector.SuperMiner) && !Patch_StationWindowColumns.IsOurStation(__instance, val, ProtoInjector.SuperBlackbox))
				{
					return true;
				}
				Player mainPlayer = GameMain.mainPlayer;
				if (mainPlayer == null)
				{
					return true;
				}
				int num2 = ((ProtoSet<ItemProto>)(object)LDB.items).Select((int)factory.entityPool[val.entityId].protoId)?.prefabDesc.stationMaxDroneCount ?? 10;
				if (mainPlayer.inhandItemId > 0 && mainPlayer.inhandItemCount == 0)
				{
					mainPlayer.SetHandItems(0, 0, 0);
					return false;
				}
				if (mainPlayer.inhandItemId > 0 && mainPlayer.inhandItemCount > 0)
				{
					if (mainPlayer.inhandItemId != 5001)
					{
						UIRealtimeTip.Popup(Localization.Translate("只能放入") + ((Proto)((ProtoSet<ItemProto>)(object)LDB.items).Select(5001)).name, true, 0);
						return false;
					}
					int num3 = num2 - (val.idleDroneCount + val.workDroneCount);
					if (num3 < 0)
					{
						num3 = 0;
					}
					int num4 = Math.Min(mainPlayer.inhandItemCount, num3);
					if (num4 <= 0)
					{
						UIRealtimeTip.Popup(Localization.Translate("栏位已满"), true, 0);
						return false;
					}
					int inhandItemCount = mainPlayer.inhandItemCount;
					int inhandItemInc = mainPlayer.inhandItemInc;
					int num5 = ItemStack.SplitInc(ref inhandItemCount, ref inhandItemInc, num4);
					val.idleDroneCount += num4;
					mainPlayer.AddHandItemCount_Unsafe(-num4);
					mainPlayer.SetHandItemInc_Unsafe(mainPlayer.inhandItemInc - num5);
					if (mainPlayer.inhandItemCount <= 0)
					{
						mainPlayer.SetHandItemId_Unsafe(0);
						mainPlayer.SetHandItemCount_Unsafe(0);
						mainPlayer.SetHandItemInc_Unsafe(0);
					}
					return false;
				}
				if (mainPlayer.inhandItemId != 0 || mainPlayer.inhandItemCount != 0)
				{
					return true;
				}
				int idleDroneCount = val.idleDroneCount;
				int num6 = idleDroneCount - 20;
				if (num6 <= 0)
				{
					if (idleDroneCount > 0)
					{
						UIRealtimeTip.Popup("内置的 " + 20 + " 架运输机不能取出", true, 0);
					}
					return false;
				}
				if (VFInput.shift || VFInput.control)
				{
					int num7 = mainPlayer.TryAddItemToPackage(5001, num6, 0, false, 0, false);
					UIItemup.Up(5001, num7);
					val.idleDroneCount -= num7;
				}
				else
				{
					mainPlayer.SetHandItemId_Unsafe(5001);
					mainPlayer.SetHandItemCount_Unsafe(num6);
					mainPlayer.SetHandItemInc_Unsafe(0);
					val.idleDroneCount -= num6;
				}
				return false;
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 运输机存取失败:" + ex.Message));
				return true;
			}
		}
	}
	[HarmonyPatch(typeof(UIStationStorage), "OnSelectItemButtonClick")]
	internal static class Patch_MinerItemFilter
	{
		internal static HashSet<int> Pending;

		internal static HashSet<int> Allowed;

		internal static bool WhitelistActive => Allowed != null;

		private static void Prefix(UIStationStorage __instance)
		{
			Pending = null;
			try
			{
				StationComponent station = __instance.station;
				UIStationWindow stationWindow = __instance.stationWindow;
				if (station == null || (Object)(object)stationWindow == (Object)null)
				{
					return;
				}
				PlanetFactory factory = stationWindow.factory;
				if (factory == null || factory.entityPool == null || station.entityId <= 0 || station.entityId >= factory.entityPool.Length || factory.entityPool[station.entityId].protoId != ProtoInjector.SuperMiner)
				{
					return;
				}
				HashSet<int> hashSet = new HashSet<int>();
				if (factory.veinPool != null)
				{
					int veinCursor = factory.veinCursor;
					for (int i = 1; i < veinCursor && i < factory.veinPool.Length; i++)
					{
						int productId = factory.veinPool[i].productId;
						if (productId > 0)
						{
							hashSet.Add(productId);
						}
					}
				}
				PlanetData planet = factory.planet;
				if (planet != null)
				{
					if (planet.waterItemId > 0)
					{
						hashSet.Add(planet.waterItemId);
					}
					PlanetData orbitAroundPlanet = planet.orbitAroundPlanet;
					if (orbitAroundPlanet != null && orbitAroundPlanet.gasItems != null)
					{
						for (int j = 0; j < orbitAroundPlanet.gasItems.Length; j++)
						{
							if (orbitAroundPlanet.gasItems[j] > 0)
							{
								hashSet.Add(orbitAroundPlanet.gasItems[j]);
							}
						}
					}
				}
				Pending = hashSet;
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 采矿机物品筛选取矿脉失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIItemPicker), "Popup")]
	internal static class Patch_ItemPickerPopup
	{
		private static void Prefix()
		{
			Patch_MinerItemFilter.Allowed = Patch_MinerItemFilter.Pending;
			Patch_MinerItemFilter.Pending = null;
		}
	}
	[HarmonyPatch(typeof(UIItemPicker), "RefreshIcons")]
	internal static class Patch_ItemPickerFilter
	{
		private static readonly FieldRef<UIItemPicker, ItemProto[]> ProtoArrayRef = AccessTools.FieldRefAccess<UIItemPicker, ItemProto[]>("protoArray");

		private static readonly FieldRef<UIItemPicker, uint[]> IndexArrayRef = AccessTools.FieldRefAccess<UIItemPicker, uint[]>("indexArray");

		private static readonly FieldRef<UIItemPicker, ComputeBuffer> IndexBufferRef = AccessTools.FieldRefAccess<UIItemPicker, ComputeBuffer>("indexBuffer");

		private static readonly FieldRef<UIItemPicker, int> CurrentTypeRef = AccessTools.FieldRefAccess<UIItemPicker, int>("currentType");

		private static void Postfix(UIItemPicker __instance)
		{
			HashSet<int> allowed = Patch_MinerItemFilter.Allowed;
			if (allowed == null)
			{
				return;
			}
			try
			{
				ItemProto[] array = ProtoArrayRef.Invoke(__instance);
				uint[] array2 = IndexArrayRef.Invoke(__instance);
				if (array == null || array2 == null)
				{
					return;
				}
				int num = 1;
				try
				{
					num = CurrentTypeRef.Invoke(__instance);
				}
				catch
				{
					num = 1;
				}
				if (num < 1)
				{
					num = 1;
				}
				HashSet<int> hashSet = new HashSet<int>();
				foreach (int item in allowed)
				{
					if (item > 0)
					{
						ItemProto val = ((ProtoSet<ItemProto>)(object)LDB.items).Select(item);
						if (val != null && val.GridIndex / 1000 == num && (GameMain.history == null || GameMain.history.ItemUnlocked(item)))
						{
							hashSet.Add(item);
						}
					}
				}
				bool flag = false;
				HashSet<int> hashSet2 = new HashSet<int>();
				for (int i = 0; i < array.Length && i < array2.Length; i++)
				{
					ItemProto val2 = array[i];
					if (val2 != null)
					{
						if (hashSet.Contains(((Proto)val2).ID))
						{
							hashSet2.Add(((Proto)val2).ID);
							continue;
						}
						array[i] = null;
						array2[i] = 0u;
						flag = true;
					}
				}
				uint[] array3 = ((GameMain.iconSet != null) ? GameMain.iconSet.itemIconIndex : null);
				if (array3 != null)
				{
					foreach (int item2 in hashSet)
					{
						if (item2 <= 0 || item2 >= array3.Length || hashSet2.Contains(item2))
						{
							continue;
						}
						uint num2 = array3[item2];
						if (num2 == 0)
						{
							continue;
						}
						int num3 = -1;
						for (int j = 0; j < array.Length && j < array2.Length; j++)
						{
							if (array[j] == null && array2[j] == 0)
							{
								num3 = j;
								break;
							}
						}
						if (num3 >= 0)
						{
							ItemProto val3 = ((ProtoSet<ItemProto>)(object)LDB.items).Select(item2);
							if (val3 != null)
							{
								array[num3] = val3;
								array2[num3] = num2;
								hashSet2.Add(item2);
								flag = true;
							}
							continue;
						}
						break;
					}
				}
				if (flag)
				{
					ComputeBuffer val4 = IndexBufferRef.Invoke(__instance);
					if (val4 != null)
					{
						val4.SetData((Array)array2);
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 过滤物品选择器失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIBuildMenu), "_OnCreate")]
	internal static class Patch_BuildMenuCategoryCreate
	{
		private static void Postfix(UIBuildMenu __instance)
		{
			try
			{
				ModBuildCategory.Ensure(__instance);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 创建建造栏专属类别失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIBuildMenu), "SetCurrentCategory")]
	internal static class Patch_BuildMenuCategorySwitch
	{
		private static bool Prefix(UIBuildMenu __instance, int category)
		{
			try
			{
				return ModBuildCategory.BeginSwitch(__instance, category);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 切换建造栏专属类别失败:" + ex.Message));
				return true;
			}
		}
	}
	[HarmonyPatch(typeof(UIBuildMenu), "_OnUpdate")]
	internal static class Patch_BuildMenuCategoryUpdate
	{
		private static void Postfix(UIBuildMenu __instance)
		{
			try
			{
				ModBuildCategory.Tick(__instance);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 刷新建造栏专属类别失败:" + ex.Message));
			}
		}
	}
	internal static class ModBuildCategory
	{
		private const int SourceRow = 8;

		private const int RowSlots = 13;

		private static readonly FieldInfo ProtosField = AccessTools.Field(typeof(UIBuildMenu), "protos");

		private static readonly FieldRef<UIBuildMenu, Player> PlayerRef = AccessTools.FieldRefAccess<UIBuildMenu, Player>("player");

		private static readonly StringBuilder Number = new StringBuilder(16);

		internal static UIButton Button;

		private static ItemProto[,] cachedProtos;

		private static UIButton anchorTemplate;

		private static bool placed;

		private static ItemProto[,] Protos()
		{
			if (cachedProtos != null)
			{
				return cachedProtos;
			}
			if (ProtosField == null)
			{
				return null;
			}
			cachedProtos = ProtosField.GetValue(null) as ItemProto[,];
			return cachedProtos;
		}

		private static void EnsureRow(ItemProto[,] protos)
		{
			int buildCategory = ProtoInjector.BuildCategory;
			if (protos == null || buildCategory < 0 || buildCategory >= protos.GetLength(0))
			{
				return;
			}
			int length = protos.GetLength(1);
			ItemProto[] itemProtos = ProtoInjector.itemProtos;
			foreach (ItemProto val in itemProtos)
			{
				if (val != null && val.BuildIndex / 100 == buildCategory)
				{
					int num = val.BuildIndex % 100;
					if (num >= 0 && num < length)
					{
						protos[buildCategory, num] = val;
					}
				}
			}
		}

		internal static void Ensure(UIBuildMenu menu)
		{
			int bc = ProtoInjector.BuildCategory;
			if (bc < 12 || (Object)(object)menu == (Object)null)
			{
				return;
			}
			EnsureRow(Protos());
			UIButton button = Button;
			if ((Object)(object)button != (Object)null && (Object)(object)((Component)button).gameObject != (Object)null)
			{
				AttachToMenu(menu);
				return;
			}
			Button = null;
			UIButton[] categoryButtons = menu.categoryButtons;
			if (categoryButtons == null || categoryButtons.Length == 0)
			{
				return;
			}
			UIButton val = ((categoryButtons.Length > 8) ? categoryButtons[8] : null);
			if ((Object)(object)val == (Object)null)
			{
				for (int num = categoryButtons.Length - 1; num >= 0; num--)
				{
					if ((Object)(object)categoryButtons[num] != (Object)null)
					{
						val = categoryButtons[num];
						break;
					}
				}
			}
			if (!((Object)(object)val == (Object)null))
			{
				UIButton val2 = ModTab.CloneFromTemplate(val, "DSPEasy.BuildCategory", bc, "改版建筑", "DSPEasy 超模建筑", ModTab.SuperMinerIcon(), "改版", delegate
				{
					menu.OnCategoryButtonClick(bc);
				});
				if (!((Object)(object)val2 == (Object)null))
				{
					PlaceAtRowEdge(val2, categoryButtons, val);
					anchorTemplate = val;
					placed = IsParentSized(val);
					Button = val2;
					AttachToMenu(menu);
				}
			}
		}

		private static bool IsParentSized(UIButton template)
		{
			//IL_0027: Unknown result type (might be due to invalid IL or missing references)
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			RectTransform val = (RectTransform)(((Object)(object)template != (Object)null) ? /*isinst with value type is only supported in some contexts*/: null);
			if ((Object)(object)val != (Object)null)
			{
				Rect rect = val.rect;
				return ((Rect)(ref rect)).width > 1f;
			}
			return false;
		}

		private static void PlaceAtRowEdge(UIButton created, UIButton[] buttons, UIButton template)
		{
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Expected O, but got Unknown
			//IL_0131: Unknown result type (might be due to invalid IL or missing references)
			//IL_0136: Unknown result type (might be due to invalid IL or missing references)
			//IL_0140: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a8: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e6: Unknown result type (might be due to invalid IL or missing references)
			//IL_01eb: 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_017c: Unknown result type (might be due to invalid IL or missing references)
			List<UIButton> list = new List<UIButton>(buttons.Length);
			foreach (UIButton val in buttons)
			{
				if ((Object)(object)val != (Object)null && (Object)(object)val != (Object)(object)created && (Object)(object)val != (Object)(object)template)
				{
					list.Add(val);
				}
			}
			RectTransform val2 = (RectTransform)((Component)created).transform;
			Transform parent = ((Component)template).transform.parent;
			RectTransform parent2 = (RectTransform)(object)((parent is RectTransform) ? parent : null);
			if (list.Count > 0)
			{
				list.Sort((UIButton a, UIButton b) => X(a).CompareTo(X(b)));
				UIButton val3 = list[0];
				float num = X(val3);
				float num2 = ((list.Count > 1) ? (X(list[1]) - num) : 52f);
				UIButton val4 = list[list.Count - 1];
				float num3 = X(val4);
				float num4 = ((list.Count > 1) ? (num3 - X(list[list.Count - 2])) : 52f);
				if (num4 < 1f)
				{
					num4 = 52f;
				}
				if (num2 < 1f)
				{
					num2 = 52f;
				}
				val2.anchoredPosition = new Vector2(num3 + num4, ((RectTransform)((Component)val4).transform).anchoredPosition.y);
				((Component)created).transform.SetSiblingIndex(((Component)val4).transform.GetSiblingIndex() + 1);
				if (!ModTab.ClampIntoParent(parent2, val2))
				{
					Plugin.Log.LogInfo((object)("[EasyBuildings] 「改版」类别按钮排在类别栏最右:" + ((object)val2.anchoredPosition/*cast due to .constrained prefix*/).ToString()));
					return;
				}
				val2.anchoredPosition = new Vector2(num - num2, ((RectTransform)((Component)val3).transform).anchoredPosition.y);
				((Component)created).transform.SetSiblingIndex(((Component)val3).transform.GetSiblingIndex());
				ModTab.ClampIntoParent(parent2, val2);
				Plugin.Log.LogWarning((object)("[EasyBuildings] 「改版」类别按钮右侧放不下,改排在类别栏最左:" + ((object)val2.anchoredPosition/*cast due to .constrained prefix*/).ToString()));
			}
			else
			{
				ModTab.PlaceAfter(created, template, null, 1);
			}
		}

		private static float X(UIButton button)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000b: Unknown result type (might be due to invalid IL or missing references)
			return ((RectTransform)((Component)button).transform).anchoredPosition.x;
		}

		private static void AttachToMenu(UIBuildMenu menu)
		{
			int buildCategory = ProtoInjector.BuildCategory;
			UIButton[] categoryButtons = menu.categoryButtons;
			if (categoryButtons != null && !((Object)(object)Button == (Object)null))
			{
				if (categoryButtons.Length <= buildCategory)
				{
					UIButton[] array = (UIButton[])(object)new UIButton[buildCategory + 1];
					Array.Copy(categoryButtons, array, categoryButtons.Length);
					array[buildCategory] = Button;
					menu.categoryButtons = array;
				}
				else
				{
					categoryButtons[buildCategory] = Button;
				}
			}
		}

		internal static bool BeginSwitch(UIBuildMenu menu, int category)
		{
			int buildCategory = ProtoInjector.BuildCategory;
			if (buildCategory < 12 || category != buildCategory)
			{
				return true;
			}
			if (PlayerRef.Invoke(menu) == null)
			{
				return false;
			}
			ItemProto[,] array = Protos();
			if (array == null)
			{
				return true;
			}
			EnsureRow(array);
			ItemProto[] array2 = (ItemProto[])(object)new ItemProto[13];
			for (int i = 0; i < 13; i++)
			{
				array2[i] = array[8, i];
				array[8, i] = array[buildCategory, i];
			}
			try
			{
				menu.SetCurrentCategory(8);
			}
			finally
			{
				for (int j = 0; j < 13; j++)
				{
					array[8, j] = array2[j];
				}
			}
			menu.currentCategory = buildCategory;
			SyncCategoryHighlight(menu, buildCategory);
			HideRowTip(menu);
			return false;
		}

		internal static void Tick(UIBuildMenu menu)
		{
			int buildCategory = ProtoInjector.BuildCategory;
			if (buildCategory < 12 || (Object)(object)menu == (Object)null)
			{
				return;
			}
			Ensure(menu);
			if (!placed && (Object)(object)Button != (Object)null)
			{
				PlaceAtRowEdge(Button, menu.categoryButtons, ((Object)(object)anchorTemplate != (Object)null) ? anchorTemplate : Button);
				placed = IsParentSized(((Object)(object)anchorTemplate != (Object)null) ? anchorTemplate : Button);
			}
			Player val = PlayerRef.Invoke(menu);
			if (val == null)
			{
				return;
			}
			ItemProto[,] array = Protos();
			if (array == null)
			{
				return;
			}
			bool showButtonsAnyways = menu.showButtonsAnyways;
			bool flag = showButtonsAnyways;
			for (int i = 0; i < 13; i++)
			{
				if (flag)
				{
					break;
				}
				ItemProto val2 = array[buildCategory, i];
				if (val2 != null && GameMain.history != null && GameMain.history.ItemUnlocked(((Proto)val2).ID))
				{
					flag = true;
				}
			}
			UIButton button = Button;
			if ((Object)(object)button != (Object)null && (Object)(object)button.button != (Object)null)
			{
				((Selectable)button.button).interactable = flag;
				button.highlighted = menu.currentCategory == buildCategory;
			}
			if (menu.currentCategory == buildCategory)
			{
				if (!flag)
				{
					menu.SetCurrentCategory(0);
					return;
				}
				RefreshRow(menu, array, val, buildCategory, showButtonsAnyways);
				HideRowTip(menu);
			}
		}

		private static void RefreshRow(UIBuildMenu menu, ItemProto[,] protos, Player player, int bc, bool showButtonsAnyways)
		{
			//IL_015a: Unknown result type (might be due to invalid IL or missing references)
			//IL_025c: Unknown result type (might be due to invalid IL or missing references)
			StorageComponent package = player.package;
			if (package == null)
			{
				return;
			}
			int num = 12;
			if (menu.childButtons != null)
			{
				num = Mathf.Min(num, menu.childButtons.Length);
			}
			if (menu.childBgs != null)
			{
				num = Mathf.Min(num, menu.childBgs.Length);
			}
			if (menu.childIcons != null)
			{
				num = Mathf.Min(num, menu.childIcons.Length);
			}
			if (menu.childNumTexts != null)
			{
				num = Mathf.Min(num, menu.childNumTexts.Length);
			}
			if (menu.childTips != null)
			{
				num = Mathf.Min(num, menu.childTips.Length);
			}
			for (int i = 0; i < num; i++)
			{
				UIButton val = menu.childButtons[i];
				if ((Object)(object)val == (Object)null || (Object)(object)val.button == (Object)null)
				{
					continue;
				}
				ItemProto val2 = protos[bc, i];
				if (val2 == null)
				{
					ResetSlot(menu, val, i);
					continue;
				}
				menu.childBgs[i].sprite = menu.normalBg;
				if (!showButtonsAnyways && (GameMain.history == null || !GameMain.history.ItemUnlocked(((Proto)val2).ID)))
				{
					ResetSlot(menu, val, i);
					continue;
				}
				val.tips.itemId = ((Proto)val2).ID;
				val.tips.itemInc = 0;
				val.tips.itemCount = 0;
				val.tips.corner = 8;
				val.tips.delay = 0.2f;
				val.tips.type = (ItemTipType)2;
				val.tips.tipTitle = "";
				val.tips.tipText = "";
				((Component)val.button).gameObject.SetActive(true);
				int num2 = package.GetItemCount(((Proto)val2).ID);
				bool flag = player.inhandItemId == ((Proto)val2).ID;
				if (flag)
				{
					num2 += player.inhandItemCount;
				}
				Number.Length = 0;
				Number.Append(' ', 6);
				StringBuilderUtility.WriteKMG(Number, 5, (long)num2, false, '\u2009', ' ');
				menu.childNumTexts[i].text = ((num2 > 0) ? Number.ToString().Trim() : "");
				((Selectable)val.button).interactable = true;
				menu.childIcons[i].sprite = val2.iconSprite;
				if (((MaskableGraphic)menu.childIcons[i]).maskable)
				{
					((MaskableGraphic)menu.childIcons[i]).maskable = false;
				}
				((Graphic)menu.childTips[i]).color = menu.tipTextColor;
				val.highlighted = flag;
			}
		}

		private static void ResetSlot(UIBuildMenu menu, UIButton child, int i)
		{
			//IL_002b: Unknown result type (might be due to invalid IL or missing references)
			child.tips.itemId = 0;
			child.tips.itemInc = 0;
			child.tips.itemCount = 0;
			child.tips.type = (ItemTipType)2;
			child.tips.tipTitle = "";
			child.tips.tipText = "";
			((Selectable)child.button).interactable = false;
			child.highlighted = false;
			((Component)child.button).gameObject.SetActive(false);
			if (menu.childBgs != null && i < menu.childBgs.Length && (Object)(object)menu.childBgs[i] != (Object)null)
			{
				menu.childBgs[i].sprite = menu.normalBg;
			}
			if (menu.childIcons != null && i < menu.childIcons.Length && (Object)(object)menu.childIcons[i] != (Object)null)
			{
				menu.childIcons[i].sprite = null;
			}
			if (menu.childNumTexts != null && i < menu.childNumTexts.Length && (Object)(object)menu.childNumTexts[i] != (Object)null)
			{
				menu.childNumTexts[i].text = "";
			}
		}

		private static void SyncCategoryHighlight(UIBuildMenu menu, int bc)
		{
			UIButton[] categoryButtons = menu.categoryButtons;
			if (categoryButtons == null)
			{
				return;
			}
			for (int i = 0; i < categoryButtons.Length; i++)
			{
				if ((Object)(object)categoryButtons[i] != (Object)null)
				{
					categoryButtons[i].highlighted = i == bc;
				}
			}
		}

		private static void HideRowTip(UIBuildMenu menu)
		{
			if (menu.currentCategory == ProtoInjector.BuildCategory && menu.categoryTips != null && menu.categoryTips.Length > 8)
			{
				Text val = menu.categoryTips[8];
				if ((Object)(object)val != (Object)null)
				{
					((Component)val).gameObject.SetActive(false);
				}
			}
		}
	}
	[HarmonyPatch(typeof(UIItemPicker), "_OnCreate")]
	internal static class Patch_ItemPickerTabCreate
	{
		private static void Postfix(UIItemPicker __instance)
		{
			try
			{
				ModTab.ItemPickerTab = ModTab.EnsurePickerTab(__instance, typeof(UIItemPicker), __instance.typeButton1, __instance.typeButton2);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 创建物品选择器专属页签失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIItemPicker), "_OnOpen")]
	internal static class Patch_ItemPickerTabOpen
	{
		private static readonly FieldRef<UIItemPicker, int> CurrentTypeRef = AccessTools.FieldRefAccess<UIItemPicker, int>("currentType");

		private static void Prefix(UIItemPicker __instance)
		{
			try
			{
				if ((Object)(object)ModTab.ItemPickerTab == (Object)null)
				{
					ModTab.ItemPickerTab = ModTab.EnsurePickerTab(__instance, typeof(UIItemPicker), __instance.typeButton1, __instance.typeButton2);
				}
				UIButton itemPickerTab = ModTab.ItemPickerTab;
				if (!((Object)(object)itemPickerTab == (Object)null) && !((Object)(object)((Component)itemPickerTab).gameObject == (Object)null))
				{
					bool whitelistActive = Patch_MinerItemFilter.WhitelistActive;
					((Component)itemPickerTab).gameObject.SetActive(!whitelistActive);
					if (whitelistActive)
					{
						CurrentTypeRef.Invoke(__instance) = 1;
					}
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 物品选择器页签状态同步失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIItemPicker), "OnTypeButtonClick")]
	internal static class Patch_ItemPickerTabHighlight
	{
		private static void Postfix(int type)
		{
			ModTab.SyncHighlight(ModTab.ItemPickerTab, type, ProtoInjector.ItemPage);
		}
	}
	[HarmonyPatch(typeof(UIRecipePicker), "_OnCreate")]
	internal static class Patch_RecipePickerTabCreate
	{
		private static void Postfix(UIRecipePicker __instance)
		{
			try
			{
				ModTab.RecipePickerTab = ModTab.EnsurePickerTab(__instance, typeof(UIRecipePicker), __instance.typeButton1, __instance.typeButton2);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 创建配方选择器专属页签失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIRecipePicker), "OnTypeButtonClick")]
	internal static class Patch_RecipePickerTabHighlight
	{
		private static void Postfix(int type)
		{
			ModTab.SyncHighlight(ModTab.RecipePickerTab, type, ProtoInjector.ItemPage);
		}
	}
	[HarmonyPatch(typeof(UIRecipePicker), "_OnOpen")]
	internal static class Patch_RecipePickerTabOpen
	{
		private static void Prefix(UIRecipePicker __instance)
		{
			try
			{
				if ((Object)(object)ModTab.RecipePickerTab == (Object)null)
				{
					ModTab.RecipePickerTab = ModTab.EnsurePickerTab(__instance, typeof(UIRecipePicker), __instance.typeButton1, __instance.typeButton2);
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 补建配方选择器专属页签失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIReplicatorWindow), "_OnCreate")]
	internal static class Patch_ReplicatorTabCreate
	{
		private static void Postfix(UIReplicatorWindow __instance)
		{
			try
			{
				ModTab.ReplicatorTab = ModTab.EnsurePickerTab(__instance, typeof(UIReplicatorWindow), __instance.typeButton1, __instance.typeButton2);
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 创建手搓窗口专属页签失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIReplicatorWindow), "OnTypeButtonClick")]
	internal static class Patch_ReplicatorTabHighlight
	{
		private static void Postfix(int type)
		{
			ModTab.SyncHighlight(ModTab.ReplicatorTab, type, ProtoInjector.ItemPage);
		}
	}
	[HarmonyPatch(typeof(UIReplicatorWindow), "_OnOpen")]
	internal static class Patch_ReplicatorTabOpen
	{
		private static void Prefix(UIReplicatorWindow __instance)
		{
			try
			{
				if ((Object)(object)ModTab.ReplicatorTab == (Object)null)
				{
					ModTab.ReplicatorTab = ModTab.EnsurePickerTab(__instance, typeof(UIReplicatorWindow), __instance.typeButton1, __instance.typeButton2);
				}
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 补建手搓窗口专属页签失败:" + ex.Message));
			}
		}
	}
	[HarmonyPatch(typeof(UIReplicatorWindow), "SetSelectedRecipe")]
	internal static class Patch_ReplicatorSelectRecipe
	{
		private static MethodInfo onTypeClick;

		private static MethodInfo selectIndex;

		private static bool Prefix(UIReplicatorWindow __instance, RecipeProto recipe, bool notify)
		{
			if (recipe == null)
			{
				return true;
			}
			int num = recipe.GridIndex / 1000;
			if (num < 3 || num != ProtoInjector.ItemPage)
			{
				return true;
			}
			try
			{
				if (!__instance.isInstantItem && (GameMain.history == null || !GameMain.history.RecipeUnlocked(((Proto)recipe).ID)))
				{
					return false;
				}
				int num2 = (recipe.GridIndex - num * 1000) / 100 - 1;
				int num3 = recipe.GridIndex % 100 - 1;
				if (num2 < 0 || num3 < 0 || num2 >= 8 || num3 >= 14)
				{
					return false;
				}
				if (onTypeClick == null)
				{
					onTypeClick = AccessTools.Method(typeof(UIReplicatorWindow), "OnTypeButtonClick", (Type[])null, (Type[])null);
				}
				if (selectIndex == null)
				{
					selectIndex = AccessTools.Method(typeof(UIReplicatorWindow), "SetSelectedRecipeIndex", (Type[])null, (Type[])null);
				}
				onTypeClick?.Invoke(__instance, new object[1] { num });
				selectIndex?.Invoke(__instance, new object[2]
				{
					num2 * 14 + num3,
					notify
				});
				return false;
			}
			catch (Exception ex)
			{
				Plugin.Log.LogWarning((object)("[EasyBuildings] 手搓窗口选中专属页配方失败:" + ex.Message));
				return true;
			}
		}
	}
	internal static class ModTab
	{
		internal const string TabName = "改版建筑";

		internal const string TabTipText = "DSPEasy 超模建筑";

		internal static readonly Color Accent = new Color(0.25f, 0.62f, 0.85f, 1f);

		internal static readonly Color AccentHover = new Color(0.36f, 0.76f, 1f, 1f);

		internal static readonly Color AccentPressed = new Color(0.17f, 0.46f, 0.68f, 1f);

		internal static readonly Color AccentDisabled = new Color(0.3f, 0.33f, 0.36f, 0.65f);

		internal static UIButton ItemPickerTab;

		internal static UIButton RecipePickerTab;

		internal static UIButton ReplicatorTab;

		private static readonly Dictionary<Type, MethodInfo> SwitchMethods = new Dictionary<Type, MethodInfo>();

		internal static Sprite SuperMinerIcon()
		{
			try
			{
				ItemProto val = ((ProtoSet<ItemProto>)(object)LDB.items).Select(ProtoInjector.SuperMiner);
				return (val != null) ? val.iconSprite : null;
			}
			catch (Exception)
			{
				return null;
			}
		}

		internal static UIButton CloneFromTemplate(UIButton template, string name, int data, string tipTitle, string tipText, Sprite icon, string label, Action<int> onPress)
		{
			//IL_00c1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f6: 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_0201: Unknown result type (might be due to invalid IL or missing references)
			//IL_020e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0219: Unknown result type (might be due to invalid IL or missing references)
			//IL_0223: Unknown result type (might be due to invalid IL or missing references)
			//IL_022e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0238: Unknown result type (might be due to invalid IL or missing references)
			//IL_0239: Unknown result type (might be due to invalid IL or missing references)
			//IL_0243: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a7: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ac: Unknown result type (might be due to invalid IL or missing references)
			//IL_02dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f7: Unknown result type (might be due to invalid IL or missing references)
			//IL_0313: Unknown result type (might be due to invalid IL or missing references)
			//IL_0318: Unknown result type (might be due to invalid IL or missing references)
			//IL_0320: Unknown result type (might be due to invalid IL or missing references)
			//IL_032b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0336: Unknown result type (might be due to invalid IL or missing references)
			//IL_0341: Unknown result type (might be due to invalid IL or missing references)
			//IL_0342: Unknown result type (might be due to invalid IL or missing references)
			//IL_0347: Unknown result type (might be due to invalid IL or missing references)
			//IL_034c: Unknown result type (might be due to invalid IL or missing references)
			//IL_034d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0352: Unknown result type (might be due to invalid IL or missing references)
			//IL_0357: Unknown result type (might be due to invalid IL or missing references)
			//IL_0358: Unknown result type (might be due to invalid IL or missing references)
			//IL_035d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0362: Unknown result type (might be due to invalid IL or missing references)
			//IL_0363: Unknown result type (might be due to invalid IL or missing references)
			//IL_0368: Unknown result type (might be due to invalid IL or missing references)
			//IL_036d: Unknown result type (might be due to invalid IL or missing references)
			//IL_036e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0373: Unknown result type (might be due to invalid IL or missing references)
			//IL_0378: Unknown result type (might be due to invalid IL or missing references)
			//IL_0383: Unknown result type (might be due to invalid IL or missing references)
			//IL_038e: Unknown result type (might be due to invalid IL or missing references)
			//IL_039a: Expected O, but got Unknown
			if ((Object)(object)template == (Object)null)
			{
				return null;
			}
			Transform parent = ((Component)template).transform.parent;
			if ((Object)(object)parent == (Object)null)
			{
				return null;
			}
			Transform val = parent.Find(name);
			if ((Object)(object)val != (Object)null)
			{
				UIButton component = ((Component)val).GetComponent<UIButton>();
				if ((Object)(object)component != (Object)null)
				{
					return component;
				}
				Object.Destroy((Object)(object)((Component)val).gameObject);
			}
			GameObject val2 = Object.Instantiate<GameObject>(((Component)template).gameObject, parent, false);
			if ((Object)(object)val2 == (Object)null)
			{
				return null;
			}
			((Object)val2).name = name;
			val2.transform.SetSiblingIndex(((Component)template).transform.GetSiblingIndex() + 1);
			val2.SetActive(false);
			Button component2 = val2.GetComponent<Button>();
			if ((Object)(object)component2 != (Object)null)
			{
				((UnityEventBase)component2.onClick).RemoveAllListeners();
			}
			Image component3 = val2.GetComponent<Image>();
			if ((Object)(object)component3 != (Object)null)
			{
				((Graphic)component3).color = Accent;
				((Graphic)component3).raycastTarget = true;
			}
			Text[] componentsInChildren = val2.GetComponentsInChildren<Text>(true);
			for (int i = 0; i < componentsInChildren.Length; i++)
			{
				if (label != null && i == 0)
				{
					componentsInChildren[i].text = label;
					((Component)componentsInChildren[i]).gameObject.SetActive(true);
				}
				else
				{
					componentsInChildren[i].text = "";
					((Component)componentsInChildren[i]).gameObject.SetActive(false);
				}
			}
			Image val3 = null;
			Image[] componentsInChildren2 = val2.GetComponentsInChildren<Image>(true);
			foreach (Image val4 in componentsInChildren2)
			{
				if (!((Object)(object)val4 == (Object)null) && !((Object)(object)((Component)val4).gameObject == (Object)(object)val2) && !((Object)(object)val4.sprite == (Object)null))
				{
					if ((Object)(object)val3 == (Object)null)
					{
						val3 = val4;
					}
					else
					{
						((Component)val4).gameObject.SetActive(false);
					}
				}
			}
			if ((Object)(object)icon != (Object)null)
			{
				if ((Object)(object)val3 != (Object)null)
				{
					val3.sprite = icon;
					((Behaviour)val3).enabled = true;
				}
				else
				{
					GameObject val5 = new GameObject("Icon", new Type[2]
					{
						typeof(RectTransform),
						typeof(Image)
					});
					RectTransform val6 = (RectTransform)val5.transform;
					((Transform)val6).SetParent(val2.transform, false);
					val6.anchorMin = new Vector2(0.14f, 0.14f);
					val6.anchorMax = new Vector2(0.86f, 0.86f);
					val6.offsetMin = Vector2.zero;
					val6.offsetMax = Vector2.zero;
					Image component4 = val5.GetComponent<Image>();
					component4.sprite = icon;
					component4.preserveAspect = true;
					((Graphic)component4).raycastTarget = false;
					val3 = component4;
				}
			}
			else if ((Object)(object)val3 != (Object)null)
			{
				((Component)val3).gameObject.SetActive(false);
			}
			UIButton val7 = val2.GetComponent<UIButton>();
			if ((Object)(object)val7 == (Object)null)
			{
				val7 = val2.AddComponent<UIButton>();
			}
			val7.data = data;
			TipSettings tips = val7.tips;
			tips.itemId = 0;
			tips.itemCount = 0;
			tips.itemInc = 0;
			tips.corner = 8;
			tips.delay = 0.2f;
			tips.type = (ItemTipType)2;
			tips.tipTitle = tipTitle;
			tips.tipText = tipText;
			val7.tips = tips;
			if ((Object)(object)component3 != (Object)null)
			{
				val7.transitions = (Transition[])(object)new Transition[1]
				{
					new Transition
					{
						target = (Graphic)(object)component3,
						damp = 0.15f,
						mouseoverSize = 1f,
						pressedSize = 1f,
						normalColor = Accent,
						mouseoverColor = AccentHover,
						pressedColor = AccentPressed,
						disabledColor = AccentDisabled,
						highlightColorOverride = AccentHover,
						highlightSizeMultiplier = 1f,
						highlightColorMultiplier = 1f,
						highlightAlphaMultiplier = 1f
					}
				};
			}
			if (onPress != null)
			{
				val7.onClick += onPress;
			}
			val2.SetActive(true);
			return val7;
		}

		internal static void PlaceAfter(UIButton clone, UIButton