Decompiled source of AutoItemPickup v1.0.0

BepInEx/plugins/AutoItemPickup.dll

Decompiled 15 hours ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Configuration;
using Unity.Netcode;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: AssemblyTitle("AutoItemPickup")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("AutoItemPickup")]
[assembly: AssemblyCopyright("Copyright ©  2025")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("1a3ecdef-4b0b-4299-b170-f5f68f0f4b69")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyVersion("1.0.0.0")]
[BepInPlugin("AutoItemPickup", "Auto Item Pickup", "1.0.0")]
public class AutoItemPickup : BaseUnityPlugin
{
	private static class ListPool<T>
	{
		private static readonly Stack<List<T>> Pool = new Stack<List<T>>();

		public static List<T> Get()
		{
			lock (Pool)
			{
				return (Pool.Count > 0) ? Pool.Pop() : new List<T>();
			}
		}

		public static void Release(List<T> list)
		{
			if (list == null)
			{
				return;
			}
			list.Clear();
			lock (Pool)
			{
				Pool.Push(list);
			}
		}
	}

	public const string PluginGuid = "AutoItemPickup";

	public const string PluginName = "Auto Item Pickup";

	public const string PluginVersion = "1.0.0";

	private const float ScanIntervalSec = 0.15f;

	private const float PickupRadius = 2.2f;

	private readonly Collider[] _hits = (Collider[])(object)new Collider[64];

	private float _nextScan;

	private bool _enabled = true;

	private ConfigEntry<KeyboardShortcut> _toggleKey;

	private readonly Dictionary<int, float> _cooldownByInstanceId = new Dictionary<int, float>(256);

	private const float PerItemCooldownSec = 0.35f;

	private MethodInfo _isFullMethodCache;

	private void Awake()
	{
		//IL_0018: Unknown result type (might be due to invalid IL or missing references)
		_toggleKey = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("General", "ToggleKey", new KeyboardShortcut((KeyCode)112, Array.Empty<KeyCode>()), "Toggle auto pickup on/off.");
	}

	private void Update()
	{
		//IL_0006: Unknown result type (might be due to invalid IL or missing references)
		//IL_000b: Unknown result type (might be due to invalid IL or missing references)
		KeyboardShortcut value = _toggleKey.Value;
		if (((KeyboardShortcut)(ref value)).IsDown())
		{
			_enabled = !_enabled;
			NotifyToggle(_enabled);
		}
		if (_enabled && !(Time.unscaledTime < _nextScan))
		{
			_nextScan = Time.unscaledTime + 0.15f;
			if (IsPlayableLocal() && HasInventorySpaceBestEffort())
			{
				TryPickupNearby();
				CleanupCooldownBestEffort();
			}
		}
	}

	private static bool IsPlayableLocal()
	{
		if ((Object)(object)NetworkManager.Singleton == (Object)null || !NetworkManager.Singleton.IsListening)
		{
			return false;
		}
		if ((Object)(object)PlayerManager.Instance == (Object)null || !PlayerManager.Instance.isLocalPlayerSpawned)
		{
			return false;
		}
		if ((Object)(object)PlayerNet.Instance == (Object)null)
		{
			return false;
		}
		return true;
	}

