Decompiled source of ControllerSupport v1.7.86

ControllerSupport.dll

Decompiled 2 hours ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Lightbug.CharacterControllerPro.Core;
using Lightbug.CharacterControllerPro.Implementation;
using Microsoft.CodeAnalysis;
using TMPro;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.Events;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Controls;
using UnityEngine.InputSystem.UI;
using UnityEngine.InputSystem.Utilities;
using UnityEngine.UI;
using UnityEngine.UIElements;

[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("ControllerSupport")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0+ff1bbba8d38aea5c762f8f77f4aacb1f7c8d74ae")]
[assembly: AssemblyProduct("ControllerSupport")]
[assembly: AssemblyTitle("ControllerSupport")]
[assembly: AssemblyVersion("1.0.0.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 ControllerSupport
{
	[BepInPlugin("com.ttr.controllersupport", "ControllerSupport", "1.7.86")]
	[DefaultExecutionOrder(-100)]
	public class ControllerSupportPlugin : BaseUnityPlugin
	{
		public enum ResponseCurveType
		{
			Linear,
			Exponential,
			Aggressive,
			Smooth
		}

		internal enum ListType
		{
			None,
			Papyrus,
			DeadTied
		}

		private enum StockpileNavArea
		{
			Items,
			Footer
		}

		private class StockpileItemData
		{
			public VisualElement Item;

			public Button TakeButton;
		}

		internal class NavGrid
		{
			public List<List<Selectable>> columns = new List<List<Selectable>>();

			public NavGrid(List<Selectable> selectables)
			{
				//IL_0051: Unknown result type (might be due to invalid IL or missing references)
				//IL_006d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0171: Unknown result type (might be due to invalid IL or missing references)
				if (selectables.Count == 0)
				{
					return;
				}
				List<Selectable> list = selectables.OrderBy((Selectable s) => GetScreenPos(s).x).ToList();
				List<Selectable> list2 = new List<Selectable>();
				float num = GetScreenPos(list[0]).x;
				foreach (Selectable item in list)
				{
					float x = GetScreenPos(item).x;
					if (Mathf.Abs(x - num) > 200f && list2.Count > 0)
					{
						columns.Add(list2);
						list2 = new List<Selectable>();
					}
					list2.Add(item);
					num = x;
				}
				if (list2.Count > 0)
				{
					columns.Add(list2);
				}
				foreach (List<Selectable> column in columns)
				{
					column.Sort(delegate(Selectable a, Selectable b)
					{
						//IL_0001: Unknown result type (might be due to invalid IL or missing references)
						//IL_0006: Unknown result type (might be due to invalid IL or missing references)
						//IL_000f: Unknown result type (might be due to invalid IL or missing references)
						//IL_0025: Unknown result type (might be due to invalid IL or missing references)
						//IL_002a: Unknown result type (might be due to invalid IL or missing references)
						//IL_0033: Unknown result type (might be due to invalid IL or missing references)
						int num3 = GetScreenPos(b).y.CompareTo(GetScreenPos(a).y);
						return (num3 != 0) ? num3 : GetScreenPos(a).x.CompareTo(GetScreenPos(b).x);
					});
				}
				for (int num2 = 0; num2 < columns.Count; num2++)
				{
					List<Selectable> list3 = columns[num2];
					list3.Average((Selectable s) => GetScreenPos(s).x);
					foreach (Selectable item2 in list3)
					{
						GetScreenPos(item2);
					}
				}
			}

			public Selectable FindNeighbor(Selectable current, int dx, int dy)
			{
				//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
				//IL_0113: Unknown result type (might be due to invalid IL or missing references)
				//IL_0165: Unknown result type (might be due to invalid IL or missing references)
				//IL_0189: Unknown result type (might be due to invalid IL or missing references)
				int num = -1;
				int num2 = -1;
				for (int i = 0; i < columns.Count; i++)
				{
					for (int j = 0; j < columns[i].Count; j++)
					{
						if ((Object)(object)columns[i][j] == (Object)(object)current)
						{
							num = i;
							num2 = j;
							break;
						}
					}
					if (num >= 0)
					{
						break;
					}
				}
				if (num < 0)
				{
					return null;
				}
				if (dy != 0)
				{
					int num3 = num2 + ((dy <= 0) ? 1 : (-1));
					if (num3 >= 0 && num3 < columns[num].Count)
					{
						return columns[num][num3];
					}
				}
				if (dx != 0)
				{
					int num4 = num + dx;
					if (num4 < 0 || num4 >= columns.Count)
					{
						return null;
					}
					int count = columns[num4].Count;
					if (count == 0)
					{
						return null;
					}
					float y = GetScreenPos(current).y;
					Selectable result = null;
					float num5 = float.MaxValue;
					int index = Math.Min(num2, count - 1);
					Selectable val = columns[num4][index];
					float num6 = Mathf.Abs(GetScreenPos(val).y - y);
					if (num6 < 150f)
					{
						result = val;
						num5 = num6;
					}
					else
					{
						string text = "";
						foreach (Selectable item in columns[num4])
						{
							float num7 = Mathf.Abs(GetScreenPos(item).y - y);
							text += $"{((Object)item).name}[Y={GetScreenPos(item).y:F1},delta={num7:F1}] ";
							if (num7 < num5)
							{
								num5 = num7;
								result = item;
							}
						}
					}
					return result;
				}
				return null;
			}

			public int GetColumnForX(float x)
			{
				//IL_005e: Unknown result type (might be due to invalid IL or missing references)
				float num = float.MaxValue;
				int result = -1;
				for (int i = 0; i < columns.Count; i++)
				{
					if (columns[i].Count == 0)
					{
						continue;
					}
					float num2 = 0f;
					int num3 = 0;
					for (int j = 0; j < columns[i].Count; j++)
					{
						Selectable val = columns[i][j];
						if ((Object)(object)val != (Object)null && Object.op_Implicit((Object)(object)val))
						{
							num2 += GetScreenPos(val).x;
							num3++;
						}
					}
					if (num3 != 0)
					{
						num2 /= (float)num3;
						float num4 = Mathf.Abs(num2 - x);
						if (num4 < num)
						{
							num = num4;
							result = i;
						}
					}
				}
				return result;
			}

			public Selectable FindYClosestInColumn(float currentY, int colIdx)
			{
				//IL_004a: Unknown result type (might be due to invalid IL or missing references)
				if (colIdx < 0 || colIdx >= columns.Count)
				{
					return null;
				}
				Selectable result = null;
				float num = float.MaxValue;
				foreach (Selectable item in columns[colIdx])
				{
					if (!((Object)(object)item == (Object)null) && Object.op_Implicit((Object)(object)item))
					{
						float num2 = Mathf.Abs(GetScreenPos(item).y - currentY);
						if (num2 < num)
						{
							num = num2;
							result = item;
						}
					}
				}
				return result;
			}
		}

		private enum WellNavArea
		{
			RecipeList,
			RightPanel,
			MapList,
			HomeCards
		}

		private class HomeCardData
		{
			public VisualElement Card;

			public List<VisualElement> Elements = new List<VisualElement>();
		}

		public const string PluginGuid = "com.ttr.controllersupport";

		public const string PluginName = "ControllerSupport";

		public const string PluginVersion = "1.7.86";

		internal static ManualLogSource Logger;

		internal static InputAction _jumpAction = null;

		internal static bool _papyrusOpen = false;

		private static InputAction _lookAction = null;

		private static bool _lookActionDisabled = false;

		private static InputAction _cameraAction = null;

		private static bool _cameraActionDisabled = false;

		internal static ConfigEntry<float> LeftStickDeadzone;

		internal static ConfigEntry<float> RightStickDeadzone;

		internal static ConfigEntry<float> LeftTriggerDeadzone;

		internal static ConfigEntry<ResponseCurveType> LeftStickCurve;

		internal static ConfigEntry<ResponseCurveType> RightStickCurve;

		internal static ConfigEntry<float> LeftStickExponent;

		internal static ConfigEntry<float> RightStickExponent;

		internal static ConfigEntry<float> LookSensitivity;

		internal static ConfigEntry<float> MovementSensitivity;

		internal static ConfigEntry<bool> ToggleCrouch;

		internal static ConfigEntry<bool> ToggleSprint;

		internal static ConfigEntry<bool> InvertLookY;

		private static bool actionsInjected = false;

		internal static bool CrouchToggled = false;

		internal static bool SprintToggled = false;

		private static bool prevCrouchButton = false;

		private static bool prevSprintButton = false;

		private static bool _blockCrouchToggleUntilRelease = false;

		internal static readonly (string action, string path)[] DefaultBindings = new(string, string)[17]
		{
			("Movement", "<Gamepad>/leftStick"),
			("Run", "<Gamepad>/leftStickPress"),
			("Look", "<Gamepad>/rightStick"),
			("Jump", "<Gamepad>/buttonSouth"),
			("Crouch", "<Gamepad>/buttonEast"),
			("Interact", "<Gamepad>/buttonWest"),
			("Push To Talk", "<Gamepad>/buttonNorth"),
			("Ragdoll", "<Gamepad>/leftShoulder"),
			("Drop", "<Gamepad>/rightShoulder"),
			("Push", "<Gamepad>/leftTrigger"),
			("Attack", "<Gamepad>/rightTrigger"),
			("Inventory", "<Gamepad>/select"),
			("Pause", "<Gamepad>/start"),
			("Item1", "<Gamepad>/dpad/up"),
			("Item2", "<Gamepad>/dpad/right"),
			("Item3", "<Gamepad>/dpad/down"),
			("Item4", "<Gamepad>/dpad/left")
		};

		internal static readonly Dictionary<string, string> RuntimeBindings = new Dictionary<string, string>();

		private static float lastProcessorUpdateTime = -1f;

		private const float PROCESSOR_UPDATE_INTERVAL = 0.3f;

		private static bool processorUpdatePending = false;

		private static float _nextInjectRetryTime = 0f;

		private static bool _wasUiOpen = false;

		internal static object _cachedPlayerController = null;

		private static object _cachedMenuController = null;

		internal static FieldInfo _isUiOpenField;

		internal static bool _pcSearched = false;

		private static float _nextPlayerControllerSearchTime = 0f;

		internal static int _uiPanelOpenCount = 0;

		internal static float _prevSprintMoveMag = 0f;

		internal static bool _movedSinceSprintToggle = false;

		internal static Slider _selectedSlider = null;

		internal static bool _sliderEditMode = false;

		private static float _sliderNavRepeatTimer = 0f;

		private static float _lastSliderHoriz = 0f;

		private static float _sliderOriginalValue = 0f;

		private static Color _sliderOriginalHandleColor;

		private static bool _sliderColorStored = false;

		private static float _sliderEditAccum = 0f;

		private static bool _sliderTypeLogged = false;

		internal static int _sliderSetGuardCount = 0;

		internal static int _sliderSetValueGuardCount = 0;

		internal static float _sliderEditStepCooldown = 0f;

		internal static bool _sliderOriginalWholeNumbers = false;

		internal static bool _sliderForceFractional = false;

		internal static Selectable _pendingNavFocus = null;

		internal static float _pendingNavTimer = 0f;

		internal static Canvas _rebindOverlayCanvas = null;

		internal static int _pendingNavDx = 0;

		internal static int _pendingNavDy = 0;

		internal static int _voiceChatGuardFrames = 0;

		internal static MonoBehaviour _disabledVoiceChatComponent = null;

		internal static Type _voiceChatOptionsButtonType = null;

		private static Type _wellPanelModeEnum;

		private static Array _wellPanelModeValues;

		private static int _currentWellTab = 0;

		private static bool _wellPanelModeResolved = false;

		private static MethodInfo _changeWellPanelMethod;

		private static float _autoFocusRetryTimer = 0f;

		internal static int _bButtonConsumedFrames = 0;

		internal static bool _suppressNextDescriptionDisableClose = false;

		internal static bool _uiWasOpenLastFrame = false;

		private static bool _serverListReadyForFocus = false;

		private static bool _serverListAutoFocused = false;

		private static bool _serverListPanelWasActive = false;

		private static float _serverListScrollAccum = 0f;

		private static float _overlayScrollAccum = 0f;

		private static List<Selectable> _cachedServerElements = new List<Selectable>();

		private static int _cachedServerElementIdx = -1;

		private static int _serverListLastFocusFrame = -5;

		private static bool _serverListNavHeldDown = false;

		private static bool _serverListNavRepeatPhase = false;

		private static float _serverListNavLastStepTime = -1f;

		internal static ListType _currentListType = ListType.None;

		internal static bool _taskListOpen = false;

		internal static int _taskListSelectedIndex = -1;

		private static bool _taskListNavHeldDown = false;

		private static bool _taskListNavRepeatPhase = false;

		private static float _taskListNavLastStepTime = -1f;

		internal static FieldInfo _taskPanelField = null;

		internal static FieldInfo _taskPapyrusField = null;

		internal static FieldInfo _taskElementParentField = null;

		internal static FieldInfo _buttonGraphicField = null;

		internal static FieldInfo _taskTextField = null;

		internal static Color _origTaskTextColor = Color.white;

		internal static TaskListUI _cachedTaskListUI = null;

		internal static List<(PlayerTaskElement element, Image graphic, Image buttonGraphic, GameObject highlightChild, Component mmUiEventListener)> _cachedTaskElements = new List<(PlayerTaskElement, Image, Image, GameObject, Component)>();

		private static Color _origHighlightColor = new Color(1f, 1f, 1f, 0f);

		private static Color _origElementGraphicColor = new Color(1f, 1f, 1f, 0f);

		private static bool _origElementGraphicColorCaptured = false;

		private static readonly Color _selectedHighlightColor = new Color(0f, 1f, 0.3f, 1f);

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

		internal static Color _origFoldoutTitleColor = Color.white;

		private static bool _graphicFallbackLogged = false;

		private static bool _textFallbackLogged = false;

		private static bool _highlightDiagLogged = false;

		private static bool _overlayDiagLogged = false;

		private static bool _feedbackDiagLogged = false;

		private static bool _diagDumpLogged = false;

		internal static bool _lateUpdaterDiagLogged = false;

		internal static bool _lateUpdaterActiveDiagLogged = false;

		private static int _highlightCallCount = 0;

		private static bool? _cursorPreviouslyVisible = null;

		internal static bool _inactiveElementsLogged = false;

		internal static GraphicRaycaster _disabledRaycaster = null;

		internal static bool _prevTaskPanelActive = false;

		internal static PropertyInfo _tiedOrDeadPropInfo = null;

		internal static bool _deadTiedCleanupPending = false;

		internal static bool _lastInputWasGamepad = false;

		private static float _lastMouseMoveTime = 0f;

		private static Vector2 _lastMousePos = Vector2.zero;

		private static float _lastGamepadInputTime = -10f;

		private const float GAMEPAD_INPUT_TIMEOUT = 0.25f;

		private static int _papyrusCacheRetryCount = 0;

		private const int MAX_PAPYRUS_CACHE_RETRIES = 60;

		private static int _deadTiedCacheRetryCount = 0;

		private const int MAX_DEADTIED_CACHE_RETRIES = 60;

		private static FieldInfo _mmEnterFeedbackField = null;

		private static FieldInfo _mmExitFeedbackField = null;

		private static MethodInfo _mmPlayFeedbacksMethod = null;

		private static FieldInfo _foldoutTitleField = null;

		private static FieldInfo _foldoutObjectField = null;

		private static Sprite _highlightSprite = null;

		private static Texture2D _highlightTex = null;

		internal static bool _overlayClosedByRelease = false;

		internal static bool _mouseOpenedInfoOverlay = false;

		internal static bool _infoOverlayOpen = false;

		internal static int _infoFoldoutIndex = -1;

		private static bool _infoFoldoutNavHeldDown = false;

		private static bool _infoFoldoutNavRepeatPhase = false;

		private static float _infoFoldoutNavLastStepTime = -1f;

		private static bool _overlayStickDiagLogged = false;

		internal static int _papyrusAPressFrame = -1;

		internal static bool _sideEffectCloseDetected = false;

		internal static FieldInfo _descToggleField = null;

		internal static DescriptionDisplayer _cachedDescriptionDisplayer = null;

		internal static FieldInfo _descriptionContainerField = null;

		internal static List<(DescriptionElement element, Toggle toggle)> _cachedFoldouts = new List<(DescriptionElement, Toggle)>();

		internal static ScrollRect _foldoutScrollRect = null;

		private static float _deferredScrollTopTimer = -1f;

		private static int _deferredScrollTopIdx = -1;

		internal static bool _suppressManualNavThisFrame = false;

		internal static float _lastControllerInputTime = -10f;

		internal static bool _controllerModeActive = false;

		private static float _lastFoldoutCacheLogTime = -1f;

		private static int _lastFoldoutCacheCount = -1;

		internal static bool _lastSettingsVisible = false;

		private static bool _wasSettingsOpen = false;

		private static bool _wasPlayerMenuOpen = false;

		private static GameObject _lastLoggedPlayerMenuPanel = null;

		internal static List<Selectable> _cachedSelectables = null;

		internal static bool _cacheNeedsRebuild = true;

		private static FieldInfo _netFieldCache;

		private static FieldInfo _brainFieldCache;

		private static PropertyInfo _scPropCache;

		private static PropertyInfo _netStateControllerPropCache;

		private static PropertyInfo _currentStatePropCache;

		private static float _wallSlideCheckTimer = 0f;

		private static bool _wallSlideCachedResult = false;

		private static FieldInfo _wcpFieldCache;

		private static FieldInfo _homeUpgradePanelFieldCache;

		private static FieldInfo _mapPanelFieldCache;

		private static FieldInfo _equipmentCraftingPanelFieldCache;

		private static FieldInfo _furnitureCraftingPanelFieldCache;

		private static FieldInfo _potionCraftingPanelFieldCache;

		private static VisualElement _cachedStockpilePanel = null;

		private static VisualElement _cachedStockpileDisplay = null;

		private static ScrollView _cachedStockpileScrollView = null;

		private static Button _cachedStockpileDepositButton = null;

		private static Button _cachedStockpileCloseButton = null;

		private static readonly List<StockpileItemData> _cachedStockpileItems = new List<StockpileItemData>();

		private static readonly List<Button> _cachedStockpileFooterButtons = new List<Button>();

		private static StockpileNavArea _stockpileNavArea = StockpileNavArea.Items;

		private static int _stockpileNavIndex = 0;

		private static int _stockpileNavColumn = 1;

		private static float _stockpileScrollAccum = 0f;

		private static float _stockpileLastNavX = 0f;

		private static float _stockpileLastNavY = 0f;

		private static bool _stockpileNavActive = false;

		private static FieldInfo _descDispFieldCache;

		private static FieldInfo _ingameMenuFieldCache;

		private static FieldInfo _settingsPanelFieldCache;

		private static FieldInfo[] _playerUiPanelFieldCache;

		private static Vector2 _lastNavStick;

		internal static float _navRepeatTimer;

		private const float NAV_INITIAL_DELAY = 0.4f;

		private const float NAV_REPEAT_RATE = 0.25f;

		internal static NavGrid _navGrid;

		private static int _wellNavIndex = 0;

		private static float _wellScrollAccum = 0f;

		private static float _wellLastDPadY = 0f;

		private static float _wellLastDPadX = 0f;

		private static VisualElement _cachedRootVE = null;

		private static ListView _cachedRecipeList = null;

		private static Button _cachedCraftBtn = null;

		private static List<Button> _cachedCostBtns = null;

		private static List<Button> _cachedMapBtns = null;

		private static List<List<HomeCardData>> _homeGrid = new List<List<HomeCardData>>();

		private static int _homeGridColumns = 0;

		private static int _homeCurrentRow = 0;

		private static int _homeCurrentCol = 0;

		private static int _homeElementIndex = 0;

		private static WellNavArea _wellNavArea = WellNavArea.RecipeList;

		private static bool _wellNavActive = false;

		private static Type _pcTypeCached = null;

		private static VisualElement _wellVisualFocusElement = null;

		private static StyleFloat _wellVisualFocusBorderTop;

		private static StyleFloat _wellVisualFocusBorderRight;

		private static StyleFloat _wellVisualFocusBorderBottom;

		private static StyleFloat _wellVisualFocusBorderLeft;

		private static StyleColor _wellVisualFocusBorderTopColor;

		private static StyleColor _wellVisualFocusBorderRightColor;

		private static StyleColor _wellVisualFocusBorderBottomColor;

		private static StyleColor _wellVisualFocusBorderLeftColor;

		private static StyleColor _wellVisualFocusBackground;

		private static object _handControllerInstance = null;

		private static MethodInfo _changeHandTargetDistanceMethod = null;

		private static MethodInfo _serverManagerGetLocalPlayerMethod = null;

		private static PropertyInfo _localPlayerHandControllerProperty = null;

		private static bool _handControllerSearched = false;

		private static float _nextHandControllerSearchTime = 0f;

		private const float HAND_CONTROLLER_SEARCH_COOLDOWN = 2f;

		private static float _handRangeStep = 0.5f;

		private static float _handRangeRepeatDelay = 0.3f;

		private static float _handRangeRepeatRate = 0.08f;

		private static float _lbHoldTime = -1f;

		private static float _rbHoldTime = -1f;

		private static object _inputHandlerInstance = null;

		private static MethodInfo _inputHandlerGetBool = null;

		private static bool _inputHandlerSearched = false;

		private static bool? _gloveRangeAdjustChecked;

		private static FieldInfo _gloveRangeActiveField;

		private static FieldInfo _glovePressingField;

		internal static string BindingsFilePath => Path.Combine(Paths.ConfigPath, "controller-bindings.json");

		private static void LoadBindings()
		{
			try
			{
				if (File.Exists(BindingsFilePath))
				{
					string[] array = File.ReadAllLines(BindingsFilePath);
					for (int i = 0; i < array.Length; i++)
					{
						string text = array[i].Trim();
						if (!string.IsNullOrEmpty(text) && !text.StartsWith("#"))
						{
							int num = text.IndexOf('|');
							if (num > 0 && num < text.Length - 1)
							{
								string key = text.Substring(0, num).Trim();
								string value = text.Substring(num + 1).Trim();
								RuntimeBindings[key] = value;
							}
						}
					}
				}
			}
			catch (Exception arg)
			{
				Logger.LogWarning((object)$"[ControllerSupport] Failed to load bindings: {arg}");
			}
			(string, string)[] defaultBindings = DefaultBindings;
			for (int i = 0; i < defaultBindings.Length; i++)
			{
				var (key2, value2) = defaultBindings[i];
				if (!RuntimeBindings.ContainsKey(key2))
				{
					RuntimeBindings[key2] = value2;
				}
			}
		}

		internal static void SaveBindings()
		{
			try
			{
				List<string> list = new List<string> { "# Controller bindings - format: action|path" };
				foreach (KeyValuePair<string, string> runtimeBinding in RuntimeBindings)
				{
					list.Add(runtimeBinding.Key + "|" + runtimeBinding.Value);
				}
				File.WriteAllLines(BindingsFilePath, list);
			}
			catch (Exception arg)
			{
				Logger.LogWarning((object)$"[ControllerSupport] Failed to save bindings: {arg}");
			}
		}

		private void Awake()
		{
			//IL_040c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0411: Unknown result type (might be due to invalid IL or missing references)
			//IL_0417: Expected O, but got Unknown
			Logger = ((BaseUnityPlugin)this).Logger;
			LeftStickDeadzone = ((BaseUnityPlugin)this).Config.Bind<float>("Deadzones", "LeftStick", 0.05f, "Deadzone for left stick (0.00-0.30). Values below this are zeroed.");
			RightStickDeadzone = ((BaseUnityPlugin)this).Config.Bind<float>("Deadzones", "RightStick", 0.05f, "Deadzone for right stick (0.00-0.30). Values below this are zeroed.");
			LeftTriggerDeadzone = ((BaseUnityPlugin)this).Config.Bind<float>("Deadzones", "LeftTrigger", 0.1f, "Deadzone for left trigger (0-0.5).");
			LeftStickCurve = ((BaseUnityPlugin)this).Config.Bind<ResponseCurveType>("Response", "LeftStickCurve", ResponseCurveType.Linear, "Response curve for left stick (movement).");
			RightStickCurve = ((BaseUnityPlugin)this).Config.Bind<ResponseCurveType>("Response", "RightStickCurve", ResponseCurveType.Linear, "Response curve for right stick (camera).");
			LeftStickExponent = ((BaseUnityPlugin)this).Config.Bind<float>("Response", "LeftStickExponent", 2f, "Exponent for exponential/aggressive curves.");
			RightStickExponent = ((BaseUnityPlugin)this).Config.Bind<float>("Response", "RightStickExponent", 2f, "Exponent for right stick curves.");
			LookSensitivity = ((BaseUnityPlugin)this).Config.Bind<float>("Input", "LookSensitivity", 1f, "Camera look sensitivity multiplier.");
			MovementSensitivity = ((BaseUnityPlugin)this).Config.Bind<float>("Input", "MovementSensitivity", 1f, "Movement input sensitivity multiplier.");
			ToggleCrouch = ((BaseUnityPlugin)this).Config.Bind<bool>("Gameplay", "ToggleCrouch", false, "Toggle crouch instead of hold.");
			ToggleSprint = ((BaseUnityPlugin)this).Config.Bind<bool>("Gameplay", "ToggleSprint", false, "Toggle sprint instead of hold.");
			InvertLookY = ((BaseUnityPlugin)this).Config.Bind<bool>("Input", "InvertLookY", false, "Invert vertical camera look.");
			InputSystem.settings.defaultDeadzoneMin = 0f;
			LoadBindings();
			Harmony.CreateAndPatchAll(typeof(InputPatches), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(ToggleActionPatches), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(WallSlideCrouchReleasePatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(DescriptionDisplayerPatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(UIPatches), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(CameraCurvePatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(SelectableOnMovePatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(SliderOnMovePatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(SliderSetPatch), "com.ttr.controllersupport");
			DerivedSliderPatches.InitializeDerivedSliderPatching();
			ExecuteMoveHandlerPatch.Initialize();
			Harmony.CreateAndPatchAll(typeof(OptionsButtonUpdatePatch), "com.ttr.controllersupport");
			try
			{
				Harmony.CreateAndPatchAll(typeof(EventSystemFocusPatch), "com.ttr.controllersupport");
			}
			catch (Exception ex)
			{
				Logger.LogWarning((object)("[ControllerSupport] Could not patch EventSystem.SetSelectedGameObject: " + ex.Message));
			}
			Harmony.CreateAndPatchAll(typeof(InputSystemHandlerReadyPatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(StaminaPatches), "com.ttr.controllersupport");
			try
			{
				Harmony.CreateAndPatchAll(typeof(PlayerRevivedPatch), "com.ttr.controllersupport");
			}
			catch (Exception arg)
			{
				Logger.LogError((object)$"[ControllerSupport] PlayerRevivedPatch registration FAILED: {arg}");
			}
			try
			{
				Harmony.CreateAndPatchAll(typeof(PlayerUntiedPatch), "com.ttr.controllersupport");
			}
			catch (Exception arg2)
			{
				Logger.LogError((object)$"[ControllerSupport] PlayerUntiedPatch registration FAILED: {arg2}");
			}
			Harmony.CreateAndPatchAll(typeof(ToggleTaskListPatch), "com.ttr.controllersupport");
			try
			{
				Harmony.CreateAndPatchAll(typeof(RefreshMouseStatePatch), "com.ttr.controllersupport");
			}
			catch (Exception arg3)
			{
				Logger.LogError((object)$"[ControllerSupport] RefreshMouseStatePatch registration FAILED: {arg3}");
			}
			Harmony.CreateAndPatchAll(typeof(ProcessJumpPatch), "com.ttr.controllersupport");
			Harmony.CreateAndPatchAll(typeof(TogglePapyrusRpcPatch), "com.ttr.controllersupport");
			try
			{
				Harmony.CreateAndPatchAll(typeof(TaskElementClickPatch), "com.ttr.controllersupport");
			}
			catch (Exception ex2)
			{
				Logger.LogWarning((object)("[ControllerSupport] Could not patch PlayerTaskElement.OnPointerClick: " + ex2.Message));
			}
			Logger.LogInfo((object)"ControllerSupport v1.7.86 loaded!");
			GameObject val = new GameObject("TaskHighlightLateUpdater");
			Object.DontDestroyOnLoad((Object)val);
			val.AddComponent<TaskHighlightLateUpdater>();
			TaskHighlightLateUpdater.Init(Logger);
		}

		private void Update()
		{
			TrackInputDevice();
			if (!actionsInjected && Time.unscaledTime >= _nextInjectRetryTime)
			{
				if (TryInjectBindings())
				{
					_nextInjectRetryTime = 0f;
				}
				else
				{
					_nextInjectRetryTime = Time.unscaledTime + 1.5f;
				}
			}
			Gamepad current = Gamepad.current;
			if (current == null)
			{
				object playerController = GetPlayerController();
				if (playerController != null)
				{
					if (_taskPanelField == null)
					{
						_taskPanelField = AccessTools.Field(playerController.GetType(), "taskPanel");
					}
					if (_taskPapyrusField == null)
					{
						_taskPapyrusField = AccessTools.Field(playerController.GetType(), "taskPapyrusList");
					}
					bool flag = false;
					bool flag2 = false;
					if (_taskPanelField != null)
					{
						object? value = _taskPanelField.GetValue(playerController);
						GameObject val = (GameObject)((value is GameObject) ? value : null);
						flag = (Object)(object)val != (Object)null && val.activeInHierarchy;
					}
					if (_taskPapyrusField != null)
					{
						object? value2 = _taskPapyrusField.GetValue(playerController);
						GameObject val2 = (GameObject)((value2 is GameObject) ? value2 : null);
						flag2 = (Object)(object)val2 != (Object)null && val2.activeInHierarchy;
					}
					if (!flag && !flag2)
					{
						EnableLookAndCameraActions();
						ClearAllTaskAndFoldoutState();
					}
					else if (flag)
					{
						Cursor.visible = true;
						Cursor.lockState = (CursorLockMode)0;
						if (_currentListType != ListType.DeadTied)
						{
							_currentListType = ListType.DeadTied;
						}
						_taskListOpen = true;
					}
				}
				UpdateLookActionState();
				return;
			}
			try
			{
				HandleUINavigation(current);
			}
			catch (Exception arg)
			{
				Logger.LogError((object)$"[ControllerSupport] HandleUINavigation: {arg}");
			}
			if (_bButtonConsumedFrames > 0)
			{
				_bButtonConsumedFrames--;
			}
			if (processorUpdatePending && Time.unscaledTime - lastProcessorUpdateTime >= 0.3f)
			{
				processorUpdatePending = false;
				lastProcessorUpdateTime = Time.unscaledTime;
				try
				{
					UpdateBindingProcessorsInternal();
				}
				catch (Exception arg2)
				{
					Logger.LogError((object)$"[ControllerSupport] UpdateBindingProcessors: {arg2}");
				}
			}
			_uiWasOpenLastFrame = IsGameplayBlockingUiOpen();
			try
			{
				HandleHandRange(current);
			}
			catch (Exception arg3)
			{
				Logger.LogError((object)$"[ControllerSupport] HandleHandRange: {arg3}");
			}
		}

		internal static bool TryInjectBindings()
		{
			//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)
			if (actionsInjected)
			{
				return true;
			}
			InputActionAsset[] array = Resources.FindObjectsOfTypeAll<InputActionAsset>();
			if (array == null || array.Length == 0)
			{
				return false;
			}
			InputActionAsset val = null;
			InputActionAsset[] array2 = array;
			foreach (InputActionAsset val2 in array2)
			{
				if (val2.actionMaps.Count > 0)
				{
					val = val2;
					break;
				}
			}
			if ((Object)(object)val == (Object)null)
			{
				return false;
			}
			try
			{
				InjectGamepadBindings(val);
				actionsInjected = true;
				return true;
			}
			catch (InvalidOperationException ex)
			{
				Logger.LogWarning((object)("[ControllerSupport] Gamepad binding injection deferred/failed: " + ex.Message));
				return false;
			}
			catch (Exception arg)
			{
				Logger.LogError((object)$"[ControllerSupport] Gamepad binding injection failed: {arg}");
				return false;
			}
		}

		private static void InjectGamepadBindings(InputActionAsset asset)
		{
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: 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_001b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_002d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e9: 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_0045: Unknown result type (might be due to invalid IL or missing references)
			//IL_004a: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f9: Unknown result type (might be due to invalid IL or missing references)
			//IL_005d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0062: 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)
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_0135: Unknown result type (might be due to invalid IL or missing references)
			//IL_013f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0144: Unknown result type (might be due to invalid IL or missing references)
			//IL_0147: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: 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_01a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ab: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b0: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b6: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c4: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_0212: Unknown result type (might be due to invalid IL or missing references)
			//IL_0247: Unknown result type (might be due to invalid IL or missing references)
			bool enabled = asset.enabled;
			asset.Disable();
			Enumerator<InputActionMap> enumerator = asset.actionMaps.GetEnumerator();
			InputBinding val;
			BindingSyntax val2;
			try
			{
				while (enumerator.MoveNext())
				{
					Enumerator<InputAction> enumerator2 = enumerator.Current.actions.GetEnumerator();
					try
					{
						while (enumerator2.MoveNext())
						{
							InputAction current = enumerator2.Current;
							ReadOnlyArray<InputBinding> bindings = current.bindings;
							for (int num = bindings.Count - 1; num >= 0; num--)
							{
								val = bindings[num];
								if (((InputBinding)(ref val)).groups != null)
								{
									val = bindings[num];
									if (((InputBinding)(ref val)).groups.Contains("Gamepad"))
									{
										val2 = InputActionSetupExtensions.ChangeBinding(current, num);
										((BindingSyntax)(ref val2)).Erase();
									}
								}
							}
						}
					}
					finally
					{
						((IDisposable)enumerator2/*cast due to .constrained prefix*/).Dispose();
					}
				}
			}
			finally
			{
				((IDisposable)enumerator/*cast due to .constrained prefix*/).Dispose();
			}
			bool flag = false;
			Enumerator<InputControlScheme> enumerator3 = asset.controlSchemes.GetEnumerator();
			try
			{
				while (enumerator3.MoveNext())
				{
					InputControlScheme current2 = enumerator3.Current;
					if (((InputControlScheme)(ref current2)).name == "Gamepad")
					{
						flag = true;
						break;
					}
				}
			}
			finally
			{
				((IDisposable)enumerator3/*cast due to .constrained prefix*/).Dispose();
			}
			if (!flag)
			{
				InputControlScheme val3 = InputActionSetupExtensions.WithRequiredDevice(new InputControlScheme("Gamepad", (IEnumerable<DeviceRequirement>)null, (string)null), "<Gamepad>");
				InputActionSetupExtensions.AddControlScheme(asset, val3);
			}
			(string, string)[] defaultBindings = DefaultBindings;
			for (int i = 0; i < defaultBindings.Length; i++)
			{
				(string, string) tuple = defaultBindings[i];
				string item = tuple.Item1;
				string item2 = tuple.Item2;
				InputAction val4 = asset.FindAction(item, false);
				if (val4 != null)
				{
					string value;
					string text = (RuntimeBindings.TryGetValue(item, out value) ? value : item2);
					val = default(InputBinding);
					val2 = InputActionSetupExtensions.AddBinding(val4, val);
					val2 = ((BindingSyntax)(ref val2)).WithPath(text);
					BindingSyntax val5 = ((BindingSyntax)(ref val2)).WithGroup("Gamepad");
					if (item == "Movement")
					{
						float value2 = LeftStickDeadzone.Value;
						float value3 = MovementSensitivity.Value;
						((BindingSyntax)(ref val5)).WithProcessor($"StickDeadzone(min={value2:F3},max=1.000),ScaleVector2(x={value3:F3},y={value3:F3})");
					}
					else if (item == "Look")
					{
						float value4 = RightStickDeadzone.Value;
						((BindingSyntax)(ref val5)).WithProcessor($"StickDeadzone(min={value4:F3},max=1.000)");
					}
				}
				else
				{
					Logger.LogDebug((object)("[ControllerSupport] Action '" + item + "' not found in asset."));
				}
			}
			if (enabled)
			{
				asset.Enable();
			}
			CacheLookAction(asset);
		}

		private static void CacheLookAction(InputActionAsset asset)
		{
			if (_lookAction != null)
			{
				return;
			}
			_lookAction = asset.FindAction("Look", false);
			if (_lookAction == null)
			{
				Logger.LogWarning((object)"[ControllerSupport] Could not find 'Look' InputAction in asset — camera block will not work");
			}
			if (_cameraAction == null)
			{
				_cameraAction = asset.FindAction("Camera", false);
				if (_cameraAction == null)
				{
					Logger.LogWarning((object)"[ControllerSupport] Could not find 'Camera' InputAction in asset — M&K mouse look block will not work");
				}
			}
		}

		internal static void EnableLookAndCameraActions()
		{
			if (_lookAction != null && !_lookAction.enabled)
			{
				_lookAction.Enable();
			}
			if (_cameraAction != null && !_cameraAction.enabled)
			{
				_cameraAction.Enable();
			}
		}

		internal static void UpdateLookActionState()
		{
			bool flag = _currentListType == ListType.DeadTied && (_infoOverlayOpen || _taskListOpen);
			if (_lookAction != null)
			{
				if (flag && !_lookActionDisabled)
				{
					if (_lookAction.enabled)
					{
						_lookAction.Disable();
					}
					_lookActionDisabled = true;
				}
				else if (!flag && _lookActionDisabled)
				{
					if (!_lookAction.enabled)
					{
						_lookAction.Enable();
					}
					_lookActionDisabled = false;
				}
			}
			if (_cameraAction == null)
			{
				return;
			}
			if (flag && !_cameraActionDisabled)
			{
				if (_cameraAction.enabled)
				{
					_cameraAction.Disable();
				}
				_cameraActionDisabled = true;
			}
			else if (!flag && _cameraActionDisabled)
			{
				if (!_cameraAction.enabled)
				{
					_cameraAction.Enable();
				}
				_cameraActionDisabled = false;
			}
		}

		internal static void UpdateBindingProcessors()
		{
			processorUpdatePending = true;
		}

		internal static void UpdateBindingProcessorsInternal()
		{
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0026: Unknown result type (might be due to invalid IL or missing references)
			InputActionAsset[] array = Resources.FindObjectsOfTypeAll<InputActionAsset>();
			if (array == null || array.Length == 0)
			{
				return;
			}
			InputActionAsset val = null;
			InputActionAsset[] array2 = array;
			foreach (InputActionAsset val2 in array2)
			{
				if (val2.actionMaps.Count > 0)
				{
					val = val2;
					break;
				}
			}
			if (!((Object)(object)val == (Object)null))
			{
				InputAction val3 = val.FindAction("Movement", false);
				if (val3 != null)
				{
					float value = LeftStickDeadzone.Value;
					float value2 = MovementSensitivity.Value;
					UpdateActionGamepadProcessors(val3, $"StickDeadzone(min={value:F3},max=1.000),ScaleVector2(x={value2:F3},y={value2:F3})");
				}
				InputAction val4 = val.FindAction("Look", false);
				if (val4 != null)
				{
					float value3 = RightStickDeadzone.Value;
					UpdateActionGamepadProcessors(val4, $"StickDeadzone(min={value3:F3},max=1.000)");
				}
			}
		}

		private static void UpdateActionGamepadProcessors(InputAction action, string processorsString)
		{
			//IL_0001: Unknown result type (might be due to invalid IL or missing references)
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0025: 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)
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			ReadOnlyArray<InputBinding> bindings = action.bindings;
			for (int i = 0; i < bindings.Count; i++)
			{
				InputBinding val = bindings[i];
				if (((InputBinding)(ref val)).groups != null)
				{
					val = bindings[i];
					if (((InputBinding)(ref val)).groups.Contains("Gamepad"))
					{
						BindingSyntax val2 = InputActionSetupExtensions.ChangeBinding(action, i);
						((BindingSyntax)(ref val2)).WithProcessors(processorsString);
						break;
					}
				}
			}
		}

		private static void AutoUnlatchSprintIfStopped()
		{
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			if (!ToggleSprint.Value || !SprintToggled)
			{
				return;
			}
			Gamepad current = Gamepad.current;
			if (current != null)
			{
				Vector2 val = ((InputControl<Vector2>)(object)current.leftStick).ReadValue();
				if (((Vector2)(ref val)).magnitude < 0.01f)
				{
					SprintToggled = false;
				}
			}
		}

		internal static Selectable FindOverlayNeighbor(Selectable source, int dx, int dy)
		{
			//IL_002f: 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_00cf: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00da: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e8: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)_rebindOverlayCanvas == (Object)null || (Object)(object)source == (Object)null)
			{
				return null;
			}
			GameObject gameObject = ((Component)_rebindOverlayCanvas).gameObject;
			if ((Object)(object)gameObject == (Object)null)
			{
				return null;
			}
			Vector2 screenPos = GetScreenPos(source);
			Selectable result = null;
			float num = float.MaxValue;
			Selectable[] allSelectablesArray = Selectable.allSelectablesArray;
			foreach (Selectable val in allSelectablesArray)
			{
				if ((Object)(object)val == (Object)null || (Object)(object)val == (Object)(object)source)
				{
					continue;
				}
				try
				{
					if (!((UIBehaviour)val).IsActive() || !val.IsInteractable())
					{
						continue;
					}
					goto IL_008d;
				}
				catch
				{
				}
				continue;
				IL_008d:
				if (!((Component)val).transform.IsChildOf(gameObject.transform) || (Object)(object)((Component)val).GetComponent<Button>() == (Object)null || (Object)(object)((Component)val).transform == (Object)(object)gameObject.transform)
				{
					continue;
				}
				Vector2 screenPos2 = GetScreenPos(val);
				float num2 = screenPos2.x - screenPos.x;
				float num3 = screenPos2.y - screenPos.y;
				if ((dx == 0 || ((int)Mathf.Sign(num2) == dx && !(Mathf.Abs(num2) < 5f) && !(Mathf.Abs(num3) > 2000f))) && (dy == 0 || ((int)Mathf.Sign(num3) == dy && !(Mathf.Abs(num3) < 5f) && !(Mathf.Abs(num2) > 2000f))))
				{
					float num4 = ((dx != 0) ? Mathf.Abs(num2) : Mathf.Abs(num3));
					float num5 = ((dx != 0) ? Mathf.Abs(num3) : Mathf.Abs(num2));
					float num6 = num4 + num5 * 2f;
					if (num6 < num)
					{
						num = num6;
						result = val;
					}
				}
			}
			return result;
		}

		internal static bool IsOverlayActive()
		{
			if ((Object)(object)_rebindOverlayCanvas != (Object)null && (Object)(object)((Component)_rebindOverlayCanvas).gameObject != (Object)null)
			{
				return ((Component)_rebindOverlayCanvas).gameObject.activeInHierarchy;
			}
			return false;
		}

		internal static void DisableVoiceChatComponent(GameObject go)
		{
			//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_004c: Expected O, but got Unknown
			if (!((Object)(object)_disabledVoiceChatComponent != (Object)null) && !((Object)(object)go == (Object)null) && !(_voiceChatOptionsButtonType == null))
			{
				Component component = go.GetComponent(_voiceChatOptionsButtonType);
				if ((Object)(object)component != (Object)null)
				{
					MonoBehaviour val = (MonoBehaviour)component;
					((Behaviour)val).enabled = false;
					_disabledVoiceChatComponent = val;
				}
			}
		}

		internal static void ReenableVoiceChatComponent()
		{
			if (!((Object)(object)_disabledVoiceChatComponent == (Object)null))
			{
				((Behaviour)_disabledVoiceChatComponent).enabled = true;
				_disabledVoiceChatComponent = null;
			}
		}

		internal static bool IsVoiceChatGameObject(GameObject go)
		{
			if ((Object)(object)go != (Object)null)
			{
				if (!((Object)go).name.Contains("voiceChat"))
				{
					return ((Object)go).name.Contains("VoiceChat");
				}
				return true;
			}
			return false;
		}

		private static void EnsureHighlightResources()
		{
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0019: Expected O, but got Unknown
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Unknown result type (might be due to invalid IL or missing references)
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)_highlightTex == (Object)null)
			{
				_highlightTex = new Texture2D(1, 1);
				_highlightTex.SetPixel(0, 0, Color.white);
				_highlightTex.Apply();
				((Object)_highlightTex).hideFlags = (HideFlags)61;
				_highlightSprite = Sprite.Create(_highlightTex, new Rect(0f, 0f, 1f, 1f), Vector2.zero);
				((Object)_highlightSprite).hideFlags = (HideFlags)61;
			}
		}

		internal static void RequestCacheRebuild()
		{
			_cacheNeedsRebuild = true;
		}

		internal static IEnumerator DelayedRebuild(float delay)
		{
			yield return (object)new WaitForSeconds(delay);
			RequestCacheRebuild();
		}

		internal static void OnGameRestarted()
		{
			actionsInjected = false;
			if (_lookAction != null && !_lookAction.enabled)
			{
				_lookAction.Enable();
			}
			_lookAction = null;
			_lookActionDisabled = false;
			if (_cameraAction != null && !_cameraAction.enabled)
			{
				_cameraAction.Enable();
			}
			_cameraAction = null;
			_cameraActionDisabled = false;
			_cachedPlayerController = null;
			_cachedMenuController = null;
			_pcSearched = false;
			_isUiOpenField = null;
			_cachedSelectables = null;
			_cacheNeedsRebuild = true;
			_navGrid = null;
			_wasUiOpen = false;
			_wasSettingsOpen = false;
			_wasPlayerMenuOpen = false;
			_lastLoggedPlayerMenuPanel = null;
			_serverListReadyForFocus = true;
			_lastSettingsVisible = false;
			_wcpFieldCache = null;
			_homeUpgradePanelFieldCache = null;
			_mapPanelFieldCache = null;
			_equipmentCraftingPanelFieldCache = null;
			_furnitureCraftingPanelFieldCache = null;
			_potionCraftingPanelFieldCache = null;
			_wellPanelModeResolved = false;
			_cachedStockpilePanel = null;
			_cachedStockpileDepositButton = null;
			_cachedStockpileCloseButton = null;
			_stockpileNavActive = false;
			ResetWellNavCache();
			_ingameMenuFieldCache = null;
			_settingsPanelFieldCache = null;
			_playerUiPanelFieldCache = null;
			_descDispFieldCache = null;
			_wallSlideCachedResult = false;
			_wallSlideCheckTimer = 0f;
			UIPatches.lastMenuPanel = null;
			UIPatches.lastPlayerPanel = null;
			_blockCrouchToggleUntilRelease = false;
			if (_sliderEditMode)
			{
				ExitSliderEditMode(confirm: true);
			}
			_sliderEditAccum = 0f;
			_selectedSlider = null;
			_sliderEditMode = false;
			ClearAllTaskAndFoldoutState();
			_taskPanelField = null;
			_taskPapyrusField = null;
			_taskElementParentField = null;
			_buttonGraphicField = null;
			_origElementGraphicColorCaptured = false;
			_highlightDiagLogged = false;
			_feedbackDiagLogged = false;
			_diagDumpLogged = false;
			_lateUpdaterDiagLogged = false;
			_lateUpdaterActiveDiagLogged = false;
			_inactiveElementsLogged = false;
			_highlightCallCount = 0;
			_prevTaskPanelActive = false;
			_deadTiedCleanupPending = false;
			_taskListNavHeldDown = false;
			_taskListNavLastStepTime = -1f;
			_cachedTaskListUI = null;
			_infoFoldoutNavHeldDown = false;
			_infoFoldoutNavLastStepTime = -1f;
			_descToggleField = null;
			_descriptionContainerField = null;
			if (_cursorPreviouslyVisible.HasValue)
			{
				Cursor.visible = _cursorPreviouslyVisible.Value;
				Cursor.lockState = (CursorLockMode)0;
				_cursorPreviouslyVisible = null;
			}
			_nextInjectRetryTime = 0f;
			GetPlayerController();
		}

		internal static void RegisterMenuController(MenuController menuController)
		{
			if (!((Object)(object)menuController == (Object)null))
			{
				_cachedMenuController = menuController;
			}
		}

		internal static object GetPlayerController()
		{
			if (_pcSearched && IsUnityObjectAlive(_cachedPlayerController) && IsLocalPlayerController(_cachedPlayerController))
			{
				return _cachedPlayerController;
			}
			if (_pcSearched && _cachedPlayerController == null && Time.unscaledTime < _nextPlayerControllerSearchTime)
			{
				return null;
			}
			Type type = AppDomain.CurrentDomain.GetAssemblies().SelectMany(delegate(Assembly a)
			{
				try
				{
					return a.GetTypes();
				}
				catch
				{
					return new Type[0];
				}
			}).FirstOrDefault((Type t) => t.Name == "PlayerController");
			if (type == null)
			{
				return null;
			}
			_cachedPlayerController = ResolveLocalPlayerController(type);
			_pcSearched = true;
			if (_cachedPlayerController == null)
			{
				_nextPlayerControllerSearchTime = Time.unscaledTime + 1f;
			}
			if (_isUiOpenField == null)
			{
				_isUiOpenField = AccessTools.Field(type, "isUiOpen");
			}
			return _cachedPlayerController;
		}

		private static object ResolveLocalPlayerController(Type pcType)
		{
			try
			{
				if (_serverManagerGetLocalPlayerMethod == null)
				{
					_serverManagerGetLocalPlayerMethod = AccessTools.Method(AppDomain.CurrentDomain.GetAssemblies().SelectMany(delegate(Assembly a)
					{
						try
						{
							return a.GetTypes();
						}
						catch
						{
							return new Type[0];
						}
					}).FirstOrDefault((Type t) => t.Name == "ServerManager"), "GetLocalPlayer", (Type[])null, (Type[])null);
				}
				object obj = _serverManagerGetLocalPlayerMethod?.Invoke(null, null);
				if (IsUnityObjectAlive(obj))
				{
					object obj2 = AccessTools.Property(obj.GetType(), "Controller")?.GetValue(obj, null);
					if (IsUnityObjectAlive(obj2))
					{
						return obj2;
					}
				}
			}
			catch
			{
			}
			try
			{
				MethodInfo method = typeof(Object).GetMethod("FindObjectsOfType", new Type[0]);
				if (method == null)
				{
					return null;
				}
				if (!(method.MakeGenericMethod(pcType).Invoke(null, null) is Array array))
				{
					return null;
				}
				foreach (object item in array)
				{
					if (IsUnityObjectAlive(item) && IsLocalPlayerController(item))
					{
						return item;
					}
				}
				foreach (object item2 in array)
				{
					if (IsUnityObjectAlive(item2))
					{
						return item2;
					}
				}
			}
			catch
			{
			}
			return null;
		}

		private static bool IsLocalPlayerController(object controller)
		{
			if (!IsUnityObjectAlive(controller))
			{
				return false;
			}
			try
			{
				if (IsLocalPlayer(controller) || IsNetworkOwner(controller))
				{
					return true;
				}
				object obj = AccessTools.Field(controller.GetType(), "networking")?.GetValue(controller);
				return IsUnityObjectAlive(obj) && (IsLocalPlayer(obj) || IsNetworkOwner(obj));
			}
			catch
			{
				return false;
			}
		}

		internal static bool IsWallSliding()
		{
			if (Time.time - _wallSlideCheckTimer < 0.1f)
			{
				return _wallSlideCachedResult;
			}
			_wallSlideCheckTimer = Time.time;
			object playerController = GetPlayerController();
			if (playerController == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			if (_netFieldCache == null)
			{
				_netFieldCache = AccessTools.Field(playerController.GetType(), "networking");
			}
			if (_netFieldCache == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			object value = _netFieldCache.GetValue(playerController);
			if (value == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			if (_netStateControllerPropCache == null)
			{
				_netStateControllerPropCache = value.GetType().GetProperty("StateController");
			}
			object obj = _netStateControllerPropCache?.GetValue(value);
			if (obj == null)
			{
				if (_brainFieldCache == null)
				{
					_brainFieldCache = AccessTools.Field(playerController.GetType(), "brain");
				}
				object obj2 = _brainFieldCache?.GetValue(playerController);
				if (obj2 != null)
				{
					if (_scPropCache == null)
					{
						_scPropCache = obj2.GetType().GetProperty("CharacterStateController");
					}
					obj = _scPropCache?.GetValue(obj2);
				}
			}
			if (obj == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			if (_currentStatePropCache == null)
			{
				_currentStatePropCache = obj.GetType().GetProperty("CurrentState");
			}
			if (_currentStatePropCache == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			object value2 = _currentStatePropCache.GetValue(obj);
			if (value2 == null)
			{
				_wallSlideCachedResult = false;
				return false;
			}
			_wallSlideCachedResult = value2.GetType().Name == "WallSlide";
			return _wallSlideCachedResult;
		}

		internal static bool IsUiOpen()
		{
			object playerController = GetPlayerController();
			if (playerController == null)
			{
				return false;
			}
			if (_isUiOpenField == null)
			{
				_isUiOpenField = AccessTools.Field(playerController.GetType(), "isUiOpen");
			}
			bool flag = false;
			if (_isUiOpenField != null)
			{
				flag = (bool)_isUiOpenField.GetValue(playerController);
			}
			if (_uiPanelOpenCount > 0)
			{
				if (flag)
				{
					return true;
				}
				_uiPanelOpenCount = 0;
			}
			if (!flag && IsInGameMenuOpen(playerController))
			{
				flag = true;
			}
			if (!flag)
			{
				GameObject playerSettingsPanel = GetPlayerSettingsPanel(playerController);
				if ((Object)(object)playerSettingsPanel != (Object)null && playerSettingsPanel.activeInHierarchy)
				{
					flag = true;
				}
			}
			return flag;
		}

		private static bool IsInGameMenuOpen(object pc = null)
		{
			pc = pc ?? GetPlayerController();
			if (pc == null)
			{
				return false;
			}
			GameObject rawInGameMenuPanel = GetRawInGameMenuPanel(pc);
			if ((Object)(object)rawInGameMenuPanel != (Object)null)
			{
				return rawInGameMenuPanel.activeInHierarchy;
			}
			return false;
		}

		private static GameObject GetPlayerSettingsPanel(object pc = null)
		{
			pc = pc ?? GetPlayerController();
			if (pc == null)
			{
				return null;
			}
			if (_settingsPanelFieldCache == null)
			{
				_settingsPanelFieldCache = AccessTools.Field(pc.GetType(), "settingsPanel");
			}
			object? obj = _settingsPanelFieldCache?.GetValue(pc);
			return (GameObject)((obj is GameObject) ? obj : null);
		}

		private static GameObject GetInGameMenuPanel(object pc = null)
		{
			return GetRawInGameMenuPanel(pc);
		}

		private static GameObject GetRawInGameMenuPanel(object pc = null)
		{
			pc = pc ?? GetPlayerController();
			if (pc == null)
			{
				return null;
			}
			if (_ingameMenuFieldCache == null)
			{
				_ingameMenuFieldCache = AccessTools.Field(pc.GetType(), "ingameMenu");
			}
			object? obj = _ingameMenuFieldCache?.GetValue(pc);
			return (GameObject)((obj is GameObject) ? obj : null);
		}

		private static GameObject FindActivePlayerUiPanel(object pc = null, bool includeSettings = true)
		{
			pc = pc ?? GetPlayerController();
			if (pc == null)
			{
				return null;
			}
			Type type = pc.GetType();
			if (_playerUiPanelFieldCache == null)
			{
				_playerUiPanelFieldCache = (from f in type.GetFields(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)
					where typeof(GameObject).IsAssignableFrom(f.FieldType)
					select f).ToArray();
			}
			GameObject result = null;
			int num = 0;
			FieldInfo[] playerUiPanelFieldCache = _playerUiPanelFieldCache;
			foreach (FieldInfo fieldInfo in playerUiPanelFieldCache)
			{
				if (!includeSettings && fieldInfo.Name.IndexOf("settings", StringComparison.OrdinalIgnoreCase) >= 0)
				{
					continue;
				}
				object? value = fieldInfo.GetValue(pc);
				GameObject val = (GameObject)((value is GameObject) ? value : null);
				if (IsNavigablePlayerPanel(val))
				{
					int num3 = val.GetComponentsInChildren<Selectable>(false).Count((Selectable s) => (Object)(object)s != (Object)null && ((UIBehaviour)s).IsActive() && s.IsInteractable());
					string text = (fieldInfo.Name + " " + ((Object)val).name).ToLowerInvariant();
					if (text.Contains("menu") || text.Contains("pause") || text.Contains("setting"))
					{
						num3 += 1000;
					}
					if (num3 > num)
					{
						num = num3;
						result = val;
					}
				}
			}
			return result;
		}

		private static bool IsNavigablePlayerPanel(GameObject panel)
		{
			if ((Object)(object)panel == (Object)null || !panel.activeInHierarchy)
			{
				return false;
			}
			try
			{
				return panel.GetComponentsInChildren<Selectable>(false).Any((Selectable s) => (Object)(object)s != (Object)null && ((UIBehaviour)s).IsActive() && s.IsInteractable());
			}
			catch
			{
				return false;
			}
		}

		private static void LogPlayerMenuPanelState(GameObject panel)
		{
			if (!((Object)(object)panel == (Object)null) && !((Object)(object)panel == (Object)(object)_lastLoggedPlayerMenuPanel))
			{
				_lastLoggedPlayerMenuPanel = panel;
			}
		}

		private static bool IsElementDisplayed(VisualElement element)
		{
			//IL_0022: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Invalid comparison between Unknown and I4
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Invalid comparison between Unknown and I4
			//IL_004c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: Invalid comparison between Unknown and I4
			if (element == null)
			{
				return false;
			}
			for (VisualElement val = element; val != null; val = val.parent)
			{
				try
				{
					if (!val.visible)
					{
						return false;
					}
				}
				catch
				{
				}
				try
				{
					if ((int)val.resolvedStyle.display == 1)
					{
						return false;
					}
				}
				catch
				{
				}
				try
				{
					StyleEnum<DisplayStyle> display = val.style.display;
					if ((int)display.keyword != 1 && (int)display.value == 1)
					{
						return false;
					}
				}
				catch
				{
				}
			}
			return true;
		}

		internal static bool IsGameplayBlockingUiOpen()
		{
			object playerController = GetPlayerController();
			if (playerController == null)
			{
				return false;
			}
			if (!IsUiOpen() && !IsWellUiOpen(playerController) && !IsStockpileUiOpen())
			{
				return IsDescriptionOverlayOpen();
			}
			return true;
		}

		internal static bool IsWellUiOpen(object pc = null)
		{
			pc = pc ?? GetPlayerController();
			if (pc == null)
			{
				return false;
			}
			Type type = pc.GetType();
			if (_wcpFieldCache == null)
			{
				_wcpFieldCache = AccessTools.Field(type, "wellCraftingPanel");
			}
			object? obj = _wcpFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj is VisualElement) ? obj : null)))
			{
				return true;
			}
			if (_homeUpgradePanelFieldCache == null)
			{
				_homeUpgradePanelFieldCache = AccessTools.Field(type, "homeUpgradePanel");
			}
			object? obj2 = _homeUpgradePanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj2 is VisualElement) ? obj2 : null)))
			{
				return true;
			}
			if (_mapPanelFieldCache == null)
			{
				_mapPanelFieldCache = AccessTools.Field(type, "mapPanel");
			}
			object? obj3 = _mapPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj3 is VisualElement) ? obj3 : null)))
			{
				return true;
			}
			if (_equipmentCraftingPanelFieldCache == null)
			{
				_equipmentCraftingPanelFieldCache = AccessTools.Field(type, "equipmentCraftingPanel");
			}
			object? obj4 = _equipmentCraftingPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj4 is VisualElement) ? obj4 : null)))
			{
				return true;
			}
			if (_furnitureCraftingPanelFieldCache == null)
			{
				_furnitureCraftingPanelFieldCache = AccessTools.Field(type, "furnitureCraftingPanel");
			}
			object? obj5 = _furnitureCraftingPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj5 is VisualElement) ? obj5 : null)))
			{
				return true;
			}
			if (_potionCraftingPanelFieldCache == null)
			{
				_potionCraftingPanelFieldCache = AccessTools.Field(type, "potionCraftingPanel");
			}
			object? obj6 = _potionCraftingPanelFieldCache?.GetValue(pc);
			return IsElementDisplayed((VisualElement)((obj6 is VisualElement) ? obj6 : null));
		}

		internal static bool IsStockpileUiOpen()
		{
			CacheWellRoot();
			if (_cachedRootVE == null)
			{
				return false;
			}
			_cachedStockpilePanel = UQueryExtensions.Q<VisualElement>(_cachedRootVE, "Stockpile", (string)null);
			return IsElementDisplayed(_cachedStockpilePanel);
		}

		private static void ResetStockpileNavCache()
		{
			ClearWellControllerHighlight();
			_cachedStockpilePanel = null;
			_cachedStockpileDisplay = null;
			_cachedStockpileScrollView = null;
			_cachedStockpileDepositButton = null;
			_cachedStockpileCloseButton = null;
			_cachedStockpileItems.Clear();
			_cachedStockpileFooterButtons.Clear();
			_stockpileNavArea = StockpileNavArea.Items;
			_stockpileNavIndex = 0;
			_stockpileNavColumn = 1;
			_stockpileScrollAccum = 0f;
			_stockpileLastNavX = 0f;
			_stockpileLastNavY = 0f;
			_stockpileNavActive = false;
		}

		private static void CacheStockpileElements()
		{
			CacheWellRoot();
			if (_cachedRootVE != null)
			{
				_cachedStockpilePanel = UQueryExtensions.Q<VisualElement>(_cachedRootVE, "Stockpile", (string)null);
				if (_cachedStockpilePanel != null)
				{
					_cachedStockpileDisplay = UQueryExtensions.Q<VisualElement>(_cachedStockpilePanel, "StockpileDisplay", (string)null);
					_cachedStockpileScrollView = ((_cachedStockpileDisplay != null) ? UQueryExtensions.Q<ScrollView>(_cachedStockpileDisplay, (string)null, (string)null) : null);
					CacheStockpileItems();
					CacheStockpileFooterButtons();
				}
			}
		}

		private static void CacheStockpileItems()
		{
			_cachedStockpileItems.Clear();
			ScrollView cachedStockpileScrollView = _cachedStockpileScrollView;
			VisualElement val = ((cachedStockpileScrollView != null) ? ((VisualElement)cachedStockpileScrollView).contentContainer : null);
			if (val == null)
			{
				return;
			}
			foreach (VisualElement item in val.Children())
			{
				if (IsElementDisplayed(item) && (item.ClassListContains("item-display") || !(((object)item).GetType().Name != "ItemDisplayView")))
				{
					Button val2 = FindDescendantButtonWithClass(item, "item-display__button_take");
					if (val2 != null && IsElementDisplayed((VisualElement)(object)val2))
					{
						_cachedStockpileItems.Add(new StockpileItemData
						{
							Item = item,
							TakeButton = val2
						});
					}
				}
			}
		}

		private static void CacheStockpileFooterButtons()
		{
			_cachedStockpileFooterButtons.Clear();
			_cachedStockpileDepositButton = UQueryExtensions.Q<Button>(_cachedStockpilePanel, "DepositResources", (string)null);
			_cachedStockpileCloseButton = UQueryExtensions.Q<Button>(_cachedStockpilePanel, "CloseMenu", (string)null);
			if (_cachedStockpileDepositButton != null && IsElementDisplayed((VisualElement)(object)_cachedStockpileDepositButton))
			{
				_cachedStockpileFooterButtons.Add(_cachedStockpileDepositButton);
			}
			if (_cachedStockpileCloseButton != null && IsElementDisplayed((VisualElement)(object)_cachedStockpileCloseButton))
			{
				_cachedStockpileFooterButtons.Add(_cachedStockpileCloseButton);
			}
		}

		private static Button FindDescendantButtonWithClass(VisualElement root, string className)
		{
			if (root == null)
			{
				return null;
			}
			Button val = (Button)(object)((root is Button) ? root : null);
			if (val != null && ((VisualElement)val).ClassListContains(className))
			{
				return val;
			}
			foreach (VisualElement item in root.Children())
			{
				Button val2 = FindDescendantButtonWithClass(item, className);
				if (val2 != null)
				{
					return val2;
				}
			}
			return null;
		}

		private static void RefreshStockpileCache()
		{
			CacheStockpileElements();
			if (_stockpileNavArea == StockpileNavArea.Items && _cachedStockpileItems.Count == 0)
			{
				_stockpileNavArea = StockpileNavArea.Footer;
			}
			if (_stockpileNavArea == StockpileNavArea.Footer && _cachedStockpileFooterButtons.Count == 0 && _cachedStockpileItems.Count > 0)
			{
				_stockpileNavArea = StockpileNavArea.Items;
			}
			if (_stockpileNavArea == StockpileNavArea.Items)
			{
				_stockpileNavIndex = Mathf.Clamp(_stockpileNavIndex, 0, _cachedStockpileItems.Count - 1);
				_stockpileNavColumn = Mathf.Clamp(_stockpileNavColumn, 0, 1);
			}
			else
			{
				_stockpileNavIndex = Mathf.Clamp(_stockpileNavIndex, 0, Mathf.Max(0, _cachedStockpileFooterButtons.Count - 1));
				_stockpileNavColumn = 0;
			}
		}

		private static VisualElement GetCurrentStockpileElement()
		{
			if (_stockpileNavArea == StockpileNavArea.Items)
			{
				if (_stockpileNavIndex < 0 || _stockpileNavIndex >= _cachedStockpileItems.Count)
				{
					return null;
				}
				StockpileItemData stockpileItemData = _cachedStockpileItems[_stockpileNavIndex];
				if (_stockpileNavColumn != 0)
				{
					return (VisualElement)(object)stockpileItemData.TakeButton;
				}
				return stockpileItemData.Item;
			}
			if (_stockpileNavIndex < 0 || _stockpileNavIndex >= _cachedStockpileFooterButtons.Count)
			{
				return null;
			}
			return (VisualElement)(object)_cachedStockpileFooterButtons[_stockpileNavIndex];
		}

		private static void FocusStockpileElement()
		{
			VisualElement currentStockpileElement = GetCurrentStockpileElement();
			if (currentStockpileElement != null)
			{
				try
				{
					((Focusable)currentStockpileElement).Focus();
				}
				catch
				{
				}
				EnsureStockpileSelectionVisible(currentStockpileElement);
				SetWellControllerHighlight(currentStockpileElement);
			}
		}

		private static void EnsureStockpileSelectionVisible(VisualElement focusedElement)
		{
			//IL_0062: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: 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)
			//IL_006e: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c5: Unknown result type (might be due to invalid IL or missing references)
			//IL_0115: Unknown result type (might be due to invalid IL or missing references)
			//IL_0148: Unknown result type (might be due to invalid IL or missing references)
			//IL_0160: Unknown result type (might be due to invalid IL or missing references)
			ScrollView cachedStockpileScrollView = _cachedStockpileScrollView;
			if (cachedStockpileScrollView == null || cachedStockpileScrollView.verticalScroller == null || focusedElement == null)
			{
				return;
			}
			VisualElement val = focusedElement;
			if (_stockpileNavArea == StockpileNavArea.Items && _stockpileNavIndex >= 0 && _stockpileNavIndex < _cachedStockpileItems.Count)
			{
				val = _cachedStockpileItems[_stockpileNavIndex].Item ?? focusedElement;
			}
			if (val == null)
			{
				return;
			}
			VisualElement val2 = (VisualElement)(((object)cachedStockpileScrollView.contentViewport) ?? ((object)cachedStockpileScrollView));
			Rect worldBound;
			Rect worldBound2;
			try
			{
				worldBound = val2.worldBound;
				worldBound2 = val.worldBound;
			}
			catch
			{
				return;
			}
			if (((Rect)(ref worldBound)).height <= 0f || ((Rect)(ref worldBound2)).height <= 0f)
			{
				return;
			}
			float highValue = cachedStockpileScrollView.verticalScroller.highValue;
			if (highValue <= 0f)
			{
				return;
			}
			VisualElement val3 = ((VisualElement)cachedStockpileScrollView).contentContainer ?? cachedStockpileScrollView.contentViewport;
			Rect worldBound3;
			try
			{
				worldBound3 = val3.worldBound;
			}
			catch
			{
				return;
			}
			float num = ((Rect)(ref worldBound)).y - ((Rect)(ref worldBound3)).y;
			float num2 = ((Rect)(ref worldBound2)).y - ((Rect)(ref worldBound3)).y;
			float num3 = num2 + ((Rect)(ref worldBound2)).height;
			float num4 = num + 8f;
			float num5 = num + ((Rect)(ref worldBound)).height - 8f;
			float y = cachedStockpileScrollView.scrollOffset.y;
			if (num2 < num4)
			{
				y -= num4 - num2;
			}
			else
			{
				if (!(num3 > num5))
				{
					return;
				}
				y += num3 - num5;
			}
			cachedStockpileScrollView.scrollOffset = new Vector2(cachedStockpileScrollView.scrollOffset.x, Mathf.Clamp(y, 0f, highValue));
		}

		private static void NavigateStockpileVertical(int dir)
		{
			RefreshStockpileCache();
			if (_stockpileNavArea == StockpileNavArea.Items)
			{
				if (_cachedStockpileItems.Count == 0)
				{
					if (_cachedStockpileFooterButtons.Count > 0)
					{
						_stockpileNavArea = StockpileNavArea.Footer;
						_stockpileNavIndex = 0;
						_stockpileNavColumn = 0;
						FocusStockpileElement();
					}
					return;
				}
				int num = _stockpileNavIndex + dir;
				if (num >= 0 && num < _cachedStockpileItems.Count)
				{
					_stockpileNavIndex = num;
				}
				else
				{
					if (dir <= 0 || _cachedStockpileFooterButtons.Count <= 0)
					{
						return;
					}
					_stockpileNavArea = StockpileNavArea.Footer;
					_stockpileNavIndex = Mathf.Min(_stockpileNavColumn, _cachedStockpileFooterButtons.Count - 1);
					_stockpileNavColumn = 0;
				}
				FocusStockpileElement();
			}
			else if (dir < 0 && _cachedStockpileItems.Count > 0)
			{
				_stockpileNavArea = StockpileNavArea.Items;
				_stockpileNavIndex = _cachedStockpileItems.Count - 1;
				_stockpileNavColumn = 1;
				FocusStockpileElement();
			}
		}

		private static void NavigateStockpileHorizontal(int dir)
		{
			RefreshStockpileCache();
			if (_stockpileNavArea == StockpileNavArea.Items)
			{
				int num = Mathf.Clamp(_stockpileNavColumn + dir, 0, 1);
				if (num != _stockpileNavColumn)
				{
					_stockpileNavColumn = num;
					FocusStockpileElement();
				}
			}
			else if (_cachedStockpileFooterButtons.Count > 1)
			{
				int num2 = Mathf.Clamp(_stockpileNavIndex + dir, 0, _cachedStockpileFooterButtons.Count - 1);
				if (num2 != _stockpileNavIndex)
				{
					_stockpileNavIndex = num2;
					FocusStockpileElement();
				}
			}
		}

		private static void ScrollStockpile(Gamepad gp)
		{
			//IL_007c: 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_00af: Unknown result type (might be due to invalid IL or missing references)
			float num = ((InputControl<float>)(object)((Vector2Control)gp.rightStick).y).ReadValue();
			if (Mathf.Abs(num) <= 0.3f)
			{
				_stockpileScrollAccum = 0f;
				return;
			}
			ScrollView cachedStockpileScrollView = _cachedStockpileScrollView;
			if (cachedStockpileScrollView == null || cachedStockpileScrollView.verticalScroller == null)
			{
				return;
			}
			float highValue = cachedStockpileScrollView.verticalScroller.highValue;
			if (!(highValue <= 0f))
			{
				_stockpileScrollAccum += (0f - num) * Time.deltaTime * 550f;
				if (!(Mathf.Abs(_stockpileScrollAccum) <= 10f))
				{
					float num2 = cachedStockpileScrollView.scrollOffset.y + _stockpileScrollAccum;
					_stockpileScrollAccum = 0f;
					cachedStockpileScrollView.scrollOffset = new Vector2(cachedStockpileScrollView.scrollOffset.x, Mathf.Clamp(num2, 0f, highValue));
				}
			}
		}

		private static void HandleStockpileNavigation(Gamepad gp)
		{
			if (!IsStockpileUiOpen())
			{
				if (_stockpileNavActive)
				{
					ResetStockpileNavCache();
				}
				return;
			}
			if (IsDescriptionOverlayOpen())
			{
				if (gp.buttonEast.wasPressedThisFrame)
				{
					CloseDescriptionOverlay();
					_bButtonConsumedFrames = 3;
				}
				return;
			}
			if (!_stockpileNavActive)
			{
				_stockpileNavActive = true;
				CacheStockpileElements();
				_stockpileNavArea = ((_cachedStockpileItems.Count <= 0) ? StockpileNavArea.Footer : StockpileNavArea.Items);
				_stockpileNavIndex = 0;
				_stockpileNavColumn = ((_cachedStockpileItems.Count > 0) ? 1 : 0);
				FocusStockpileElement();
			}
			RefreshStockpileCache();
			ScrollStockpile(gp);
			float num = ((InputControl<float>)(object)((Vector2Control)gp.dpad).x).ReadValue();
			float num2 = ((InputControl<float>)(object)((Vector2Control)gp.leftStick).x).ReadValue();
			float num3 = ((InputControl<float>)(object)((Vector2Control)gp.dpad).y).ReadValue();
			float num4 = ((InputControl<float>)(object)((Vector2Control)gp.leftStick).y).ReadValue();
			float num5 = ((Mathf.Abs(num2) > 0.6f) ? num2 : ((Mathf.Abs(num) > 0.5f) ? num : 0f));
			float num6 = ((Mathf.Abs(num4) > 0.6f) ? num4 : ((Mathf.Abs(num3) > 0.5f) ? num3 : 0f));
			if ((num5 != 0f && _stockpileLastNavX == 0f) || (num6 != 0f && _stockpileLastNavY == 0f))
			{
				if (num5 != 0f)
				{
					NavigateStockpileHorizontal((num5 > 0f) ? 1 : (-1));
				}
				else
				{
					NavigateStockpileVertical((num6 < 0f) ? 1 : (-1));
				}
			}
			_stockpileLastNavX = num5;
			_stockpileLastNavY = num6;
			if (gp.buttonSouth.wasPressedThisFrame)
			{
				VisualElement currentStockpileElement = GetCurrentStockpileElement();
				if (currentStockpileElement != null)
				{
					SimulateVEClick(currentStockpileElement);
				}
			}
			if (gp.buttonWest.wasPressedThisFrame && _cachedStockpileDepositButton != null && IsElementDisplayed((VisualElement)(object)_cachedStockpileDepositButton))
			{
				SimulateVEClick((VisualElement)(object)_cachedStockpileDepositButton);
			}
		}

		private static int GetVisibleWellTab(object pc)
		{
			if (pc == null)
			{
				return _currentWellTab;
			}
			Type type = pc.GetType();
			if (_wcpFieldCache == null)
			{
				_wcpFieldCache = AccessTools.Field(type, "wellCraftingPanel");
			}
			object? obj = _wcpFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj is VisualElement) ? obj : null)))
			{
				return 0;
			}
			if (_mapPanelFieldCache == null)
			{
				_mapPanelFieldCache = AccessTools.Field(type, "mapPanel");
			}
			object? obj2 = _mapPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj2 is VisualElement) ? obj2 : null)))
			{
				return 1;
			}
			if (_furnitureCraftingPanelFieldCache == null)
			{
				_furnitureCraftingPanelFieldCache = AccessTools.Field(type, "furnitureCraftingPanel");
			}
			object? obj3 = _furnitureCraftingPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj3 is VisualElement) ? obj3 : null)))
			{
				return 2;
			}
			if (_homeUpgradePanelFieldCache == null)
			{
				_homeUpgradePanelFieldCache = AccessTools.Field(type, "homeUpgradePanel");
			}
			object? obj4 = _homeUpgradePanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj4 is VisualElement) ? obj4 : null)))
			{
				return 3;
			}
			if (_potionCraftingPanelFieldCache == null)
			{
				_potionCraftingPanelFieldCache = AccessTools.Field(type, "potionCraftingPanel");
			}
			object? obj5 = _potionCraftingPanelFieldCache?.GetValue(pc);
			if (IsElementDisplayed((VisualElement)((obj5 is VisualElement) ? obj5 : null)))
			{
				return 4;
			}
			return _currentWellTab;
		}

		internal static bool IsPlayerControllerUiOpen(object playerController)
		{
			if (playerController == null)
			{
				return false;
			}
			FieldInfo fieldInfo = _isUiOpenField ?? AccessTools.Field(playerController.GetType(), "isUiOpen");
			if (fieldInfo == null)
			{
				return false;
			}
			_isUiOpenField = fieldInfo;
			try
			{
				return (bool)fieldInfo.GetValue(playerController);
			}
			catch
			{
				return false;
			}
		}

		private static void EnsureEventSystem()
		{
			//IL_0014: Unknown result type (might be due to invalid IL or missing references)
			EventSystem val = EventSystem.current;
			if ((Object)(object)val == (Object)null)
			{
				val = new GameObject("ControllerSupport_EventSystem").AddComponent<EventSystem>();
			}
			val.sendNavigationEvents = false;
			if ((Object)(object)((Component)val).GetComponent<InputSystemUIInputModule>() != (Object)null)
			{
				return;
			}
			try
			{
				((Component)val).gameObject.AddComponent<InputSystemUIInputModule>();
			}
			catch (Exception arg)
			{
				Logger.LogError((object)$"[ControllerSupport] InputSystemUIInputModule failed: {arg}");
				if ((Object)(object)((Component)val).GetComponent<StandaloneInputModule>() == (Object)null)
				{
					((Component)val).gameObject.AddComponent<StandaloneInputModule>();
					Logger.LogWarning((object)"[ControllerSupport] Fell back to StandaloneInputModule");
				}
			}
		}

		internal static void RebuildTaskElementCache(bool forPapyrus = true)
		{
			//IL_01a1: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a6: Unknown result type (might be due to invalid IL or missing references)
			//IL_017b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0180: 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_0349: Unknown result type (might be due to invalid IL or missing references)
			//IL_03a6: Unknown result type (might be due to invalid IL or missing references)
			//IL_03ab: Unknown result type (might be due to invalid IL or missing references)
			_cachedTaskElements.Clear();
			if (_buttonGraphicField == null)
			{
				_buttonGraphicField = AccessTools.Field(typeof(PlayerTaskElement), "buttonGraphic");
			}
			if (_taskTextField == null)
			{
				_taskTextField = AccessTools.Field(typeof(PlayerTaskElement), "taskText");
			}
			PlayerTaskElement[] array = Object.FindObjectsOfType<PlayerTaskElement>();
			List<PlayerTaskElement> list = new List<PlayerTaskElement>();
			List<PlayerTaskElement> list2 = new List<PlayerTaskElement>();
			PlayerTaskElement[] array2 = array;
			foreach (PlayerTaskElement val in array2)
			{
				bool flag = false;
				Transform val2 = ((Component)val).transform;
				while ((Object)(object)val2 != (Object)null)
				{
					if (((Object)val2).name == "papyrus" || ((Object)val2).name == "Papyrus")
					{
						flag = true;
						break;
					}
					val2 = val2.parent;
				}
				if (flag)
				{
					list.Add(val);
				}
				else
				{
					list2.Add(val);
				}
			}
			List<PlayerTaskElement> list3 = ((!forPapyrus) ? list2 : ((list.Count > 0) ? list : new List<PlayerTaskElement>(array)));
			list3.Sort(delegate(PlayerTaskElement a, PlayerTaskElement b)
			{
				//IL_0042: Unknown result type (might be due to invalid IL or missing references)
				//IL_0053: Unknown result type (might be due to invalid IL or missing references)
				if ((Object)(object)((Component)a).transform.parent == (Object)(object)((Component)b).transform.parent)
				{
					return ((Component)a).transform.GetSiblingIndex().CompareTo(((Component)b).transform.GetSiblingIndex());
				}
				float y = ((Component)a).GetComponent<RectTransform>().anchoredPosition.y;
				float y2 = ((Component)b).GetComponent<RectTransform>().anchoredPosition.y;
				return y2.CompareTo(y);
			});
			if (list3.Count > 0)
			{
				for (int num = 0; num < list3.Count; num++)
				{
					PlayerTaskElement val3 = list3[num];
					GameObject gameObject = ((Component)val3).gameObject;
					if (_taskTextField != null && num == 0)
					{
						object? value = _taskTextField.GetValue(val3);
						TMP_Text val4 = (TMP_Text)((value is TMP_Text) ? value : null);
						if ((Object)(object)val4 != (Object)null)
						{
							_origTaskTextColor = ((Graphic)val4).color;
						}
					}
					Image component = ((Component)val3).GetComponent<Image>();
					if (!_origElementGraphicColorCaptured && (Object)(object)component != (Object)null)
					{
						_origElementGraphicColor = ((Graphic)component).color;
						_origElementGraphicColorCaptured = true;
					}
					Image item = null;
					if (_buttonGraphicField != null)
					{
						object? value2 = _buttonGraphicField.GetValue(val3);
						item = (Image)((value2 is Image) ? value2 : null);
					}
					GameObject item2 = CreateHighlightOverlay(gameObject);
					Component component2 = gameObject.GetComponent("MMUiEventListener");
					_cachedTaskElements.Add((val3, component, item, item2, component2));
					if (_mmEnterFeedbackField == null && (Object)(object)component2 != (Object)null)
					{
						Type type = ((object)component2).GetType();
						_mmEnterFeedbackField = type.GetField("onPointerEnterFeedback", BindingFlags.Instance | BindingFlags.NonPublic);
						_mmExitFeedbackField = type.GetField("onPointerExitFeedback", BindingFlags.Instance | BindingFlags.NonPublic);
						Type type2 = _mmEnterFeedbackField?.FieldType;
						if (type2 != null)
						{
							_mmPlayFeedbacksMethod = type2.GetMethod("PlayFeedbacks", Type.EmptyTypes);
						}
					}
					if (!_highlightDiagLogged)
					{
						_highlightDiagLogged = true;
					}
				}
			}
			else
			{
				if ((Object)(object)_cachedTaskListUI == (Object)null)
				{
					return;
				}
				if (_taskElementParentField == null)
				{
					_taskElementParentField = AccessTools.Field(typeof(TaskListUI), "taskElementParent");
				}
				if (_taskElementParentField == null)
				{
					return;
				}
				object? value3 = _taskElementParentField.GetValue(_cachedTaskListUI);
				Transform val5 = (Transform)((value3 is Transform) ? value3 : null);
				if ((Object)(object)val5 == (Object)null)
				{
					return;
				}
				if (_taskTextField != null)
				{
					for (int num2 = 0; num2 < val5.childCount; num2++)
					{
						PlayerTaskElement component3 = ((Component)val5.GetChild(num2)).GetComponent<PlayerTaskElement>();
						if ((Object)(object)component3 != (Object)null)
						{
							object? value4 = _taskTextField.GetValue(component3);
							TMP_Text val6 = (TMP_Text)((value4 is TMP_Text) ? value4 : null);
							if ((Object)(object)val6 != (Object)null)
							{
								_origTaskTextColor = ((Graphic)val6).color;
								break;
							}
						}
					}
				}
				for (int num3 = 0; num3 < val5.childCount; num3++)
				{
					Transform child = val5.GetChild(num3);
					PlayerTaskElement component4 = ((Component)child).GetComponent<PlayerTaskElement>();
					if ((Object)(object)component4 == (Object)null)
					{
						continue;
					}
					Image component5 = ((Component)component4).GetComponent<Image>();
					if (!_origElementGraphicColorCaptured && (Object)(object)component5 != (Object)null)
					{
						_origElementGraphicColor = ((Graphic)component5).color;
						_origElementGraphicColorCaptured = true;
					}
					Image item3 = null;
					if (_buttonGraphicField != null)
					{
						object? value5 = _buttonGraphicField.GetValue(component4);
						item3 = (Image)((value5 is Image) ? value5 : null);
					}
					GameObject item4 = CreateHighlightOverlay(((Component)child).gameObject);
					Component component6 = ((Component)child).GetComponent("MMUiEventListener");
					_cachedTaskElements.Add((component4, component5, item3, item4, component6));
					if (_mmEnterFeedbackField == null && (Object)(object)component6 != (Object)null)
					{
						Type type3 = ((object)component6).GetType();
						_mmEnterFeedbackField = type3.GetField("onPointerEnterFeedback", BindingFlags.Instance | BindingFlags.NonPublic);
						_mmExitFeedbackField = type3.GetField("onPointerExitFeedback", BindingFlags.Instance | BindingFlags.NonPublic);
						Type type4 = _mmEnterFeedbackField?.FieldType;
						if (type4 != null)
						{
							_mmPlayFeedbacksMethod = type4.GetMethod("PlayFeedbacks", Type.EmptyTypes);
						}
					}
				}
			}
		}

		internal static void ClearTaskElementHighlights()
		{
			//IL_0031: Unknown result type (might be due to invalid IL or missing references)
			//IL_0085: Unknown result type (might be due to invalid IL or missing references)
			if (!_lastInputWasGamepad)
			{
				return;
			}
			foreach (var cachedTaskElement in _cachedTaskElements)
			{
				if ((Object)(object)cachedTaskElement.buttonGraphic != (Object)null)
				{
					((Graphic)cachedTaskElement.buttonGraphic).color = _origHighlightColor;
				}
				PlayMMFeedback(cachedTaskElement.mmUiEventListener, isEnter: false);
				if ((Object)(object)cachedTaskElement.highlightChild != (Object)null)
				{
					cachedTaskElement.highlightChild.SetActive(false);
				}
				if ((Object)(object)cachedTaskElement.element != (Object)null)
				{
					RectTransform component = ((Component)cachedTaskElement.element).GetComponent<RectTransform>();
					if ((Object)(object)component != (Object)null)
					{
						((Transform)component).localScale = Vector3.one;
					}
				}
			}
		}

		private static void PlayMMFeedback(Component mmUiEventListener, bool isEnter)
		{
			if ((Object)(object)mmUiEventListener == (Object)null || _mmEnterFeedbackField == null || _mmPlayFeedbacksMethod == null)
			{
				return;
			}
			try
			{
				FieldInfo fieldInfo = (isEnter ? _mmEnterFeedbackField : _mmExitFeedbackField);
				if (fieldInfo == null)
				{
					return;
				}
				object? value = fieldInfo.GetValue(mmUiEventListener);
				Component val = (Component)((value is Component) ? value : null);
				if ((Object)(object)val == (Object)null)
				{
					if (!_feedbackDiagLogged)
					{
						_feedbackDiagLogged = true;
						Logger.LogWarning((object)("[ControllerSupport] PlayMMFeedback(" + (isEnter ? "enter" : "exit") + "): feedback is null!"));
					}
				}
				else
				{
					if (!val.gameObject.activeInHierarchy)
					{
						val.gameObject.SetActive(true);
					}
					_mmPlayFeedbacksMethod.Invoke(val, null);
				}
			}
			catch (Exception ex)
			{
				if (!_feedbackDiagLogged)
				{
					_feedbackDiagLogged = true;
					Logger.LogWarning((object)("[ControllerSupport] PlayMMFeedback(" + (isEnter ? "enter" : "exit") + ") exception: " + ex.Message));
				}
			}
		}

		internal static void HighlightTaskElement(int index)
		{
			//IL_008f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0102: Unknown result type (might be due to invalid IL or missing references)
			//IL_0108: Expected O, but got Unknown
			if (!_lastInputWasGamepad)
			{
				return;
			}
			ClearTaskElementHighlights();
			if (index < 0 || index >= _cachedTaskElements.Count)
			{
				return;
			}
			(PlayerTaskElement, Image, Image, GameObject, Component) tuple = _cachedTaskElements[index];
			EnsureHighlightResources();
			_highlightCallCount++;
			_ = _highlightCallCount;
			_ = 3;
			if ((Object)(object)tuple.Item3 != (Object)null)
			{
				if (!((Component)tuple.Item3).gameObject.activeSelf)
				{
					((Component)tuple.Item3).gameObject.SetActive(true);
				}
				((Graphic)tuple.Item3).color = new Color(1f, 1f, 1f, 1f);
			}
			if ((Object)(object)tuple.Item1 != (Object)null)
			{
				RectTransform component = ((Component)tuple.Item1).GetComponent<RectTransform>();
				if ((Object)(object)component != (Object)null)
				{
					((Transform)component).localScale = new Vector3(1.08f, 1.08f, 1.08f);
				}
			}
			PlayMMFeedback(tuple.Item5, isEnter: true);
			if (!((Object)(object)tuple.Item1 != (Object)null) || !((Object)(object)EventSystem.current != (Object)null))
			{
				return;
			}
			try
			{
				PointerEventData val = new PointerEventData(EventSystem.current);
				val.pointerEnter = ((Component)tuple.Item1).gameObject;
				ExecuteEvents.Execute<IPointerEnterHandler>(((Component)tuple.Item1).gameObject, (BaseEventData)(object)val, ExecuteEvents.pointerEnterHandler);
			}
			catch (Exception ex)
			{
				if (_highlightCallCount <= 3)
				{
					Logger.LogWarning((object)("[ControllerSupport] ExecuteEvents.pointerEnterHandler exception: " + ex.Message));
				}
			}
		}

		private static GameObject CreateHighlightOverlay(GameObject taskElement)
		{
			//IL_000a: Unknown result type (might be due to invalid IL or missing references)
			//IL_000f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0021: Unknown result type (might be due to invalid IL or missing references)
			//IL_0028: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: 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)
			//IL_0049: Unknown result type (might be due to invalid IL or missing references)
			//IL_0058: Unknown result type (might be due to invalid IL or missing references)
			//IL_007e: Unknown result type (might be due to invalid IL or missing references)
			//IL_008e: 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_00a2: Expected O, but got Unknown
			EnsureHighlightResources();
			GameObject val = new GameObject("ControllerHighlightOverlay");
			val.transform.SetParent(taskElement.transform, false);
			RectTransform obj = val.AddComponent<RectTransform>();
			obj.anchorMin = Vector2.zero;
			obj.anchorMax = Vector2.one;
			obj.offsetMin = Vector2.zero;
			obj.offsetMax = Vector2.zero;
			((Transform)obj).SetAsLastSibling();
			Image obj2 = val.AddComponent<Image>();
			obj2.sprite = _highlightSprite;
			((Graphic)obj2).color = new Color(0f, 1f, 0.3f, 0.4f);
			((Graphic)obj2).raycastTarget = false;
			val.AddComponent<LayoutElement>().ignoreLayout = true;
			val.SetActive(false);
			return val;
		}

		internal static void ClearAllTaskAndFoldoutState()
		{
			ClearTaskElementHighlights();
			_taskListSelectedIndex = -1;
			_taskListOpen = false;
			_infoOverlayOpen = false;
			UpdateLookActionState();
			_mouseOpenedInfoOverlay = false;
			_infoFoldoutIndex = -1;
			_cachedTaskElements.Clear();
			_cachedTaskListUI = null;
			_cachedFoldouts.Clear();
			_cachedDescriptionDisplayer = null;
			_lateUpdaterActiveDiagLogged = false;
			_inactiveElementsLogged = false;
			_highlightCallCount = 0;
			_prevTaskPanelActive = false;
			if (_cursorPreviouslyVisible.HasValue)
			{
				Cursor.visible = _cursorPreviouslyVisible.Value;
				Cursor.lockState = (CursorLockMode)0;
				_cursorPreviouslyVisible = null;
			}
			if ((Object)(object)_disabledRaycaster != (Object)null)
			{
				((Behaviour)_disabledRaycaster).enabled = true;
				_disabledRaycaster = null;
			}
			_papyrusCacheRetryCount = 0;
			_deadTiedCacheRetryCount = 0;
			_currentListType = ListType.None;
		}

		private static void RebuildFoldoutCache(bool preserveSelection = false)
		{
			int infoFoldoutIndex = _infoFoldoutIndex;
			_cachedFoldouts.Clear();
			_infoFoldoutIndex = -1;
			if (_descToggleField == null)
			{
				_descToggleField = AccessTools.Field(typeof(DescriptionElement), "toggle");
			}
			if ((Object)(object)_cachedDescriptionDisplayer == (Object)null)
			{
				_cachedDescriptionDisplayer = Object.FindObjectOfType<DescriptionDisplayer>();
				if ((Object)(object)_cachedDescriptionDisplayer == (Object)null)
				{
					return;
				}
				if (_descriptionContainerField == null)
				{
					_descriptionContainerField = AccessTools.Field(typeof(DescriptionDisplayer), "descriptionContainer");
				}
			}
			if (_descriptionContainerField == null)
			{
				return;
			}
			object? value = _descriptionContainerField.GetValue(_cachedDescriptionDisplayer);
			GameObject val = (GameObject)((value is GameObject) ? value : null);
			if ((Object)(object)val == (Object)null)
			{
				return;
			}
			if ((Object)(object)_foldoutScrollRect == (Object)null)
			{
				_foldoutScrollRect = val.GetComponentInParent<ScrollRect>();
			}
			DescriptionElement[] componentsInChildren = val.GetComponentsInChildren<DescriptionElement>(false);
			int num = 0;
			int num2 = 0;
			DescriptionElement[] array = componentsInChildren;
			foreach (DescriptionElement val2 in array)
			{
				Toggle val3 = null;
				if (_descToggleField != null)
				{
					object? value2 = _descToggleField.GetValue(val2);
					val3 = (Toggle)((value2 is Toggle) ? value2 : null);
				}
				if ((Object)(object)val3 == (Object)null)
				{
					num++;
					continue;
				}
				int num3 = 0;
				Transform parent = ((Component)val2).transform.parent;
				while ((Object)(object)parent != (Object)null && (Object)(object)parent != (Object)(object)val.transform)
				{
					if ((Object)(object)((Component)parent).GetComponent<DescriptionElement>() != (Object)null)
					{
						num3++;
					}
					parent = parent.parent;
				}
				if (!((Behaviour)val3).enabled)
				{
					num2++;
					continue;
				}
				_cachedFoldouts.Add((val2, val3));
				if (_foldoutTitleField == null)
				{
					_foldoutTitleField = AccessTools.Field(typeof(DescriptionElement), "title");
				}
				if (_foldoutTitleField != null)
				{
					object? value3 = _foldoutTitleField.GetValue(val2);
					TMP_Text val4 = (TMP_Text)((value3 is TMP_Text) ? value3 : null);
					if ((Object)(object)val4 != (Object)null)
					{
						_ = val4.text;
					}
				}
				if (_foldoutObjectField == null)
				{
					_foldoutObjectField = AccessTools.Field(typeof(DescriptionElement), "toggleObject");
				}
				if (_foldoutObjectField != null)
				{
					object? value4 = _foldoutObjectField.GetValue(val2);
					GameObject val5 = (GameObject)((value4 is GameObject) ? value4 : null);
					if ((Object)(object)val5 != (Object)null)
					{
						_ = val5.activeSelf;
					}
				}
				if (num3 != 0)
				{
					_ = $"nested(d{num3})";
				}
			}
			if (_cachedFoldouts.Count != _lastFoldoutCacheCount || Time.unscaledTime - _lastFoldoutCacheLogTime >= 1f)
			{
				_lastFoldoutCacheCount = _cachedFoldouts.Count;
				_lastFoldoutCacheLogTime = Time.unscaledTime;
			}
			if (_cachedFoldouts.Count > 0)
			{
				if (preserveSelection && infoFoldoutIndex >= 0 && infoFoldoutIndex < _cachedFoldouts.Count)
				{
					_infoFoldoutIndex = infoFoldoutIndex;
				}
				else
				{
					_infoFoldoutIndex = 0;
				}
			}
		}

		private static void SelectFoldout(int index)
		{
			//IL_00b5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ba: 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_00c7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cc: Unknown result type (might be due to invalid IL or missing references)
			ClearFoldoutHighlights();
			if (index < 0 || index >= _cachedFoldouts.Count)
			{
				return;
			}
			Toggle item = _cachedFoldouts[index].toggle;
			DescriptionElement item2 = _cachedFoldouts[index].element;
			if ((Object)(object)item != (Object)null && (Object)(object)EventSystem.current != (Object)null)
			{
				EventSystem.current.SetSelectedGameObject(((Component)item).gameObject);
			}
			if (_foldoutTitleField == null)
			{
				_foldoutTitleField = AccessTools.Field(typeof(DescriptionElement), "title");
			}
			if (!(_foldoutTitleField != null) || !((Object)(object)item2 != (Object)null))
			{
				return;
			}
			object? value = _foldoutTitleField.GetValue(item2);
			TMP_Text val = (TMP_Text)((value is TMP_Text) ? value : null);
			if ((Object)(object)val != (Object)null)
			{
				if (_origFoldoutTitleColor == Color.white)
				{
					_origFoldoutTitleColor = ((Graphic)val).color;
				}
				((Graphic)val).color = _selectedHighlightColor;
			}
		}

		private static void ScrollToFoldout(int index)
		{
			//IL_008c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_0096: 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_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_00b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e4: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e9: 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_00f8: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)_foldoutScrollRect == (Object)null || index < 0 || index >= _cachedFoldouts.Count)
			{
				return;
			}
			Toggle item = _cachedFoldouts[index].toggle;
			if ((Object)(object)item == (Object)null || (Object)(object)_foldoutScrollRect.viewport == (Object)null || (Object)(object)_foldoutScrollRect.content == (Object)null)
			{
				return;
			}
			Canvas.ForceUpdateCanvases();
			RectTransform component = ((Component)item).GetComponent<RectTransform>();
			RectTransform viewport = _foldoutScrollRect.viewport;
			RectTransform content = _foldoutScrollRect.content;
			if (!((Object)(object)component == (Object)null))
			{
				Vector2 val = Vector2.op_Implicit(((Transform)viewport).InverseTransformPoint(((Transform)component).position));
				Rect rect = viewport.rect;
				float num = ((Rect)(ref rect)).height / 2f;
				rect = component.rect;
				float num2 = ((Rect)(ref rect)).height / 2f;
				float num3 = val.y + num2;
				float num4 = val.y - num2;
				rect = content.rect;
				float height = ((Rect)(ref rect)).height;
				rect = viewport.rect;
				float num5 = Mathf.Max(1f, height - ((Rect)(ref rect)).height);
				if (num3 > num)
				{
					float num6 = num3 - num;
					_foldoutScrollRect.verticalNormalizedPosition = Mathf.Clamp01(_foldoutScrollRect.verticalNormalizedPosition + num6 / num5);
				}
				else if (num4 < 0f - num)
				{
					float num7 = 0f - num - num4;
					_foldoutScrollRect.verticalNormalizedPosition = Mathf.Clamp01(_foldoutScrollRect.verticalNormalizedPosition - num7 / num5);
				}
			}
		}

		internal static void ClearFoldoutHighlights()
		{
			//IL_0042: Unknown result type (might be due to invalid IL or missing references)
			foreach (var cachedFoldout in _cachedFoldouts)
			{
				if (_foldoutTitleField != null)
				{
					object? value = _foldoutTitleField.GetValue(cachedFoldout.element);
					TMP_Text val = (TMP_Text)((value is TMP_Text) ? value : null);
					if ((Object)(object)val != (Object)null)
					{
						((Graphic)val).color = _origFoldoutTitleColor;
					}
				}
			}
		}

		internal static void CloseOverlayAndPapyrus()
		{
			_infoOverlayOpen = false;
			_overlayClosedByRelease = true;
			_mouseOpenedInfoOverlay = false;
			_papyrusAPressFrame = -1;
			Equipmen