Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of MobScanner v1.0.1
BepInEx/Plugins/MobScanner.dll
Decompiled 7 minutes agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Microsoft.CodeAnalysis; using UnityEngine; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: IgnoresAccessChecksTo("")] [assembly: AssemblyCompany("Liore")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("MobScanner")] [assembly: AssemblyTitle("MobScanner")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)] internal sealed class NullableContextAttribute : Attribute { public readonly byte Flag; public NullableContextAttribute(byte P_0) { Flag = P_0; } } [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 MobScanner { [BepInPlugin("Liore.MobScanner", "MobScanner", "1.0")] public class MobScanner : BaseUnityPlugin { internal static ConfigEntry<bool> DebugLogging; internal static MobScanner Instance { get; private set; } internal static ManualLogSource Logger => Instance._logger; private ManualLogSource _logger => ((BaseUnityPlugin)this).Logger; internal Harmony? Harmony { get; set; } internal static void LogDebug(string message) { if (DebugLogging != null && DebugLogging.Value) { Logger.LogInfo((object)message); } } private void Awake() { Instance = this; ((Component)this).gameObject.transform.parent = null; ((Object)((Component)this).gameObject).hideFlags = (HideFlags)61; DebugLogging = ((BaseUnityPlugin)this).Config.Bind<bool>("Debug", "DebugLogging", false, "Write detailed scan, marker, preview and shop diagnostics to the log."); Scanner.ScanKey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("Controls", "ScanKey", (KeyCode)122, "Hold this key to scan."); Scanner.HoldTime = ((BaseUnityPlugin)this).Config.Bind<float>("Scanning", "HoldTime", 3f, "How many seconds you must hold the key without moving."); Scanner.ScanRadius = ((BaseUnityPlugin)this).Config.Bind<float>("Scanning", "ScanRadius", 20f, "How far the scan reaches, in meters. Lower = shorter range."); Scanner.ResultDuration = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "ResultDuration", 15f, "How many seconds the scan results stay on screen."); Scanner.MarkerScale = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "MarkerScale", 1f, "Size of the dot drawn on the map. Raise this if you cannot see it."); Scanner.MarkerHeight = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "MarkerHeight", 0.35f, "How far above the map surface the dot floats. Raise if dots are hidden by unexplored areas."); Scanner.ShowModel = ((BaseUnityPlugin)this).Config.Bind<bool>("Display", "ShowModel", true, "Show a spinning 3D model of the monster that was found."); Scanner.SpinSpeed = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "SpinSpeed", 55f, "How fast the 3D model spins, in degrees per second."); Scanner.ModelCycleTime = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "ModelCycleTime", 2f, "Seconds each monster is shown before switching to the next one."); Scanner.UpgradePrice = ((BaseUnityPlugin)this).Config.Bind<float>("Shop", "UpgradePrice", 5f, "Android vision price. The shop displays thousands, so 5 shows as $5K."); Scanner.UsesPerLevel = ((BaseUnityPlugin)this).Config.Bind<int>("Shop", "UsesPerLevel", 2, "How many successful scans you get per level. Set to 0 for unlimited."); Scanner.RequireUpgrade = ((BaseUnityPlugin)this).Config.Bind<bool>("Shop", "RequireUpgrade", true, "If false, scanning works without buying the upgrade (useful for testing)."); Scanner.AlwaysInShop = ((BaseUnityPlugin)this).Config.Bind<bool>("Shop", "AlwaysInShop", true, "Always offer Android vision in the shop, even if you cannot afford it yet."); Scanner.EyeEffect = ((BaseUnityPlugin)this).Config.Bind<bool>("Display", "EyeEffect", true, "Make your eyes glow while scanning. Other players can see this too."); Scanner.EyeFlashSpeed = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "EyeFlashSpeed", 4f, "How many times per second the eyes switch between orange and red."); Scanner.EyeResultTime = ((BaseUnityPlugin)this).Config.Bind<float>("Display", "EyeResultTime", 3f, "Seconds your eyes stay pink (found) or green (clear) after a scan."); Scanner.FontName = ((BaseUnityPlugin)this).Config.Bind<string>("Display", "FontName", "", "Font to use for the scanner text. Leave empty to auto-pick. The log lists every available font name on the first scan."); Scanner.Cooldown = ((BaseUnityPlugin)this).Config.Bind<float>("Scanning", "Cooldown", 3f, "Seconds you must wait after a scan before you can scan again."); ((Component)this).gameObject.AddComponent<Scanner>(); Patch(); Logger.LogInfo((object)$"{((BaseUnityPlugin)this).Info.Metadata.GUID} v{((BaseUnityPlugin)this).Info.Metadata.Version} has loaded!"); } internal void Patch() { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_0026: Expected O, but got Unknown if (Harmony == null) { Harmony val = new Harmony(((BaseUnityPlugin)this).Info.Metadata.GUID); Harmony val2 = val; Harmony = val; } Harmony.PatchAll(); } internal void Unpatch() { Harmony? harmony = Harmony; if (harmony != null) { harmony.UnpatchSelf(); } } } public class ModelPreview { private GameObject? _root; private Camera? _camera; private RenderTexture? _texture; private const int PreviewLayer = 31; private static readonly Vector3 StageOrigin = new Vector3(0f, -5000f, 0f); public bool IsValid => (Object)(object)_root != (Object)null && (Object)(object)_texture != (Object)null; public RenderTexture? Texture => _texture; public bool Build(EnemyParent enemyParent, int size) { //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Expected O, but got Unknown //IL_0077: Unknown result type (might be due to invalid IL or missing references) //IL_0087: Unknown result type (might be due to invalid IL or missing references) //IL_008e: Expected O, but got Unknown //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00f5: Unknown result type (might be due to invalid IL or missing references) //IL_0107: Unknown result type (might be due to invalid IL or missing references) //IL_0166: Unknown result type (might be due to invalid IL or missing references) //IL_016b: Unknown result type (might be due to invalid IL or missing references) //IL_0177: Unknown result type (might be due to invalid IL or missing references) //IL_0186: Unknown result type (might be due to invalid IL or missing references) //IL_0195: Unknown result type (might be due to invalid IL or missing references) //IL_01d1: Unknown result type (might be due to invalid IL or missing references) //IL_01d8: Unknown result type (might be due to invalid IL or missing references) //IL_01ef: Unknown result type (might be due to invalid IL or missing references) //IL_01f4: Unknown result type (might be due to invalid IL or missing references) //IL_022c: Unknown result type (might be due to invalid IL or missing references) //IL_0231: Unknown result type (might be due to invalid IL or missing references) //IL_0235: Unknown result type (might be due to invalid IL or missing references) //IL_023a: Unknown result type (might be due to invalid IL or missing references) //IL_023c: Unknown result type (might be due to invalid IL or missing references) //IL_0243: Unknown result type (might be due to invalid IL or missing references) //IL_024a: Unknown result type (might be due to invalid IL or missing references) //IL_025f: Unknown result type (might be due to invalid IL or missing references) //IL_0264: Unknown result type (might be due to invalid IL or missing references) //IL_0268: Unknown result type (might be due to invalid IL or missing references) //IL_026f: Unknown result type (might be due to invalid IL or missing references) //IL_032b: Unknown result type (might be due to invalid IL or missing references) //IL_0330: Unknown result type (might be due to invalid IL or missing references) //IL_0334: Unknown result type (might be due to invalid IL or missing references) //IL_0340: Unknown result type (might be due to invalid IL or missing references) //IL_0345: Unknown result type (might be due to invalid IL or missing references) //IL_034a: Unknown result type (might be due to invalid IL or missing references) //IL_0353: Unknown result type (might be due to invalid IL or missing references) //IL_0355: Unknown result type (might be due to invalid IL or missing references) //IL_03c0: Unknown result type (might be due to invalid IL or missing references) //IL_03e7: Unknown result type (might be due to invalid IL or missing references) //IL_03ee: Expected O, but got Unknown //IL_041d: Unknown result type (might be due to invalid IL or missing references) //IL_0470: Unknown result type (might be due to invalid IL or missing references) //IL_0477: Expected O, but got Unknown //IL_04a6: Unknown result type (might be due to invalid IL or missing references) //IL_04f9: Unknown result type (might be due to invalid IL or missing references) //IL_0503: Expected O, but got Unknown //IL_0514: Unknown result type (might be due to invalid IL or missing references) //IL_051b: Expected O, but got Unknown //IL_054a: Unknown result type (might be due to invalid IL or missing references) //IL_05a4: Unknown result type (might be due to invalid IL or missing references) //IL_0602: Unknown result type (might be due to invalid IL or missing references) Dispose(); if ((Object)(object)enemyParent == (Object)null || (Object)(object)enemyParent.Enemy == (Object)null) { return false; } GameObject val = (((Object)(object)enemyParent.EnableObject != (Object)null) ? enemyParent.EnableObject : ((Component)enemyParent).gameObject); if ((Object)(object)val == (Object)null) { return false; } try { _root = new GameObject("MobScanner Preview Root"); _root.transform.position = StageOrigin; GameObject val2 = new GameObject("Model"); val2.transform.SetParent(_root.transform, false); val2.transform.localPosition = Vector3.zero; bool activeSelf = val.activeSelf; val.SetActive(false); GameObject val3 = Object.Instantiate<GameObject>(val, val2.transform); val.SetActive(activeSelf); ((Object)val3).name = "ModelBody"; val3.transform.localRotation = Quaternion.identity; val3.transform.localScale = Vector3.one; StripToVisualsOnly(val3); SetLayerRecursive(_root, 31); val3.SetActive(true); Transform[] componentsInChildren = val3.GetComponentsInChildren<Transform>(true); foreach (Transform val4 in componentsInChildren) { ((Component)val4).gameObject.SetActive(true); } Bounds val5 = CalculateBounds(val3); float num = Mathf.Max(new float[3] { ((Bounds)(ref val5)).size.x, ((Bounds)(ref val5)).size.y, ((Bounds)(ref val5)).size.z }); if (num <= 0.001f) { num = 1f; } float num2 = 2f / num; val3.transform.localScale = Vector3.one * num2; Renderer[] componentsInChildren2 = val3.GetComponentsInChildren<Renderer>(true); Vector3 size2 = ((Bounds)(ref val5)).size; float num3 = Mathf.Max(((Vector3)(ref size2)).magnitude * 3f, 6f); int num4 = 0; int num5 = 0; Renderer[] array = componentsInChildren2; foreach (Renderer val6 in array) { Bounds bounds = val6.bounds; Vector3 size3 = ((Bounds)(ref bounds)).size; float num6 = Mathf.Max(size3.x, Mathf.Max(size3.y, size3.z)); bounds = val6.bounds; bool flag = Vector3.Distance(((Bounds)(ref bounds)).center, ((Bounds)(ref val5)).center) > num3; bool flag2 = num6 > 25f; if (flag || flag2) { val6.enabled = false; num4++; } else { num5++; } } if (num5 == 0) { Renderer[] array2 = componentsInChildren2; foreach (Renderer val7 in array2) { val7.enabled = true; } num4 = 0; num5 = componentsInChildren2.Length; MobScanner.LogDebug("PREVIEW: filter emptied model - restored all"); } MobScanner.LogDebug($"PREVIEW: hid {num4}, showing {num5}"); Bounds val8 = CalculateBounds(val3); Vector3 val9 = ((Bounds)(ref val8)).center - val2.transform.position; val3.transform.localPosition = -val9; MobScanner.LogDebug("PREVIEW: source=" + ((Object)val).name + " " + $"renderers={val3.GetComponentsInChildren<Renderer>(true).Length} " + $"skinned={val3.GetComponentsInChildren<SkinnedMeshRenderer>(true).Length} " + $"size={((Bounds)(ref val5)).size} fitScale={num2:F2}"); GameObject val10 = new GameObject("Key Light"); val10.transform.SetParent(_root.transform, false); val10.transform.localPosition = new Vector3(2f, 2.5f, -3f); val10.layer = 31; Light val11 = val10.AddComponent<Light>(); val11.type = (LightType)2; val11.range = 40f; val11.intensity = 6f; val11.cullingMask = int.MinValue; GameObject val12 = new GameObject("Fill Light"); val12.transform.SetParent(_root.transform, false); val12.transform.localPosition = new Vector3(-2.5f, 1f, -2f); val12.layer = 31; Light val13 = val12.AddComponent<Light>(); val13.type = (LightType)2; val13.range = 40f; val13.intensity = 3f; val13.cullingMask = int.MinValue; _texture = new RenderTexture(size, size, 16); _texture.Create(); GameObject val14 = new GameObject("Preview Camera"); val14.transform.SetParent(_root.transform, false); val14.transform.localPosition = new Vector3(0f, 0f, -4f); val14.layer = 31; _camera = val14.AddComponent<Camera>(); _camera.cullingMask = int.MinValue; _camera.clearFlags = (CameraClearFlags)2; _camera.backgroundColor = new Color(0.04f, 0.05f, 0.04f, 1f); _camera.targetTexture = _texture; _camera.fieldOfView = 40f; _camera.nearClipPlane = 0.05f; _camera.farClipPlane = 100f; val14.transform.LookAt(val2.transform.position); ((Behaviour)_camera).enabled = true; Object.DontDestroyOnLoad((Object)(object)_root); return true; } catch (Exception ex) { MobScanner.Logger.LogWarning((object)("PREVIEW: failed to build - " + ex.Message)); Dispose(); return false; } } private static void StripToVisualsOnly(GameObject model) { for (int i = 0; i < 4; i++) { MonoBehaviour[] componentsInChildren = model.GetComponentsInChildren<MonoBehaviour>(true); foreach (MonoBehaviour val in componentsInChildren) { if (!((Object)(object)val == (Object)null)) { try { Object.DestroyImmediate((Object)(object)val); } catch (Exception) { } } } } Component[] componentsInChildren2 = model.GetComponentsInChildren<Component>(true); foreach (Component val2 in componentsInChildren2) { if ((Object)(object)val2 == (Object)null) { continue; } string name = ((object)val2).GetType().Name; if (name.Contains("Photon") || name.Contains("NavMesh")) { try { Object.DestroyImmediate((Object)(object)val2); } catch (Exception) { } } } Collider[] componentsInChildren3 = model.GetComponentsInChildren<Collider>(true); foreach (Collider val3 in componentsInChildren3) { if ((Object)(object)val3 != (Object)null) { Object.DestroyImmediate((Object)(object)val3); } } Rigidbody[] componentsInChildren4 = model.GetComponentsInChildren<Rigidbody>(true); foreach (Rigidbody val4 in componentsInChildren4) { if ((Object)(object)val4 != (Object)null) { Object.DestroyImmediate((Object)(object)val4); } } Animator[] componentsInChildren5 = model.GetComponentsInChildren<Animator>(true); foreach (Animator val5 in componentsInChildren5) { if ((Object)(object)val5 != (Object)null) { ((Behaviour)val5).enabled = false; } } ParticleSystem[] componentsInChildren6 = model.GetComponentsInChildren<ParticleSystem>(true); foreach (ParticleSystem val6 in componentsInChildren6) { if ((Object)(object)val6 != (Object)null) { Object.DestroyImmediate((Object)(object)val6); } } AudioSource[] componentsInChildren7 = model.GetComponentsInChildren<AudioSource>(true); foreach (AudioSource val7 in componentsInChildren7) { if ((Object)(object)val7 != (Object)null) { Object.DestroyImmediate((Object)(object)val7); } } Light[] componentsInChildren8 = model.GetComponentsInChildren<Light>(true); foreach (Light val8 in componentsInChildren8) { if ((Object)(object)val8 != (Object)null) { Object.DestroyImmediate((Object)(object)val8); } } Renderer[] componentsInChildren9 = model.GetComponentsInChildren<Renderer>(true); foreach (Renderer val9 in componentsInChildren9) { val9.enabled = true; ((Component)val9).gameObject.SetActive(true); } } private static Bounds CalculateBounds(GameObject model) { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //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) //IL_0316: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Unknown result type (might be due to invalid IL or missing references) //IL_0060: 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_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0179: Unknown result type (might be due to invalid IL or missing references) //IL_017e: Unknown result type (might be due to invalid IL or missing references) //IL_0103: Unknown result type (might be due to invalid IL or missing references) //IL_0108: 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_009a: Unknown result type (might be due to invalid IL or missing references) //IL_00a1: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: 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_0133: 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_028e: Unknown result type (might be due to invalid IL or missing references) //IL_0293: Unknown result type (might be due to invalid IL or missing references) //IL_0295: Unknown result type (might be due to invalid IL or missing references) //IL_020d: 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_01d1: Unknown result type (might be due to invalid IL or missing references) //IL_01b9: Unknown result type (might be due to invalid IL or missing references) //IL_01be: Unknown result type (might be due to invalid IL or missing references) //IL_02a3: Unknown result type (might be due to invalid IL or missing references) //IL_02b1: Unknown result type (might be due to invalid IL or missing references) //IL_0223: Unknown result type (might be due to invalid IL or missing references) //IL_0310: Unknown result type (might be due to invalid IL or missing references) //IL_0312: Unknown result type (might be due to invalid IL or missing references) //IL_02cd: Unknown result type (might be due to invalid IL or missing references) //IL_02d2: Unknown result type (might be due to invalid IL or missing references) //IL_02dc: Unknown result type (might be due to invalid IL or missing references) //IL_02e1: Unknown result type (might be due to invalid IL or missing references) //IL_02f0: Unknown result type (might be due to invalid IL or missing references) //IL_02f5: Unknown result type (might be due to invalid IL or missing references) //IL_02ff: Unknown result type (might be due to invalid IL or missing references) //IL_0304: Unknown result type (might be due to invalid IL or missing references) Renderer[] componentsInChildren = model.GetComponentsInChildren<Renderer>(true); if (componentsInChildren.Length == 0) { return new Bounds(model.transform.position, Vector3.one); } List<Renderer> list = new List<Renderer>(); List<float> list2 = new List<float>(); Renderer[] array = componentsInChildren; foreach (Renderer val in array) { Bounds bounds = val.bounds; Vector3 size = ((Bounds)(ref bounds)).size; if (!(size.y < 0.02f) || (!(size.x > 5f) && !(size.z > 5f))) { float num = Mathf.Max(size.x, Mathf.Max(size.y, size.z)); if (!(num > 25f)) { list.Add(val); list2.Add(num); } } } if (list.Count == 0) { Bounds bounds2 = componentsInChildren[0].bounds; for (int j = 1; j < componentsInChildren.Length; j++) { ((Bounds)(ref bounds2)).Encapsulate(componentsInChildren[j].bounds); } return bounds2; } List<float> list3 = new List<float>(list2); list3.Sort(); float num2 = list3[list3.Count / 2]; float num3 = Mathf.Max(num2 * 4f, 1.5f); bool flag = false; Bounds bounds3 = default(Bounds); ((Bounds)(ref bounds3))..ctor(model.transform.position, Vector3.zero); int num4 = 0; for (int k = 0; k < list.Count; k++) { if (!(list2[k] > num3)) { if (!flag) { bounds3 = list[k].bounds; flag = true; } else { ((Bounds)(ref bounds3)).Encapsulate(list[k].bounds); } num4++; } } if (!flag) { bounds3 = list[0].bounds; for (int l = 1; l < list.Count; l++) { ((Bounds)(ref bounds3)).Encapsulate(list[l].bounds); } num4 = list.Count; } MobScanner.LogDebug($"PREVIEW: measured {num4}/{componentsInChildren.Length} parts, median={num2:F2}, limit={num3:F2}"); Vector3 size2 = ((Bounds)(ref bounds3)).size; if (size2.x < 0.1f || size2.y < 0.1f || size2.z < 0.1f) { ((Bounds)(ref bounds3)).Encapsulate(((Bounds)(ref bounds3)).center + Vector3.one * 0.25f); ((Bounds)(ref bounds3)).Encapsulate(((Bounds)(ref bounds3)).center - Vector3.one * 0.25f); } return bounds3; } private static void SetLayerRecursive(GameObject target, int layer) { target.layer = layer; Transform[] componentsInChildren = target.GetComponentsInChildren<Transform>(true); foreach (Transform val in componentsInChildren) { ((Component)val).gameObject.layer = layer; } } public void Spin(float degreesPerSecond) { //IL_0035: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_root == (Object)null)) { Transform val = _root.transform.Find("Model"); if ((Object)(object)val != (Object)null) { val.Rotate(Vector3.up, degreesPerSecond * Time.deltaTime, (Space)0); } } } public void Dispose() { if ((Object)(object)_camera != (Object)null) { _camera.targetTexture = null; _camera = null; } if ((Object)(object)_texture != (Object)null) { _texture.Release(); Object.Destroy((Object)(object)_texture); _texture = null; } if ((Object)(object)_root != (Object)null) { Object.Destroy((Object)(object)_root); _root = null; } } } public class ScanResult { public string Name = ""; public int Tier = 1; public int Count = 1; public Transform? EnemyTransform; public EnemyParent? Parent; public GameObject? Marker; } public class Scanner : MonoBehaviour { public static ConfigEntry<KeyCode> ScanKey = null; public static ConfigEntry<float> ScanRadius = null; public static ConfigEntry<float> HoldTime = null; public static ConfigEntry<float> ResultDuration = null; public static ConfigEntry<float> MarkerScale = null; public static ConfigEntry<float> Cooldown = null; public static ConfigEntry<float> MarkerHeight = null; public static ConfigEntry<bool> ShowModel = null; public static ConfigEntry<float> SpinSpeed = null; public static ConfigEntry<float> ModelCycleTime = null; public static ConfigEntry<float> UpgradePrice = null; public static ConfigEntry<int> UsesPerLevel = null; public static ConfigEntry<bool> RequireUpgrade = null; public static ConfigEntry<bool> AlwaysInShop = null; public static ConfigEntry<bool> EyeEffect = null; public static ConfigEntry<float> EyeFlashSpeed = null; public static ConfigEntry<float> EyeResultTime = null; public static ConfigEntry<string> FontName = null; private float _holdTimer; private bool _scanning; private bool _awaitingRelease; private readonly List<ScanResult> _results = new List<ScanResult>(); private float _resultTimer; private float _cooldownTimer; private bool _foundAnything; private static bool _hasScanner; private static int _usesLeft; private string _lastLevelName = ""; private float _messageTimer; private string _message = ""; private readonly ModelPreview _preview = new ModelPreview(); private int _previewIndex; private float _previewTimer; private string _previewName = ""; private Texture2D? _dotTexture; private static readonly Color TierGreen = new Color(0.2f, 1f, 0.2f); private static readonly Color TierOrange = new Color(1f, 0.65f, 0f); private static readonly Color TierRed = new Color(1f, 0.15f, 0.15f); private float _shopRegisterTimer; private float _eyeFlashTimer; private bool _eyeUseRed; private float _eyeResultTimer; private bool _eyeResultFound; private static Font? _gameFont; private static bool _fontSearched; private static Font? GameFont { get { EnsureFont(); return _gameFont; } } public static void GrantScanner() { _hasScanner = true; } private static Color ColourForTier(int tier) { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Unknown result type (might be due to invalid IL or missing references) //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) //IL_001c: 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_002c: Unknown result type (might be due to invalid IL or missing references) if (tier >= 3) { return TierRed; } if (tier == 2) { return TierOrange; } return TierGreen; } private void Awake() { //IL_0004: Unknown result type (might be due to invalid IL or missing references) //IL_000e: Expected O, but got Unknown //IL_0016: Unknown result type (might be due to invalid IL or missing references) _dotTexture = new Texture2D(1, 1); _dotTexture.SetPixel(0, 0, Color.white); _dotTexture.Apply(); } private void Update() { //IL_02ee: Unknown result type (might be due to invalid IL or missing references) //IL_02aa: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)ShopIntegration.RegisteredItem == (Object)null) { _shopRegisterTimer -= Time.deltaTime; if (_shopRegisterTimer <= 0f) { _shopRegisterTimer = 1f; ShopIntegration.TryRegister(); } } UpdateMarkers(); if (_resultTimer > 0f) { _preview.Spin(SpinSpeed.Value); if (_previewTimer > 0f) { _previewTimer -= Time.deltaTime; if (_previewTimer <= 0f) { ShowNextPreview(); } } } if (_resultTimer > 0f) { _resultTimer -= Time.deltaTime; if (_resultTimer <= 0f) { ClearResults(); } } if (_cooldownTimer > 0f) { _cooldownTimer -= Time.deltaTime; } if (_messageTimer > 0f) { _messageTimer -= Time.deltaTime; } if ((Object)(object)Map.Instance == (Object)null || (Object)(object)PlayerController.instance == (Object)null) { _eyeResultTimer = 0f; return; } if (_eyeResultTimer > 0f) { _eyeResultTimer -= Time.deltaTime; ShowResultEyes(); } string levelKey = GetLevelKey(); if (levelKey != _lastLevelName) { MobScanner.LogDebug("SCAN: level changed '" + _lastLevelName + "' -> '" + levelKey + "'"); _lastLevelName = levelKey; _usesLeft = UsesPerLevel.Value; ClearResults(); MobScanner.LogDebug($"SCAN: uses reset to {_usesLeft}"); } if (RequireUpgrade.Value && !_hasScanner) { return; } if (_cooldownTimer > 0f) { _scanning = false; _holdTimer = 0f; } else if (UsesPerLevel.Value > 0 && _usesLeft <= 0) { if (Input.GetKeyDown(ScanKey.Value)) { _message = "NO SCANS LEFT"; _messageTimer = 2f; } _scanning = false; _holdTimer = 0f; } else if (!Input.GetKey(ScanKey.Value)) { if (_scanning) { MobScanner.LogDebug("SCAN: cancelled (key released)"); } _scanning = false; _holdTimer = 0f; _awaitingRelease = false; } else { if (_awaitingRelease) { return; } if (!_scanning) { _scanning = true; _holdTimer = 0f; MobScanner.LogDebug("SCAN: started - charging..."); return; } UpdateEyeEffect(); _holdTimer += Time.deltaTime; if (!(_holdTimer >= HoldTime.Value)) { return; } _scanning = false; _holdTimer = 0f; _awaitingRelease = true; DoScan(); _eyeResultFound = _foundAnything; _eyeResultTimer = EyeResultTime.Value; if (_foundAnything) { _cooldownTimer = Cooldown.Value; if (UsesPerLevel.Value > 0) { _usesLeft--; MobScanner.LogDebug($"SCAN: use consumed - {_usesLeft} left this level"); } else { MobScanner.LogDebug("SCAN: unlimited mode - no use consumed"); } } else { MobScanner.LogDebug("SCAN: nothing found - use NOT consumed"); } } } private static void EnsureFont() { if (_fontSearched) { return; } _fontSearched = true; Font[] array = Resources.FindObjectsOfTypeAll<Font>(); MobScanner.LogDebug($"FONT: {array.Length} font(s) loaded in memory"); Font[] array2 = array; foreach (Font val in array2) { if ((Object)(object)val != (Object)null) { MobScanner.LogDebug("FONT: available '" + ((Object)val).name + "'"); } } string text = FontName.Value ?? ""; if (text.Length > 0) { Font[] array3 = array; foreach (Font val2 in array3) { if ((Object)(object)val2 != (Object)null && ((Object)val2).name.IndexOf(text, StringComparison.OrdinalIgnoreCase) >= 0) { _gameFont = val2; MobScanner.LogDebug("FONT: using '" + ((Object)val2).name + "' (matched config)"); return; } } MobScanner.Logger.LogWarning((object)("FONT: no font matching '" + text + "' - falling back to the default")); return; } string[] array4 = new string[7] { "pixel", "silk", "vcr", "press", "arcade", "8bit", "bit" }; string[] array5 = array4; foreach (string text2 in array5) { Font[] array6 = array; foreach (Font val3 in array6) { if ((Object)(object)val3 != (Object)null && ((Object)val3).name.IndexOf(text2, StringComparison.OrdinalIgnoreCase) >= 0) { _gameFont = val3; MobScanner.LogDebug("FONT: auto-picked '" + ((Object)val3).name + "' (hint '" + text2 + "')"); return; } } } MobScanner.LogDebug("FONT: no pixel font found - using Unity's default"); } private void UpdateEyeEffect() { //IL_00a5: 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) if (!EyeEffect.Value) { return; } PlayerAvatar playerAvatarScript = PlayerController.instance.playerAvatarScript; if (!((Object)(object)playerAvatarScript == (Object)null) && !((Object)(object)playerAvatarScript.playerHealth == (Object)null)) { _eyeFlashTimer -= Time.deltaTime; if (_eyeFlashTimer <= 0f) { _eyeFlashTimer = 1f / Mathf.Max(EyeFlashSpeed.Value, 0.1f); _eyeUseRed = !_eyeUseRed; } EyeOverrideState val = (EyeOverrideState)(_eyeUseRed ? 1 : 4); playerAvatarScript.playerHealth.EyeMaterialOverride(val, 0.25f, 2); } } private void ShowResultEyes() { //IL_005c: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) if (EyeEffect.Value && !((Object)(object)PlayerController.instance == (Object)null)) { PlayerAvatar playerAvatarScript = PlayerController.instance.playerAvatarScript; if (!((Object)(object)playerAvatarScript == (Object)null) && !((Object)(object)playerAvatarScript.playerHealth == (Object)null)) { EyeOverrideState val = (EyeOverrideState)(_eyeResultFound ? 3 : 2); playerAvatarScript.playerHealth.EyeMaterialOverride(val, 0.25f, 3); } } } private static string GetLevelKey() { RunManager instance = RunManager.instance; if ((Object)(object)instance == (Object)null) { return "no-run"; } string arg = (((Object)(object)instance.levelCurrent != (Object)null) ? ((Object)instance.levelCurrent).name : "null"); return $"{arg}|{instance.levelsCompleted}|{instance.runLives}"; } private List<ScanResult> UniqueResults() { List<ScanResult> list = new List<ScanResult>(); foreach (ScanResult result in _results) { if (result.Count > 0) { list.Add(result); } } return list; } private void ShowNextPreview() { if (ShowModel.Value) { List<ScanResult> list = UniqueResults(); if (list.Count <= 1) { _previewTimer = ModelCycleTime.Value; return; } _previewIndex = (_previewIndex + 1) % list.Count; BuildPreviewFor(list[_previewIndex]); } } private void BuildPreviewFor(ScanResult result) { if (!((Object)(object)result.Parent == (Object)null)) { if (_preview.IsValid && _previewName == result.Name) { _previewTimer = ModelCycleTime.Value; return; } bool flag = _preview.Build(result.Parent, 220); _previewName = result.Name; _previewTimer = ModelCycleTime.Value; MobScanner.LogDebug("PREVIEW: showing " + result.Name + " (" + (flag ? "ok" : "failed") + ")"); } } private void ClearResults() { foreach (ScanResult result in _results) { if ((Object)(object)result.Marker != (Object)null) { Object.Destroy((Object)(object)result.Marker); } } _results.Clear(); _preview.Dispose(); _previewIndex = 0; _previewTimer = 0f; _previewName = ""; } private void UpdateMarkers() { //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_0088: Unknown result type (might be due to invalid IL or missing references) //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Unknown result type (might be due to invalid IL or missing references) //IL_0095: 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_00bb: Unknown result type (might be due to invalid IL or missing references) //IL_00c2: Unknown result type (might be due to invalid IL or missing references) //IL_00ea: Unknown result type (might be due to invalid IL or missing references) //IL_00ef: Unknown result type (might be due to invalid IL or missing references) //IL_00f1: 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_0100: Unknown result type (might be due to invalid IL or missing references) //IL_0105: Unknown result type (might be due to invalid IL or missing references) //IL_0139: Unknown result type (might be due to invalid IL or missing references) //IL_016b: Unknown result type (might be due to invalid IL or missing references) //IL_0172: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)Map.Instance == (Object)null) { return; } foreach (ScanResult result in _results) { if (!((Object)(object)result.Marker == (Object)null) && !((Object)(object)result.EnemyTransform == (Object)null)) { Transform transform = result.Marker.transform; Vector3 val = result.EnemyTransform.position * Map.Instance.Scale + Map.Instance.OverLayerParent.position; transform.position = new Vector3(val.x, Map.Instance.OverLayerParent.position.y + MarkerHeight.Value, val.z); float num = Mathf.PingPong(Time.time * 2.2f, 1f); Color val2 = ColourForTier(result.Tier); Color color = Color.Lerp(val2, Color.white, num * 0.55f); color.a = 0.55f + num * 0.45f; SpriteRenderer[] componentsInChildren = result.Marker.GetComponentsInChildren<SpriteRenderer>(true); foreach (SpriteRenderer val3 in componentsInChildren) { val3.color = color; } float num2 = MarkerScale.Value * (1f + num * 0.35f); transform.localScale = Vector3.one * num2; } } } private GameObject? CreateMarker(Transform enemyTransform, Color colour) { //IL_00ea: 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_011d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)Map.Instance == (Object)null) { return null; } GameObject val = (((Object)(object)Map.Instance.ValuableObject != (Object)null) ? Map.Instance.ValuableObject : Map.Instance.EnemyObject); if ((Object)(object)val == (Object)null) { return null; } GameObject val2 = Object.Instantiate<GameObject>(val, Map.Instance.OverLayerParent); ((Object)val2).name = "MobScanner Marker"; val2.SetActive(true); MapValuable component = val2.GetComponent<MapValuable>(); if ((Object)(object)component != (Object)null) { SpriteRenderer spriteRenderer = component.spriteRenderer; if ((Object)(object)spriteRenderer != (Object)null && (Object)(object)spriteRenderer.sprite == (Object)null) { spriteRenderer.sprite = (((Object)(object)component.spriteBig != (Object)null) ? component.spriteBig : component.spriteSmall); } Object.Destroy((Object)(object)component); } val2.transform.localScale = Vector3.one * MarkerScale.Value; SpriteRenderer[] componentsInChildren = val2.GetComponentsInChildren<SpriteRenderer>(true); foreach (SpriteRenderer val3 in componentsInChildren) { val3.color = colour; ((Renderer)val3).enabled = true; ((Renderer)val3).sortingOrder = 32000; } Transform[] componentsInChildren2 = val2.GetComponentsInChildren<Transform>(true); foreach (Transform val4 in componentsInChildren2) { ((Component)val4).gameObject.SetActive(true); ((Component)val4).gameObject.layer = ((Component)Map.Instance.OverLayerParent).gameObject.layer; } MobScanner.LogDebug($"MARKER: built from {((Object)val).name}, scale={MarkerScale.Value}"); return val2; } private void DoScan() { //IL_002d: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0106: Unknown result type (might be due to invalid IL or missing references) //IL_010b: Unknown result type (might be due to invalid IL or missing references) //IL_010d: Unknown result type (might be due to invalid IL or missing references) //IL_010e: Unknown result type (might be due to invalid IL or missing references) //IL_018c: Unknown result type (might be due to invalid IL or missing references) //IL_0192: Unknown result type (might be due to invalid IL or missing references) //IL_0195: Expected I4, but got Unknown //IL_0197: Unknown result type (might be due to invalid IL or missing references) //IL_019c: Unknown result type (might be due to invalid IL or missing references) //IL_031b: Unknown result type (might be due to invalid IL or missing references) //IL_022f: Unknown result type (might be due to invalid IL or missing references) MobScanner.LogDebug("=== SCAN COMPLETE ==="); ClearResults(); _resultTimer = ResultDuration.Value; Vector3 position = ((Component)PlayerController.instance).transform.position; List<RoomVolume> list = new List<RoomVolume>(); PlayerAvatar playerAvatarScript = PlayerController.instance.playerAvatarScript; if ((Object)(object)playerAvatarScript != (Object)null && (Object)(object)playerAvatarScript.RoomVolumeCheck != (Object)null) { list.AddRange(playerAvatarScript.RoomVolumeCheck.CurrentRooms); } foreach (EnemyParent item in EnemyDirector.instance.enemiesSpawned) { if ((Object)(object)item == (Object)null || (Object)(object)item.Enemy == (Object)null || !item.Spawned || (item.Enemy.HasHealth && item.Enemy.Health.dead)) { continue; } Vector3 position2 = ((Component)item.Enemy).transform.position; float num = Vector3.Distance(position, position2); if (num > ScanRadius.Value) { continue; } bool flag = false; foreach (RoomVolume currentRoom in item.currentRooms) { if ((Object)(object)currentRoom != (Object)null && list.Contains(currentRoom)) { flag = true; break; } } int num2 = item.difficulty + 1; Color colour = ColourForTier(num2); ScanResult scanResult = null; foreach (ScanResult result in _results) { if (result.Name == item.enemyName) { scanResult = result; break; } } if (scanResult != null) { scanResult.Count++; scanResult.Marker = scanResult.Marker; GameObject val = CreateMarker(((Component)item.Enemy).transform, colour); if ((Object)(object)val != (Object)null) { _results.Add(new ScanResult { Name = item.enemyName, Tier = num2, Count = 0, EnemyTransform = ((Component)item.Enemy).transform, Parent = item, Marker = val }); } MobScanner.LogDebug($"SCAN: found {item.enemyName} | T{num2} | {num:F1}m | " + (flag ? "SAME ROOM" : "nearby room")); } else { ScanResult scanResult2 = new ScanResult { Name = item.enemyName, Tier = num2, EnemyTransform = ((Component)item.Enemy).transform, Parent = item }; scanResult2.Marker = CreateMarker(((Component)item.Enemy).transform, colour); if ((Object)(object)scanResult2.Marker == (Object)null) { MobScanner.Logger.LogWarning((object)"SCAN: could not create map marker"); } _results.Add(scanResult2); MobScanner.LogDebug($"SCAN: found {item.enemyName} | T{num2} | {num:F1}m | " + (flag ? "SAME ROOM" : "nearby room")); } } _foundAnything = _results.Count > 0; if (_foundAnything && ShowModel.Value) { List<ScanResult> list2 = UniqueResults(); if (list2.Count > 0) { _previewIndex = 0; BuildPreviewFor(list2[0]); } } if (_results.Count == 0) { MobScanner.LogDebug("SCAN: no monsters in range"); } MobScanner.LogDebug("====================="); } private void DrawRect(float x, float y, float width, float height, Color colour) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0019: 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) //IL_0037: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_dotTexture == (Object)null)) { Color color = GUI.color; GUI.color = colour; GUI.DrawTexture(new Rect(x, y, width, height), (Texture)(object)_dotTexture); GUI.color = color; } } private void DrawDot(float x, float y, float size, Color colour) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0019: 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_0036: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_dotTexture == (Object)null)) { Color color = GUI.color; GUI.color = colour; GUI.DrawTexture(new Rect(x, y, size, size), (Texture)(object)_dotTexture); GUI.color = color; } } private void OnGUI() { //IL_0048: Unknown result type (might be due to invalid IL or missing references) //IL_004d: 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_0062: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Expected O, but got Unknown //IL_0082: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: 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_00f5: Unknown result type (might be due to invalid IL or missing references) //IL_00fe: Unknown result type (might be due to invalid IL or missing references) //IL_0108: Expected O, but got Unknown //IL_023c: Unknown result type (might be due to invalid IL or missing references) //IL_0251: Unknown result type (might be due to invalid IL or missing references) //IL_0256: Unknown result type (might be due to invalid IL or missing references) //IL_0262: Unknown result type (might be due to invalid IL or missing references) //IL_026b: Unknown result type (might be due to invalid IL or missing references) //IL_0275: Expected O, but got Unknown //IL_028d: Unknown result type (might be due to invalid IL or missing references) //IL_02aa: Unknown result type (might be due to invalid IL or missing references) //IL_0153: Unknown result type (might be due to invalid IL or missing references) //IL_02e6: Unknown result type (might be due to invalid IL or missing references) //IL_02eb: Unknown result type (might be due to invalid IL or missing references) //IL_02f7: Unknown result type (might be due to invalid IL or missing references) //IL_0300: Unknown result type (might be due to invalid IL or missing references) //IL_0309: Expected O, but got Unknown //IL_0138: 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_052d: Unknown result type (might be due to invalid IL or missing references) //IL_0533: Expected O, but got Unknown //IL_0385: Unknown result type (might be due to invalid IL or missing references) //IL_03c4: Unknown result type (might be due to invalid IL or missing references) //IL_03eb: Unknown result type (might be due to invalid IL or missing references) //IL_03fd: Unknown result type (might be due to invalid IL or missing references) //IL_0566: Unknown result type (might be due to invalid IL or missing references) //IL_0550: Unknown result type (might be due to invalid IL or missing references) //IL_057d: Unknown result type (might be due to invalid IL or missing references) //IL_0445: Unknown result type (might be due to invalid IL or missing references) //IL_048f: Unknown result type (might be due to invalid IL or missing references) //IL_0494: Unknown result type (might be due to invalid IL or missing references) //IL_04a0: Unknown result type (might be due to invalid IL or missing references) //IL_04a9: Unknown result type (might be due to invalid IL or missing references) //IL_04b1: Unknown result type (might be due to invalid IL or missing references) //IL_04bb: Expected O, but got Unknown //IL_04d6: Unknown result type (might be due to invalid IL or missing references) //IL_04fa: Unknown result type (might be due to invalid IL or missing references) //IL_05e7: Unknown result type (might be due to invalid IL or missing references) //IL_05ec: Unknown result type (might be due to invalid IL or missing references) //IL_060e: Unknown result type (might be due to invalid IL or missing references) //IL_0617: Unknown result type (might be due to invalid IL or missing references) //IL_061e: Expected O, but got Unknown //IL_0625: Unknown result type (might be due to invalid IL or missing references) //IL_063d: Unknown result type (might be due to invalid IL or missing references) //IL_0661: Unknown result type (might be due to invalid IL or missing references) //IL_0668: Expected O, but got Unknown //IL_066f: Unknown result type (might be due to invalid IL or missing references) //IL_06bc: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)Map.Instance == (Object)null) { return; } if (_messageTimer > 0f && _message != "") { GUIStyle val = new GUIStyle(GUI.skin.label) { font = GameFont, fontSize = 18, fontStyle = (FontStyle)1 }; val.normal.textColor = new Color(1f, 0.4f, 0.3f); GUI.Label(new Rect(20f, (float)Screen.height * 0.44f, 320f, 26f), _message, val); } if (!RequireUpgrade.Value || _hasScanner) { GUIStyle val2 = new GUIStyle(GUI.skin.label) { font = GameFont, fontSize = 14, fontStyle = (FontStyle)1 }; val2.normal.textColor = ((UsesPerLevel.Value <= 0 || _usesLeft > 0) ? new Color(0.4f, 1f, 0.5f, 0.85f) : new Color(0.7f, 0.3f, 0.3f, 0.85f)); string text = ((UsesPerLevel.Value > 0) ? $"SCANS: {_usesLeft}" : "SCANS: UNLIMITED"); GUI.Label(new Rect(20f, (float)Screen.height * 0.41f, 320f, 20f), text, val2); } float num = 20f; float num2 = (float)Screen.height * 0.44f; if (_scanning) { float num3 = _holdTimer / HoldTime.Value; float num4 = 4f + num3 * 8f; float num5 = Mathf.PingPong(Time.time * num4, 1f); float num6 = 0.35f + num5 * 0.65f; DrawDot(num, num2 + 7f, 11f, new Color(0.2f, 1f, 0.2f, num6)); GUIStyle val3 = new GUIStyle(GUI.skin.label) { font = GameFont, fontSize = 18, fontStyle = (FontStyle)1 }; val3.normal.textColor = new Color(0.2f, 1f, 0.2f, num6); GUI.Label(new Rect(num + 20f, num2, 320f, 28f), "SCANNING...", val3); } else { if (_resultTimer <= 0f) { return; } GUIStyle val4 = new GUIStyle(GUI.skin.label) { font = GameFont, fontSize = 18, fontStyle = (FontStyle)1 }; if (_preview.IsValid && (Object)(object)_preview.Texture != (Object)null) { float num7 = 150f; float num8 = 4f; float num9 = num2 - num7 - 12f; float x = num - num8; float y = num9 - num8; float num10 = num7 + num8 * 2f; DrawRect(x, y, num10, num10, new Color(0.58f, 0.6f, 0.57f, 0.95f)); DrawRect(num - 1f, num9 - 1f, num7 + 2f, num7 + 2f, new Color(0.08f, 0.1f, 0.08f, 1f)); DrawRect(num, num9, num7, num7, new Color(0.07f, 0.13f, 0.09f, 1f)); GUI.DrawTexture(new Rect(num, num9, num7, num7), (Texture)(object)_preview.Texture); Color colour = default(Color); ((Color)(ref colour))..ctor(0f, 0f, 0f, 0.14f); for (float num11 = 1f; num11 < num7 - 1f; num11 += 4f) { DrawRect(num, num9 + num11, num7, 2f, colour); } List<ScanResult> list = UniqueResults(); if (list.Count > 1) { GUIStyle val5 = new GUIStyle(GUI.skin.label) { font = GameFont, fontSize = 12, fontStyle = (FontStyle)1, alignment = (TextAnchor)5 }; val5.normal.textColor = new Color(0.5f, 1f, 0.6f, 0.85f); GUI.Label(new Rect(num, num9 + num7 - 18f, num7 - 5f, 16f), $"{_previewIndex + 1}/{list.Count}", val5); } } GUIStyle val6 = new GUIStyle(val4); val6.normal.textColor = (_foundAnything ? new Color(0.2f, 1f, 0.2f) : new Color(0.75f, 0.75f, 0.75f)); GUI.Label(new Rect(num, num2, 320f, 26f), _foundAnything ? "FOUND" : "NOT FOUND", val6); float num12 = 26f; float num13 = num2 + 28f; int num14 = 0; for (int i = 0; i < _results.Count; i++) { ScanResult scanResult = _results[i]; if (scanResult.Count > 0) { Color val7 = ColourForTier(scanResult.Tier); float num15 = num13 + (float)num14 * num12; num14++; DrawDot(num, num15 + 7f, 11f, val7); GUIStyle val8 = new GUIStyle(val4); val8.normal.textColor = val7; GUI.Label(new Rect(num + 20f, num15, 36f, num12), $"T{scanResult.Tier}", val8); GUIStyle val9 = new GUIStyle(val4); val9.normal.textColor = Color.white; string text2 = ((scanResult.Count > 1) ? $"{scanResult.Name} x{scanResult.Count}" : scanResult.Name); GUI.Label(new Rect(num + 54f, num15, 280f, num12), text2, val9); } } } } private void OnDestroy() { ClearResults(); } } public static class ShopIntegration { public const string ItemKey = "Item Upgrade Android Vision"; public const string DisplayName = "Android vision"; private const string TemplateKey = "Item Upgrade Player Grab Strength"; internal static Item? RegisteredItem; public static void TryRegister() { //IL_01d1: Unknown result type (might be due to invalid IL or missing references) //IL_00de: Unknown result type (might be due to invalid IL or missing references) //IL_00e4: Invalid comparison between Unknown and I4 if ((Object)(object)RegisteredItem != (Object)null || (Object)(object)StatsManager.instance == (Object)null) { return; } Dictionary<string, Item> itemDictionary = StatsManager.instance.itemDictionary; if (itemDictionary.Count == 0) { return; } if (itemDictionary.ContainsKey("Item Upgrade Android Vision")) { RegisteredItem = itemDictionary["Item Upgrade Android Vision"]; return; } MobScanner.LogDebug($"SHOP: item dictionary has {itemDictionary.Count} entries, registering..."); Item val = null; if (itemDictionary.ContainsKey("Item Upgrade Player Grab Strength")) { val = itemDictionary["Item Upgrade Player Grab Strength"]; } else { foreach (KeyValuePair<string, Item> item in itemDictionary) { if ((Object)(object)item.Value != (Object)null && (int)item.Value.itemType == 3) { val = item.Value; MobScanner.LogDebug("SHOP: template 'Item Upgrade Player Grab Strength' missing, using '" + item.Key + "'"); break; } } } if ((Object)(object)val == (Object)null) { MobScanner.Logger.LogWarning((object)"SHOP: no upgrade template found - cannot register"); return; } Item val2 = Object.Instantiate<Item>(val); ((Object)val2).name = "Item Upgrade Android Vision"; val2.itemName = "Android vision"; val2.itemNameLocalized = null; val2.value.valueMin = 2000f; val2.value.valueMax = 2000f; val2.maxAmountInShop = 1; Object.DontDestroyOnLoad((Object)(object)val2); itemDictionary["Item Upgrade Android Vision"] = val2; RegisteredItem = val2; MobScanner.LogDebug("SHOP: registered 'Android vision' (template=" + ((Object)val).name + ", " + $"type={val2.itemType})"); } } [HarmonyPatch(typeof(StatsManager))] internal static class StatsManagerPatch { [HarmonyPostfix] [HarmonyPatch("LoadItemsFromFolder")] private static void LoadItemsFromFolder_Postfix() { ShopIntegration.TryRegister(); } } [HarmonyPatch(typeof(ShopManager), "UpgradeValueGet")] internal static class UpgradeValueGetPatch { private static void Postfix(Item item, ref float __result) { if ((Object)(object)item != (Object)null && ((Object)item).name == "Item Upgrade Android Vision") { __result = Scanner.UpgradePrice.Value; } } } [HarmonyPatch(typeof(ShopManager), "GetAllItemsFromStatsManager")] internal static class ForceIntoPoolPatch { private static void Postfix(ShopManager __instance) { if (!Scanner.AlwaysInShop.Value) { return; } Item registeredItem = ShopIntegration.RegisteredItem; if ((Object)(object)registeredItem == (Object)null) { return; } foreach (Item potentialItemUpgrade in __instance.potentialItemUpgrades) { if ((Object)(object)potentialItemUpgrade != (Object)null && ((Object)potentialItemUpgrade).name == "Item Upgrade Android Vision") { return; } } if (SemiFunc.StatGetItemsPurchased(((Object)registeredItem).name) < registeredItem.maxAmountInShop) { __instance.potentialItemUpgrades.Add(registeredItem); MobScanner.LogDebug($"SHOP POOL: forced Android vision to front of {__instance.potentialItemUpgrades.Count} upgrades " + $"(shop shows {__instance.itemUpgradesAmount})"); } } } [HarmonyPatch(typeof(ShopManager), "GetAllItemsFromStatsManager")] internal static class ShopPoolPatch { private static void Postfix(ShopManager __instance) { int count = __instance.potentialItemUpgrades.Count; int num = 0; foreach (Item potentialItemUpgrade in __instance.potentialItemUpgrades) { if ((Object)(object)potentialItemUpgrade != (Object)null && ((Object)potentialItemUpgrade).name == "Item Upgrade Android Vision") { num++; } } MobScanner.LogDebug($"SHOP POOL: {count} upgrades available, {num} of them are Android vision"); for (int i = 0; i < __instance.potentialItemUpgrades.Count; i++) { Item val = __instance.potentialItemUpgrades[i]; if ((Object)(object)val != (Object)null && ((Object)val).name == "Item Upgrade Android Vision") { MobScanner.LogDebug($"SHOP POOL: Android vision is at position {i} " + $"(shop displays the first {__instance.itemUpgradesAmount})"); break; } } if (num == 0) { MobScanner.LogDebug("SHOP POOL: Android vision was filtered out - checking why..."); if ((Object)(object)ShopIntegration.RegisteredItem == (Object)null) { MobScanner.LogDebug("SHOP POOL: reason = item never registered"); return; } Item registeredItem = ShopIntegration.RegisteredItem; int num2 = SemiFunc.StatGetItemsPurchased(((Object)registeredItem).name); MobScanner.LogDebug($"SHOP POOL: purchased={num2} " + $"maxAmountInShop={registeredItem.maxAmountInShop} " + $"maxPurchase={registeredItem.maxPurchase} " + $"minPlayerCount={registeredItem.minPlayerCount} " + $"valueMax={registeredItem.value.valueMax} " + $"currency={__instance.totalCurrency}"); } } } [HarmonyPatch(typeof(PunManager), "SpawnShopItem")] internal static class SpawnShopItemPatch { private static void Postfix(ItemVolume itemVolume, List<Item> itemList, bool __result) { //IL_006b: Unknown result type (might be due to invalid IL or missing references) if (!__result) { return; } bool flag = false; foreach (Item item in itemList) { if ((Object)(object)item != (Object)null && ((Object)item).name == "Item Upgrade Android Vision") { flag = true; break; } } MobScanner.LogDebug($"SHOP SPAWN: placed an item on a '{itemVolume.itemVolume}' shelf, " + $"{itemList.Count} left in this list, ours still queued: {flag}"); } } [HarmonyPatch(typeof(PunManager), "ShopPopulateItemVolumes")] internal static class ShelfCheckPatch { private static void Prefix() { //IL_0052: 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_008d: Unknown result type (might be due to invalid IL or missing references) Item registeredItem = ShopIntegration.RegisteredItem; if ((Object)(object)registeredItem == (Object)null || (Object)(object)ShopManager.instance == (Object)null) { return; } int num = 0; foreach (ItemVolume itemVolume in ShopManager.instance.itemVolumes) { if ((Object)(object)itemVolume != (Object)null && itemVolume.itemVolume == registeredItem.itemVolume) { num++; } } MobScanner.LogDebug($"SHOP SHELVES: Android vision needs a '{registeredItem.itemVolume}' shelf; " + $"{num} of {ShopManager.instance.itemVolumes.Count} shelves match. " + "prefab=" + ((registeredItem.prefab == null) ? "NULL" : ((PrefabRef<GameObject>)(object)registeredItem.prefab).ResourcePath)); } } [HarmonyPatch(typeof(ItemAttributes), "Start")] internal static class ItemAttributesStartPatch { internal static int PendingSpawns; private static void Postfix(ItemAttributes __instance) { //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Invalid comparison between Unknown and I4 if (PendingSpawns > 0 && SemiFunc.RunIsShop()) { Item registeredItem = ShopIntegration.RegisteredItem; if (!((Object)(object)registeredItem == (Object)null) && !((Object)(object)__instance.item == (Object)null) && (!(((Object)__instance.item).name != ((Object)registeredItem).name) || (int)__instance.item.itemType == 3)) { PendingSpawns--; __instance.item = registeredItem; __instance.itemName = "Android vision"; __instance.value = (int)Scanner.UpgradePrice.Value; MobScanner.LogDebug("SHOP: converted a spawned upgrade into 'Android vision' " + $"at {__instance.value}"); } } } } [HarmonyPatch(typeof(PunManager), "ShopPopulateItemVolumes")] internal static class MarkPendingPatch { private static void Prefix() { Item registeredItem = ShopIntegration.RegisteredItem; if ((Object)(object)registeredItem == (Object)null) { ItemAttributesStartPatch.PendingSpawns = 0; return; } if (SemiFunc.StatGetItemsPurchased(((Object)registeredItem).name) >= registeredItem.maxAmountInShop) { ItemAttributesStartPatch.PendingSpawns = 0; return; } ItemAttributesStartPatch.PendingSpawns = 1; MobScanner.LogDebug("SHOP: expecting to convert 1 upgrade into Android vision"); } } [HarmonyPatch(typeof(StatsManager), "AddItemsUpgradesPurchased")] internal static class UpgradePurchasedPatch { private static void Postfix(string itemName) { if (!(itemName != "Item Upgrade Android Vision")) { Scanner.GrantScanner(); MobScanner.LogDebug("SHOP: Android vision activated"); } } } public static class UpgradeBoxModel { private static readonly Color BodyOrange = new Color(0.85f, 0.42f, 0.13f); private static readonly Color BodyDark = new Color(0.55f, 0.26f, 0.08f); private static readonly Color ScreenGreen = new Color(0.24f, 0.78f, 0.35f); private static readonly Color ScreenGlow = new Color(0.45f, 1f, 0.55f); private static readonly Color CaseGrey = new Color(0.72f, 0.74f, 0.68f); public static GameObject Build() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Expected O, but got Unknown //IL_0026: Unknown result type (might be due to invalid IL or missing references) //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_0064: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_007d: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00b6: Unknown result type (might be due to invalid IL or missing references) //IL_00bb: 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_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_0105: Unknown result type (might be due to invalid IL or missing references) //IL_012f: Unknown result type (might be due to invalid IL or missing references) //IL_0143: 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_016d: Unknown result type (might be due to invalid IL or missing references) //IL_0181: Unknown result type (might be due to invalid IL or missing references) //IL_0186: 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_01ba: Unknown result type (might be due to invalid IL or missing references) //IL_01bf: Unknown result type (might be due to invalid IL or missing references) //IL_01e4: Unknown result type (might be due to invalid IL or missing references) //IL_01e9: Unknown result type (might be due to invalid IL or missing references) //IL_01f3: Unknown result type (might be due to invalid IL or missing references) //IL_01f8: Unknown result type (might be due to invalid IL or missing references) //IL_021d: Unknown result type (might be due to invalid IL or missing references) //IL_0222: Unknown result type (might be due to invalid IL or missing references) //IL_022c: Unknown result type (might be due to invalid IL or missing references) //IL_0240: Unknown result type (might be due to invalid IL or missing references) //IL_0265: Unknown result type (might be due to invalid IL or missing references) //IL_026a: Unknown result type (might be due to invalid IL or missing references) //IL_0274: Unknown result type (might be due to invalid IL or missing references) //IL_0288: Unknown result type (might be due to invalid IL or missing references) //IL_02ad: Unknown result type (might be due to invalid IL or missing references) //IL_02b2: Unknown result type (might be due to invalid IL or missing references) //IL_02bc: Unknown result type (might be due to invalid IL or missing references) //IL_02d0: Unknown result type (might be due to invalid IL or missing references) GameObject val = new GameObject("Android Vision Model"); GameObject val2 = MakeCube(val.transform, "Body", new Vector3(0f, 0f, 0f), new Vector3(0.55f, 0.62f, 0.3f), BodyOrange); MakeCube(val.transform, "Base", new Vector3(0f, -0.34f, 0f), new Vector3(0.62f, 0.1f, 0.36f), BodyDark); MakeCube(val.transform, "Bezel", new Vector3(0f, 0.08f, -0.16f), new Vector3(0.44f, 0.36f, 0.04f), CaseGrey); GameObject part = MakeCube(val.transform, "Screen", new Vector3(0f, 0.08f, -0.185f), new Vector3(0.36f, 0.28f, 0.02f), ScreenGreen); MakeEmissive(part, ScreenGlow, 1.4f); MakeCylinder(val.transform, "Antenna L", new Vector3(-0.16f, 0.42f, 0f), new Vector3(0.03f, 0.12f, 0.03f), CaseGrey); MakeCylinder(val.transform, "Antenna R", new Vector3(0.16f, 0.42f, 0f), new Vector3(0.03f, 0.12f, 0.03f), CaseGrey); MakeSphere(val.transform, "Antenna Tip L", new Vector3(-0.16f, 0.55f, 0f), Vector3.one * 0.07f, CaseGrey); MakeSphere(val.transform, "Antenna Tip R", new Vector3(0.16f, 0.55f, 0f), Vector3.one * 0.07f, CaseGrey); MakeSphere(val.transform, "Light T1", new Vector3(-0.12f, -0.18f, -0.17f), Vector3.one * 0.055f, new Color(0.2f, 1f, 0.2f)); MakeSphere(val.transform, "Light T2", new Vector3(0f, -0.18f, -0.17f), Vector3.one * 0.055f, new Color(1f, 0.65f, 0f)); MakeSphere(val.transform, "Light T3", new Vector3(0.12f, -0.18f, -0.17f), Vector3.one * 0.055f, new Color(1f, 0.15f, 0.15f)); return val; } private static GameObject MakeCube(Transform parent, string name, Vector3 position, Vector3 scale, Color colour) { //IL_0004: Unknown result type (might be due to invalid IL or missing references) //IL_0005: 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) return MakePrimitive((PrimitiveType)3, parent, name, position, scale, colour); } private static GameObject MakeCylinder(Transform parent, string name, Vector3 position, Vector3 scale, Color colour) { //IL_0004: Unknown result type (might be due to invalid IL or missing references) //IL_0005: 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) return MakePrimitive((PrimitiveType)2, parent, name, position, scale, colour); } private static GameObject MakeSphere(Transform parent, string name, Vector3 position, Vector3 scale, Color colour) { //IL_0004: Unknown result type (might be due to invalid IL or missing references) //IL_0005: 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) return MakePrimitive((PrimitiveType)0, parent, name, position, scale, colour); } private static GameObject MakePrimitive(PrimitiveType type, Transform parent, string name, Vector3 position, Vector3 scale, Color colour) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0024: 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_0071: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Expected O, but got Unknown //IL_007a: Unknown result type (might be due to invalid IL or missing references) GameObject val = GameObject.CreatePrimitive(type); ((Object)val).name = name; val.transform.SetParent(parent, false); val.transform.localPosition = position; val.transform.localScale = scale; Collider component = val.GetComponent<Collider>(); if ((Object)(object)component != (Object)null) { Object.Destroy((Object)(object)component); } Renderer component2 = val.GetComponent<Renderer>(); if ((Object)(object)component2 != (Object)null) { Material val2 = new Material(Shader.Find("Standard")); val2.color = colour; component2.material = val2; } return val; } private static void MakeEmissive(GameObject part, Color colour, float strength) { //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Unknown result type (might be due to invalid IL or missing references) Renderer component = part.GetComponent<Renderer>(); if (!((Object)(object)component == (Object)null) && !((Object)(object)component.material == (Object)null)) { Material material = component.material; material.EnableKeyword("_EMISSION"); material.SetColor("_EmissionColor", colour * strength); } } } }