	private bool HasInventorySpaceBestEffort()
	{
		try
		{
			if ((Object)(object)ContainerManager.Instance == (Object)null)
			{
				return true;
			}
			ulong localClientId = NetworkManager.Singleton.LocalClientId;
			ContainerNet val = default(ContainerNet);
			if (!ContainerManager.Instance.GetPlayerContainer(localClientId, ref val) || (Object)(object)val == (Object)null)
			{
				return true;
			}
			if (_isFullMethodCache == null)
			{
				_isFullMethodCache = ((object)val).GetType().GetMethod("IsFull", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
			}
			if (_isFullMethodCache != null && _isFullMethodCache.ReturnType == typeof(bool) && _isFullMethodCache.GetParameters().Length == 0)
			{
				return !(bool)_isFullMethodCache.Invoke(val, null);
			}
			return true;
		}
		catch
		{
			return true;
		}
	}

	private void TryPickupNearby()
	{
		//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_0010: Unknown result type (might be due to invalid IL or missing references)
		//IL_013c: Unknown result type (might be due to invalid IL or missing references)
		//IL_0141: Unknown result type (might be due to invalid IL or missing references)
		//IL_0142: 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_00a6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
		//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
		//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
		Vector3 position = ((Component)PlayerNet.Instance).transform.position;
		int num = Physics.OverlapSphereNonAlloc(position, 2.2f, _hits, -1, (QueryTriggerInteraction)2);
		Vector3 val3;
		if (num > 0)
		{
			CollectibleNet val = null;
			float num2 = float.MaxValue;
			for (int i = 0; i < num; i++)
			{
				Collider val2 = _hits[i];
				if ((Object)(object)val2 == (Object)null)
				{
					continue;
				}
				CollectibleNet componentInParent = ((Component)val2).GetComponentInParent<CollectibleNet>();
				if ((Object)(object)componentInParent == (Object)null || !((NetworkBehaviour)componentInParent).IsSpawned || IsLivestock(componentInParent))
				{
					continue;
				}
				int instanceID = ((Object)((Component)componentInParent).gameObject).GetInstanceID();
				if (!_cooldownByInstanceId.TryGetValue(instanceID, out var value) || !(Time.unscaledTime < value))
				{
					val3 = ((Component)componentInParent).transform.position - position;
					float sqrMagnitude = ((Vector3)(ref val3)).sqrMagnitude;
					if (sqrMagnitude < num2)
					{
						num2 = sqrMagnitude;
						val = componentInParent;
					}
				}
			}
			if ((Object)(object)val != (Object)null)
			{
				InvokePickup(val);
				return;
			}
		}
		CollectibleNet[] array = Object.FindObjectsByType<CollectibleNet>((FindObjectsInactive)0, (FindObjectsSortMode)0);
		if (array == null || array.Length == 0)
		{
			return;
		}
		CollectibleNet val4 = null;
		float num3 = float.MaxValue;
		float num4 = 4.84f;
		foreach (CollectibleNet val5 in array)
		{
			if ((Object)(object)val5 == (Object)null || !((NetworkBehaviour)val5).IsSpawned || IsLivestock(val5))
			{
				continue;
			}
			val3 = ((Component)val5).transform.position - position;
			float sqrMagnitude2 = ((Vector3)(ref val3)).sqrMagnitude;
			if (!(sqrMagnitude2 > num4))
			{
				int instanceID2 = ((Object)((Component)val5).gameObject).GetInstanceID();
				if ((!_cooldownByInstanceId.TryGetValue(instanceID2, out var value2) || !(Time.unscaledTime < value2)) && sqrMagnitude2 < num3)
				{
					num3 = sqrMagnitude2;
					val4 = val5;
				}
			}
		}
		if ((Object)(object)val4 != (Object)null)
		{
			InvokePickup(val4);
		}
	}

	private static bool IsLivestock(CollectibleNet cn)
	{
		if ((Object)(object)cn != (Object)null)
		{
			return (Object)(object)((Component)cn).GetComponentInParent<PaddockAnimal>() != (Object)null;
		}
		return false;
	}

	private void InvokePickup(CollectibleNet cn)
	{
		//IL_0003: Unknown result type (might be due to invalid IL or missing references)
		//IL_0009: Unknown result type (might be due to invalid IL or missing references)
		try
		{
			cn.PickupServerRpc(default(ServerRpcParams));
			int instanceID = ((Object)((Component)cn).gameObject).GetInstanceID();
			_cooldownByInstanceId[instanceID] = Time.unscaledTime + 0.35f;
		}
		catch
		{
		}
	}

	private static void NotifyToggle(bool enabled)
	{
		try
		{
			Game instance = Game.Instance;
			if (!((Object)(object)instance == (Object)null))
			{
				instance.onGameEventText?.Invoke(enabled ? "AutoItemPickup:ON" : "AutoItemPickup:OFF");
			}
		}
		catch
		{
		}
	}

	private void CleanupCooldownBestEffort()
	{
		if (_cooldownByInstanceId.Count < 256)
		{
			return;
		}
		float unscaledTime = Time.unscaledTime;
		List<int> list = ListPool<int>.Get();
		try
		{
			foreach (KeyValuePair<int, float> item in _cooldownByInstanceId)
			{
				if (item.Value + 3f < unscaledTime)
				{
					list.Add(item.Key);
				}
			}
			for (int i = 0; i < list.Count; i++)
			{
				_cooldownByInstanceId.Remove(list[i]);
			}
		}
		finally
		{
			ListPool<int>.Release(list);
		}
	}
}