Decompiled source of PerfectPlacement v1.2.1

PerfectPlacement.dll

Decompiled a day ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.IO.Compression;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Serialization;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Cryptography;
using System.Security.Permissions;
using System.Text;
using BepInEx;
using BepInEx.Bootstrap;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using JetBrains.Annotations;
using Microsoft.CodeAnalysis;
using PerfectPlacement;
using PerfectPlacement.Patches;
using PerfectPlacement.Patches.Compatibility;
using PerfectPlacement.Patches.Compatibility.WardIsLove;
using PerfectPlacement.UI;
using ServerSync;
using TMPro;
using UnityEngine;
using UnityEngine.UI;

[assembly: AssemblyFileVersion("1.2.1")]
[assembly: Guid("E3FE707A-B402-4C69-8C3D-E9C0C709715D")]
[assembly: ComVisible(false)]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCopyright("Copyright ©  2023")]
[assembly: AssemblyProduct("PerfectPlacement")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyTitle("PerfectPlacement")]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: CompilationRelaxations(8)]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: AssemblyCompany("Azumatt_and_ValheimPlusDevs")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.2.1.0")]
[module: <ab043c51-b323-4fc2-8cc4-41afcefc3551>RefSafetyRules(11)]
[module: UnverifiableCode]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[<870a58b0-781a-44ea-86dc-6b25988258c3>Embedded]
	internal sealed class <870a58b0-781a-44ea-86dc-6b25988258c3>EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
	[<870a58b0-781a-44ea-86dc-6b25988258c3>Embedded]
	[CompilerGenerated]
	internal sealed class <7c9394e6-3d44-4e55-8044-ef4c85cdd883>NullableAttribute : Attribute
	{
		public readonly byte[] NullableFlags;

		public <7c9394e6-3d44-4e55-8044-ef4c85cdd883>NullableAttribute(byte P_0)
		{
			NullableFlags = new byte[1] { P_0 };
		}

		public <7c9394e6-3d44-4e55-8044-ef4c85cdd883>NullableAttribute(byte[] P_0)
		{
			NullableFlags = P_0;
		}
	}
	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)]
	[<870a58b0-781a-44ea-86dc-6b25988258c3>Embedded]
	[CompilerGenerated]
	internal sealed class <e5b64376-848c-44b5-ad84-53dd18df5967>NullableContextAttribute : Attribute
	{
		public readonly byte Flag;

		public <e5b64376-848c-44b5-ad84-53dd18df5967>NullableContextAttribute(byte P_0)
		{
			Flag = P_0;
		}
	}
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	[CompilerGenerated]
	[<870a58b0-781a-44ea-86dc-6b25988258c3>Embedded]
	internal sealed class <ab043c51-b323-4fc2-8cc4-41afcefc3551>RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public <ab043c51-b323-4fc2-8cc4-41afcefc3551>RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
[HarmonyPatch(typeof(Player))]
public class PlayerPatches
{
	[HarmonyPostfix]
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	[HarmonyPatch("SetLocalPlayer")]
	public static void AttachGizmoManager(Player __instance)
	{
		if ((Object)(object)((Component)__instance).gameObject.GetComponent<GizmoManager>() == (Object)null)
		{
			((Component)__instance).gameObject.AddComponent<GizmoManager>();
		}
	}
}
[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
public class GizmoManager : MonoBehaviour
{
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(0)]
	public enum Axis
	{
		None,
		X,
		Y,
		Z
	}

	private const string GizmoTag = "BuildGizmo";

	public static GizmoManager gizmoManager = null;

	public static Color xAxisGizmoColor = new Color(1f, 0f, 0f, 0.502f);

	public static Color yAxisGizmoColor = new Color(0f, 1f, 0f, 0.502f);

	public static Color zAxisGizmoColor = new Color(0f, 0f, 1f, 0.502f);

	private GameObject _ghost;

	private float ArcRadius = 2f;

	private const float LineLength = 2f;

	public static Vector3 CurrentAxis = Vector3.zero;

	private GameObject _lastGhost;

	private void Awake()
	{
		gizmoManager = this;
	}

	private void Update()
	{
		if (PerfectPlacementPlugin.neverShowGizmos.Value.IsOn())
		{
			ClearGizmos();
			return;
		}
		if (PerfectPlacementPlugin.onlyShowGizmosInABMOrAEM.Value.IsOn() && !ABM.IsInAbmMode() && !AEM.IsInAemMode())
		{
			ClearGizmos();
			return;
		}
		bool num = PerfectPlacementPlugin.showArcs.Value.IsOn();
		bool flag = PerfectPlacementPlugin.showArrows.Value.IsOn();
		if (!num && !flag)
		{
			ClearGizmos();
			return;
		}
		_ghost = Player.m_localPlayer?.m_placementGhost ?? (AEM.IsInAemMode() ? AEM.HitObject : null);
		if ((Object)(object)_ghost == (Object)null)
		{
			ClearGizmos();
			return;
		}
		if ((Object)(object)_ghost != (Object)(object)_lastGhost)
		{
			_lastGhost = _ghost;
			CalculateGizmoRadius();
		}
		RenderGizmos();
	}

	private void OnRenderObject()
	{
		//IL_002b: Unknown result type (might be due to invalid IL or missing references)
		if ((Object)(object)_ghost != (Object)null && PerfectPlacementPlugin.showArrows.Value.IsOn())
		{
			DrawLinesToArrows(_ghost.transform.rotation);
		}
	}

	private void RenderGizmos()
	{
		//IL_0012: Unknown result type (might be due to invalid IL or missing references)
		//IL_0017: 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_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_0073: Unknown result type (might be due to invalid IL or missing references)
		//IL_0112: Unknown result type (might be due to invalid IL or missing references)
		//IL_011c: Unknown result type (might be due to invalid IL or missing references)
		//IL_0121: Unknown result type (might be due to invalid IL or missing references)
		//IL_0093: Unknown result type (might be due to invalid IL or missing references)
		//IL_00a3: 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_00ad: Unknown result type (might be due to invalid IL or missing references)
		//IL_0137: 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_0146: Unknown result type (might be due to invalid IL or missing references)
		//IL_00d1: Unknown result type (might be due to invalid IL or missing references)
		//IL_00e1: Unknown result type (might be due to invalid IL or missing references)
		//IL_00e6: Unknown result type (might be due to invalid IL or missing references)
		//IL_00eb: 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)
		//IL_016a: Unknown result type (might be due to invalid IL or missing references)
		//IL_016f: Unknown result type (might be due to invalid IL or missing references)
		//IL_0185: Unknown result type (might be due to invalid IL or missing references)
		Axis activeAxis = GetActiveAxis();
		Quaternion rotation = _ghost.transform.rotation;
		float value = PerfectPlacementPlugin.defaultArcScale.Value;
		float value2 = PerfectPlacementPlugin.activeArcScale.Value;
		float value3 = PerfectPlacementPlugin.inactiveArcScale.Value;
		if (PerfectPlacementPlugin.showArcs.Value.IsOn())
		{
			GizmoMeshCache.DrawArc(_ghost.transform.position, ArcRadius, PerfectPlacementPlugin.xAxisGizmoColor.Value, Vector3.right, rotation, activeAxis switch
			{
				Axis.None => value, 
				Axis.X => value2, 
				_ => value3, 
			});
			GizmoMeshCache.DrawArc(_ghost.transform.position, ArcRadius, PerfectPlacementPlugin.yAxisGizmoColor.Value, Vector3.up, Quaternion.identity, activeAxis switch
			{
				Axis.None => value, 
				Axis.Y => value2, 
				_ => value3, 
			});
			GizmoMeshCache.DrawArc(_ghost.transform.position, ArcRadius, PerfectPlacementPlugin.zAxisGizmoColor.Value, Vector3.forward, rotation, activeAxis switch
			{
				Axis.None => value, 
				Axis.Z => value2, 
				_ => value3, 
			});
		}
		if (PerfectPlacementPlugin.showArrows.Value.IsOn())
		{
			DrawArrowForAxis(Vector3.right, PerfectPlacementPlugin.xAxisGizmoColor.Value, rotation, activeAxis switch
			{
				Axis.None => value, 
				Axis.X => value2, 
				_ => value3, 
			});
			DrawArrowForAxis(Vector3.up, PerfectPlacementPlugin.yAxisGizmoColor.Value, Quaternion.identity, activeAxis switch
			{
				Axis.None => value, 
				Axis.Y => value2, 
				_ => value3, 
			});
			DrawArrowForAxis(Vector3.forward, PerfectPlacementPlugin.zAxisGizmoColor.Value, rotation, activeAxis switch
			{
				Axis.None => value, 
				Axis.Z => value2, 
				_ => value3, 
			});
			DrawLinesToArrows(rotation);
		}
	}

	private Axis GetActiveAxis()
	{
		//IL_0000: 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_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_0026: Unknown result type (might be due to invalid IL or missing references)
		//IL_002b: Unknown result type (might be due to invalid IL or missing references)
		if (CurrentAxis == Vector3.right)
		{
			return Axis.X;
		}
		if (CurrentAxis == Vector3.up)
		{
			return Axis.Y;
		}
		if (!(CurrentAxis == Vector3.forward))
		{
			return Axis.None;
		}
		return Axis.Z;
	}

	public void SetActiveAxis(Axis activeAxis)
	{
		//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_001e: Unknown result type (might be due to invalid IL or missing references)
		//IL_0023: 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_002b: 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_0035: Unknown result type (might be due to invalid IL or missing references)
		//IL_002e: 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)
		CurrentAxis = (Vector3)(activeAxis switch
		{
			Axis.X => Vector3.right, 
			Axis.Y => Vector3.up, 
			Axis.Z => Vector3.forward, 
			_ => Vector3.zero, 
		});
	}

	private void CalculateGizmoRadius()
	{
		//IL_001e: Unknown result type (might be due to invalid IL or missing references)
		//IL_0023: Unknown result type (might be due to invalid IL or missing references)
		//IL_003c: 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)
		//IL_0058: Unknown result type (might be due to invalid IL or missing references)
		Renderer[] componentsInChildren = _ghost.GetComponentsInChildren<Renderer>();
		if (componentsInChildren.Length != 0)
		{
			Bounds val = default(Bounds);
			((Bounds)(ref val))..ctor(_ghost.transform.position, Vector3.zero);
			Renderer[] array = componentsInChildren;
			foreach (Renderer val2 in array)
			{
				((Bounds)(ref val)).Encapsulate(val2.bounds);
			}
			Vector3 extents = ((Bounds)(ref val)).extents;
			ArcRadius = ((Vector3)(ref extents)).magnitude + PerfectPlacementPlugin.extraRadiusMargin.Value;
		}
	}

	private void DrawArrowForAxis(Vector3 direction, Color color, Quaternion objectRotation, float scale)
	{
		//IL_002c: 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_0032: 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_0034: 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_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_0045: Unknown result type (might be due to invalid IL or missing references)
		//IL_0051: Unknown result type (might be due to invalid IL or missing references)
		//IL_0056: 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_0064: 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_0073: Unknown result type (might be due to invalid IL or missing references)
		//IL_0074: Unknown result type (might be due to invalid IL or missing references)
		//IL_0075: Unknown result type (might be due to invalid IL or missing references)
		//IL_007b: Unknown result type (might be due to invalid IL or missing references)
		//IL_007c: 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_0083: Unknown result type (might be due to invalid IL or missing references)
		float value = PerfectPlacementPlugin.arrowLineLength.Value;
		float value2 = PerfectPlacementPlugin.arrowTipLength.Value;
		_ = PerfectPlacementPlugin.arrowTipScale.Value;
		Vector3 position = _ghost.transform.position;
		Vector3 end = position + objectRotation * (direction * value);
		Vector3 position2 = _ghost.transform.position + objectRotation * (direction * (ArcRadius + 0.5f));
		GizmoMeshCache.DrawLine(position, end, color);
		GizmoMeshCache.DrawArrow(position2, objectRotation * direction, value2, color, scale);
	}

	private void DrawLinesToArrows(Quaternion objectRotation)
	{
		//IL_000b: 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_0011: Unknown result type (might be due to invalid IL or missing references)
		//IL_0012: 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_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_002e: Unknown result type (might be due to invalid IL or missing references)
		//IL_0038: Unknown result type (might be due to invalid IL or missing references)
		//IL_0042: Unknown result type (might be due to invalid IL or missing references)
		//IL_0043: 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)
		//IL_0055: Unknown result type (might be due to invalid IL or missing references)
		//IL_005a: 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_006e: Unknown result type (might be due to invalid IL or missing references)
		//IL_006f: 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_0081: Unknown result type (might be due to invalid IL or missing references)
		//IL_0086: Unknown result type (might be due to invalid IL or missing references)
		//IL_008b: 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)
		Vector3 position = _ghost.transform.position;
		GizmoMeshCache.DrawLine(position, position + objectRotation * (Vector3.right * (ArcRadius + 0.5f)), PerfectPlacementPlugin.xAxisGizmoColor.Value);
		GizmoMeshCache.DrawLine(position, position + Vector3.up * (ArcRadius + 0.5f), PerfectPlacementPlugin.yAxisGizmoColor.Value);
		GizmoMeshCache.DrawLine(position, position + objectRotation * (Vector3.forward * (ArcRadius + 0.5f)), PerfectPlacementPlugin.zAxisGizmoColor.Value);
	}

	private void ClearGizmos()
	{
		//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)
		_ghost = null;
		_lastGhost = null;
		CurrentAxis = Vector3.zero;
	}
}
[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
public static class GizmoMeshCache
{
	private static readonly Dictionary<Tuple<Color, Vector3, float>, Mesh> ArcMeshes = new Dictionary<Tuple<Color, Vector3, float>, Mesh>();

	private static readonly Dictionary<Color, Mesh> ArrowMeshes = new Dictionary<Color, Mesh>();

	public static void DrawArc(Vector3 position, float radius, Color color, Vector3 axis, Quaternion objectRotation, float scale)
	{
		//IL_0000: Unknown result type (might be due to invalid IL or missing references)
		//IL_0001: 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_000d: 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_0017: 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_0043: 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_004b: Unknown result type (might be due to invalid IL or missing references)
		//IL_004c: 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)
		//IL_0058: Unknown result type (might be due to invalid IL or missing references)
		//IL_005d: Unknown result type (might be due to invalid IL or missing references)
		//IL_0060: Unknown result type (might be due to invalid IL or missing references)
		//IL_0030: Unknown result type (might be due to invalid IL or missing references)
		Quaternion val = ((axis == Vector3.up) ? Quaternion.identity : objectRotation);
		Tuple<Color, Vector3, float> key = Tuple.Create<Color, Vector3, float>(color, axis, radius);
		if (!ArcMeshes.TryGetValue(key, out var value))
		{
			value = CreateArcMesh(radius, axis);
			ArcMeshes[key] = value;
		}
		Material material = GetMaterial(color);
		Matrix4x4 val2 = Matrix4x4.TRS(position, val, Vector3.one * scale);
		Graphics.DrawMesh(value, val2, material, 0);
	}

	private static Mesh CreateArcMesh(float radius, Vector3 axis)
	{
		//IL_0000: Unknown result type (might be due to invalid IL or missing references)
		//IL_0006: Expected O, but got Unknown
		//IL_0019: Unknown result type (might be due to invalid IL or missing references)
		//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_005d: 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)
		//IL_0060: Unknown result type (might be due to invalid IL or missing references)
		//IL_0065: Unknown result type (might be due to invalid IL or missing references)
		Mesh val = new Mesh();
		Vector3[] array = (Vector3[])(object)new Vector3[64];
		int[] array2 = new int[128];
		Quaternion val2 = Quaternion.LookRotation(axis);
		Vector3 val3 = default(Vector3);
		for (int i = 0; i < 64; i++)
		{
			float num = (float)i * (float)Math.PI * 2f / 63f;
			((Vector3)(ref val3))..ctor(radius * Mathf.Cos(num), radius * Mathf.Sin(num), 0f);
			array[i] = val2 * val3;
			if (i < 63)
			{
				array2[i * 2] = i;
				array2[i * 2 + 1] = i + 1;
			}
		}
		val.vertices = array;
		val.SetIndices(array2, (MeshTopology)3, 0);
		return val;
	}

	public static void DrawArrow(Vector3 position, Vector3 direction, float length, Color color, float scale)
	{
		//IL_0005: 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_0022: 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_003b: Unknown result type (might be due to invalid IL or missing references)
		//IL_003c: Unknown result type (might be due to invalid IL or missing references)
		//IL_003d: 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_0045: Unknown result type (might be due to invalid IL or missing references)
		//IL_004b: Unknown result type (might be due to invalid IL or missing references)
		//IL_0050: Unknown result type (might be due to invalid IL or missing references)
		//IL_0051: 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_005a: 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_0061: Unknown result type (might be due to invalid IL or missing references)
		//IL_0068: 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_0072: Unknown result type (might be due to invalid IL or missing references)
		//IL_0075: Unknown result type (might be due to invalid IL or missing references)
		//IL_001a: Unknown result type (might be due to invalid IL or missing references)
		if (!ArrowMeshes.TryGetValue(color, out var value))
		{
			value = CreateArrowMesh();
			ArrowMeshes[color] = value;
		}
		Quaternion val = Quaternion.LookRotation(direction);
		Quaternion val2 = Quaternion.Euler(90f, 0f, 0f);
		Quaternion val3 = val * val2;
		Vector3 val4 = ((Vector3)(ref direction)).normalized * length;
		Material material = GetMaterial(color);
		Matrix4x4 val5 = Matrix4x4.TRS(position + val4, val3, Vector3.one * scale);
		Graphics.DrawMesh(value, val5, material, 0);
	}

	private static Mesh CreateArrowMesh()
	{
		//IL_0000: Unknown result type (might be due to invalid IL or missing references)
		//IL_0006: Expected O, but got Unknown
		//IL_000c: 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)
		Mesh val = new Mesh();
		List<Vector3> list = new List<Vector3> { Vector3.zero };
		List<int> list2 = new List<int>();
		for (int i = 0; i <= 16; i++)
		{
			float num = (float)i * (float)Math.PI * 2f / 16f;
			list.Add(new Vector3(0.1f * Mathf.Cos(num), -0.2f, 0.1f * Mathf.Sin(num)));
			if (i > 0)
			{
				list2.Add(0);
				list2.Add(i);
				list2.Add(i + 1);
			}
		}
		val.vertices = list.ToArray();
		val.triangles = list2.ToArray();
		val.RecalculateNormals();
		return val;
	}

	public static void DrawLine(Vector3 start, Vector3 end, Color color)
	{
		//IL_0000: 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_001e: 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)
		Material material = GetMaterial(color);
		GL.PushMatrix();
		material.SetPass(0);
		GL.Begin(1);
		GL.Color(color);
		GL.Vertex(start);
		GL.Vertex(end);
		GL.End();
		GL.PopMatrix();
	}

	private static Material GetMaterial(Color color)
	{
		//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_0017: Expected O, but got Unknown
		return new Material(Shader.Find("Sprites/Default"))
		{
			color = color
		};
	}
}
namespace AllManagersModTemplate
{
	[HarmonyPatch(typeof(ZNet), "OnNewConnection")]
	public static class RegisterAndCheckVersion
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Prefix(ZNetPeer peer, ref ZNet __instance)
		{
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0040: Expected O, but got Unknown
			PerfectPlacementPlugin.PerfectPlacementLogger.LogDebug((object)"Registering version RPC handler");
			peer.m_rpc.Register<ZPackage>("PerfectPlacement_VersionCheck", (Action<ZRpc, ZPackage>)RpcHandlers.RPC_AllManagersModTemplate_Version);
			PerfectPlacementPlugin.PerfectPlacementLogger.LogDebug((object)"Invoking version check");
			ZPackage val = new ZPackage();
			val.Write("1.2.1");
			val.Write(RpcHandlers.ComputeHashForMod().Replace("-", ""));
			peer.m_rpc.Invoke("PerfectPlacement_VersionCheck", new object[1] { val });
		}
	}
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
	[HarmonyPatch(typeof(ZNet), "RPC_PeerInfo")]
	public static class VerifyClient
	{
		private static bool Prefix(ZRpc rpc, ZPackage pkg, ref ZNet __instance)
		{
			if (!__instance.IsServer() || RpcHandlers.ValidatedPeers.Contains(rpc))
			{
				return true;
			}
			PerfectPlacementPlugin.PerfectPlacementLogger.LogWarning((object)("Peer (" + rpc.m_socket.GetHostName() + ") never sent version or couldn't due to previous disconnect, disconnecting"));
			rpc.Invoke("Error", new object[1] { 3 });
			return false;
		}

		private static void Postfix(ZNet __instance)
		{
			//IL_001c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0022: Expected O, but got Unknown
			ZRoutedRpc.instance.InvokeRoutedRPC(ZRoutedRpc.instance.GetServerPeerID(), "PerfectPlacementRequestAdminSync", new object[1] { (object)new ZPackage() });
		}
	}
	[HarmonyPatch(typeof(FejdStartup), "ShowConnectError")]
	public class ShowConnectionError
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Postfix(FejdStartup __instance)
		{
			if (__instance.m_connectionFailedPanel.activeSelf)
			{
				TMP_Text connectionFailedError = __instance.m_connectionFailedError;
				connectionFailedError.text = connectionFailedError.text + "\n" + PerfectPlacementPlugin.ConnectionError;
			}
		}
	}
	[HarmonyPatch(typeof(ZNet), "Disconnect")]
	public static class RemoveDisconnectedPeerFromVerified
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Prefix(ZNetPeer peer, ref ZNet __instance)
		{
			if (__instance.IsServer())
			{
				PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)("Peer (" + peer.m_rpc.m_socket.GetHostName() + ") disconnected, removing from validated list"));
				RpcHandlers.ValidatedPeers.Remove(peer.m_rpc);
			}
		}
	}
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
	public static class RpcHandlers
	{
		public static readonly List<ZRpc> ValidatedPeers = new List<ZRpc>();

		public static void RPC_AllManagersModTemplate_Version(ZRpc rpc, ZPackage pkg)
		{
			string text = pkg.ReadString();
			string text2 = pkg.ReadString();
			string text3 = ComputeHashForMod().Replace("-", "");
			PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)("Version check, local: 1.2.1,  remote: " + text));
			if (text2 != text3 || text != "1.2.1")
			{
				PerfectPlacementPlugin.ConnectionError = "PerfectPlacement Installed: 1.2.1 " + text3 + "\n Needed: " + text + " " + text2;
				if (ZNet.instance.IsServer())
				{
					PerfectPlacementPlugin.PerfectPlacementLogger.LogWarning((object)("Peer (" + rpc.m_socket.GetHostName() + ") has incompatible version, disconnecting..."));
					rpc.Invoke("Error", new object[1] { 3 });
				}
			}
			else if (!ZNet.instance.IsServer())
			{
				PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)"Received same version from server!");
			}
			else
			{
				PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)("Adding peer (" + rpc.m_socket.GetHostName() + ") to validated list"));
				ValidatedPeers.Add(rpc);
			}
		}

		public static string ComputeHashForMod()
		{
			using SHA256 sHA = SHA256.Create();
			byte[] array = sHA.ComputeHash(File.ReadAllBytes(Assembly.GetExecutingAssembly().Location));
			StringBuilder stringBuilder = new StringBuilder();
			byte[] array2 = array;
			foreach (byte b in array2)
			{
				stringBuilder.Append(b.ToString("X2"));
			}
			return stringBuilder.ToString();
		}
	}
}
namespace PerfectPlacement
{
	[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	[BepInPlugin("Azumatt_and_ValheimPlusDevs.PerfectPlacement", "PerfectPlacement", "1.2.1")]
	public class PerfectPlacementPlugin : BaseUnityPlugin
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(0)]
		public enum Toggle
		{
			On = 1,
			Off = 0
		}

		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(0)]
		internal class PlayerData
		{
			public Vector3 PlaceRotation = Vector3.zero;

			public bool Opposite;

			[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(1)]
			public Piece LastPiece;

			public KeyCode LastKeyCode;
		}

		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(0)]
		private class ConfigurationManagerAttributes
		{
			[UsedImplicitly]
			public int? Order;

			[UsedImplicitly]
			public bool? Browsable;

			[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(2)]
			[UsedImplicitly]
			public string Category;

			[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(new byte[] { 2, 1 })]
			[UsedImplicitly]
			public Action<ConfigEntryBase> CustomDrawer;
		}

		internal const string ModName = "PerfectPlacement";

		internal const string ModVersion = "1.2.1";

		internal const string Author = "Azumatt_and_ValheimPlusDevs";

		private const string ModGUID = "Azumatt_and_ValheimPlusDevs.PerfectPlacement";

		private static string ConfigFileName = "Azumatt_and_ValheimPlusDevs.PerfectPlacement.cfg";

		private static string ConfigFileFullPath;

		internal static string ConnectionError;

		internal readonly Harmony _harmony = new Harmony("Azumatt_and_ValheimPlusDevs.PerfectPlacement");

		public static readonly ManualLogSource PerfectPlacementLogger;

		private static readonly ConfigSync ConfigSync;

		internal static PerfectPlacementPlugin Instance;

		internal static readonly Dictionary<Player, PlayerData> PlayersData;

		private static ConfigEntry<Toggle> _serverConfigLocked;

		internal static ConfigEntry<Toggle> fpmIsEnabled;

		internal static ConfigEntry<KeyCode> fpmrotateY;

		internal static ConfigEntry<KeyCode> fpmrotateX;

		internal static ConfigEntry<KeyCode> fpmrotateZ;

		internal static ConfigEntry<KeyCode> fpmcopyRotationParallel;

		internal static ConfigEntry<KeyCode> fpmcopyRotationPerpendicular;

		internal static ConfigEntry<Toggle> abmIsEnabled;

		internal static ConfigEntry<KeyCode> abmenterAdvancedBuildingMode;

		internal static ConfigEntry<KeyCode> abmresetAdvancedBuildingMode;

		internal static ConfigEntry<KeyCode> abmexitAdvancedBuildingMode;

		internal static ConfigEntry<KeyCode> abmcopyObjectRotation;

		internal static ConfigEntry<KeyCode> abmpasteObjectRotation;

		internal static ConfigEntry<KeyCode> abmincreaseScrollSpeed;

		internal static ConfigEntry<KeyCode> abmdecreaseScrollSpeed;

		internal static ConfigEntry<Toggle> aemIsEnabled;

		internal static ConfigEntry<KeyCode> aementerAdvancedEditingMode;

		internal static ConfigEntry<KeyCode> aemresetAdvancedEditingMode;

		internal static ConfigEntry<KeyCode> aemabortAndExitAdvancedEditingMode;

		internal static ConfigEntry<KeyCode> aemconfirmPlacementOfAdvancedEditingMode;

		internal static ConfigEntry<KeyCode> aemcopyObjectRotation;

		internal static ConfigEntry<KeyCode> aempasteObjectRotation;

		internal static ConfigEntry<KeyCode> aemincreaseScrollSpeed;

		internal static ConfigEntry<KeyCode> aemdecreaseScrollSpeed;

		internal static ConfigEntry<Toggle> gridAlignmentEnabled;

		internal static ConfigEntry<KeyCode> alignToGrid;

		internal static ConfigEntry<KeyCode> alignToggle;

		internal static ConfigEntry<KeyCode> changeDefaultAlignment;

		public static ConfigEntry<Toggle> onlyShowGizmosInABMOrAEM;

		public static ConfigEntry<Toggle> neverShowGizmos;

		public static ConfigEntry<float> defaultArcScale;

		public static ConfigEntry<float> activeArcScale;

		public static ConfigEntry<float> inactiveArcScale;

		public static ConfigEntry<float> extraRadiusMargin;

		public static ConfigEntry<float> arrowLineLength;

		public static ConfigEntry<float> arrowTipLength;

		public static ConfigEntry<float> arrowTipScale;

		public static ConfigEntry<Color> xAxisGizmoColor;

		public static ConfigEntry<Color> yAxisGizmoColor;

		public static ConfigEntry<Color> zAxisGizmoColor;

		public static ConfigEntry<Toggle> showArrows;

		public static ConfigEntry<Toggle> showArcs;

		public void Awake()
		{
			//IL_0032: Unknown result type (might be due to invalid IL or missing references)
			//IL_003d: Expected O, but got Unknown
			//IL_007e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Expected O, but got Unknown
			//IL_014e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0159: Expected O, but got Unknown
			//IL_026a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0275: Expected O, but got Unknown
			//IL_03a6: Unknown result type (might be due to invalid IL or missing references)
			//IL_03b1: Expected O, but got Unknown
			//IL_0443: Unknown result type (might be due to invalid IL or missing references)
			//IL_044e: Expected O, but got Unknown
			//IL_0480: Unknown result type (might be due to invalid IL or missing references)
			//IL_048b: Expected O, but got Unknown
			//IL_04bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_04c8: Expected O, but got Unknown
			//IL_04fa: Unknown result type (might be due to invalid IL or missing references)
			//IL_0505: Expected O, but got Unknown
			//IL_053b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0546: Expected O, but got Unknown
			//IL_057c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0587: Expected O, but got Unknown
			//IL_05bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_05c8: Expected O, but got Unknown
			//IL_05fd: Unknown result type (might be due to invalid IL or missing references)
			//IL_0608: Expected O, but got Unknown
			//IL_063d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0648: Expected O, but got Unknown
			//IL_067d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0688: Expected O, but got Unknown
			//IL_06bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_06c8: Expected O, but got Unknown
			//IL_06ec: Unknown result type (might be due to invalid IL or missing references)
			//IL_0711: Unknown result type (might be due to invalid IL or missing references)
			//IL_071c: Expected O, but got Unknown
			//IL_0740: Unknown result type (might be due to invalid IL or missing references)
			//IL_0765: Unknown result type (might be due to invalid IL or missing references)
			//IL_0770: Expected O, but got Unknown
			//IL_0794: Unknown result type (might be due to invalid IL or missing references)
			//IL_07b9: Unknown result type (might be due to invalid IL or missing references)
			//IL_07c4: Expected O, but got Unknown
			Instance = this;
			_serverConfigLocked = config("1 - General", "Lock Configuration", Toggle.On, new ConfigDescription("If on, the configuration is locked and can be changed by server admins only.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 5
				}
			}));
			ConfigSync.AddLockingConfigEntry<Toggle>(_serverConfigLocked);
			fpmIsEnabled = config("1 - General", "Enable Free Placement Rotation", Toggle.On, new ConfigDescription("If on, Free Placement Rotation is enabled. Everything in section 2 will be affected.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 1
				}
			}));
			fpmrotateY = config<KeyCode>("2 - Free Placement Rotation", "Rotate Y", (KeyCode)308, "The key to rotate the object you are placing on the Y axis, Rotates placement marker by 1 degree with keep ability to attach to nearly pieces.", synchronizedSetting: false);
			fpmrotateX = config<KeyCode>("2 - Free Placement Rotation", "Rotate X", (KeyCode)99, "The key to rotate the object you are placing on the X axis, Rotates placement marker by 1 degree with keep ability to attach to nearly pieces.", synchronizedSetting: false);
			fpmrotateZ = config<KeyCode>("2 - Free Placement Rotation", "Rotate Z", (KeyCode)118, "The key to rotate the object you are placing on the Z axis, Rotates placement marker by 1 degree with keep ability to attach to nearly pieces.", synchronizedSetting: false);
			fpmcopyRotationParallel = config<KeyCode>("2 - Free Placement Rotation", "Copy Rotation Parallel", (KeyCode)102, "Copy rotation of placement marker from target piece in front of you.", synchronizedSetting: false);
			fpmcopyRotationPerpendicular = config<KeyCode>("2 - Free Placement Rotation", "Copy Rotation Perpendicular", (KeyCode)103, "Set rotation to be perpendicular to piece in front of you.", synchronizedSetting: false);
			abmIsEnabled = config("1 - General", "Enable Advanced Building Mode", Toggle.On, new ConfigDescription("If on, Advanced Building Mode is enabled. Everything in section 3 will be affected.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 2
				}
			}));
			abmenterAdvancedBuildingMode = config<KeyCode>("3 - Advanced Building Mode", "Enter Advanced Building Mode", (KeyCode)282, "The key to enter Advanced Building Mode when building", synchronizedSetting: false);
			abmresetAdvancedBuildingMode = config<KeyCode>("3 - Advanced Building Mode", "Reset Advanced Building Mode", (KeyCode)288, "The key to reset the object to its original position and rotation", synchronizedSetting: false);
			abmexitAdvancedBuildingMode = config<KeyCode>("3 - Advanced Building Mode", "Exit Advanced Building Mode", (KeyCode)284, "The key to exit Advanced Building Mode when building", synchronizedSetting: false);
			abmcopyObjectRotation = config<KeyCode>("3 - Advanced Building Mode", "Copy Object Rotation", (KeyCode)263, "Copy the object rotation of the currently selected object in ABM", synchronizedSetting: false);
			abmpasteObjectRotation = config<KeyCode>("3 - Advanced Building Mode", "Paste Object Rotation", (KeyCode)264, "Apply the copied object rotation to the currently selected object in ABM", synchronizedSetting: false);
			abmincreaseScrollSpeed = config<KeyCode>("3 - Advanced Building Mode", "Increase Scroll Speed", (KeyCode)270, "Increases the amount an object rotates and moves. Holding Shift will increase in increments of 10 instead of 1.", synchronizedSetting: false);
			abmdecreaseScrollSpeed = config<KeyCode>("3 - Advanced Building Mode", "Decrease Scroll Speed", (KeyCode)269, "Decreases the amount an object rotates and moves. Holding Shift will decrease in increments of 10 instead of 1.", synchronizedSetting: false);
			aemIsEnabled = config("1 - General", "Enable Advanced Editing Mode", Toggle.On, new ConfigDescription("If on, Advanced Editing Mode is enabled. Everything in section 4 will be affected.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 3
				}
			}));
			aementerAdvancedEditingMode = config<KeyCode>("4 - Advanced Editing Mode", "Enter Advanced Editing Mode", (KeyCode)256, "The key to enter Advanced Editing Mode", synchronizedSetting: false);
			aemresetAdvancedEditingMode = config<KeyCode>("4 - Advanced Editing Mode", "Reset Advanced Editing Mode", (KeyCode)288, "The key to reset the object to its original position and rotation", synchronizedSetting: false);
			aemabortAndExitAdvancedEditingMode = config<KeyCode>("4 - Advanced Editing Mode", "Abort and Exit Advanced Editing Mode", (KeyCode)289, "The key to abort and exit Advanced Editing Mode and reset the object", synchronizedSetting: false);
			aemconfirmPlacementOfAdvancedEditingMode = config<KeyCode>("4 - Advanced Editing Mode", "Confirm Placement of Advanced Editing Mode", (KeyCode)271, "The key to confirm the placement of the object and place it", synchronizedSetting: false);
			aemcopyObjectRotation = config<KeyCode>("4 - Advanced Editing Mode", "Copy Object Rotation", (KeyCode)263, "The key to copy the object rotation of the currently selected object in AEM", synchronizedSetting: false);
			aempasteObjectRotation = config<KeyCode>("4 - Advanced Editing Mode", "Paste Object Rotation", (KeyCode)264, "The key to apply the copied object rotation to the currently selected object in AEM", synchronizedSetting: false);
			aemincreaseScrollSpeed = config<KeyCode>("4 - Advanced Editing Mode", "Increase Scroll Speed", (KeyCode)270, "The key to increase the scroll speed. Increases the amount an object rotates and moves. Holding Shift will increase in increments of 10 instead of 1.", synchronizedSetting: false);
			aemdecreaseScrollSpeed = config<KeyCode>("4 - Advanced Editing Mode", "Decrease Scroll Speed", (KeyCode)269, "The key to decrease the scroll speed. Decreases the amount an object rotates and moves. Holding Shift will increase in increments of 10 instead of 1.", synchronizedSetting: false);
			gridAlignmentEnabled = config("1 - General", "Enable Grid Alignment", Toggle.Off, new ConfigDescription("If off, Grid Alignment is disabled overall, all code for it will be skipped. Everything in section 5 will be affected.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 4
				}
			}));
			alignToGrid = config<KeyCode>("5 - Grid Alignment", "Align to Grid", (KeyCode)308, "The key to enable grid alignment while building", synchronizedSetting: false);
			alignToggle = config<KeyCode>("5 - Grid Alignment", "Align Toggle", (KeyCode)288, "The key to toggle grid alignment while building", synchronizedSetting: false);
			changeDefaultAlignment = config<KeyCode>("5 - Grid Alignment", "Change Default Alignment", (KeyCode)287, "The key to change the default alignment", synchronizedSetting: false);
			onlyShowGizmosInABMOrAEM = config("6 - Gizmos", "Show Gizmos only in AEM or ABM", Toggle.On, new ConfigDescription("If off, anytime you're about to build something, the gizmo's will show. If on, the gizmos will only show when in ABM or AEM mode.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 15
				}
			}), synchronizedSetting: false);
			neverShowGizmos = config("6 - Gizmos", "Never Show Gizmos", Toggle.Off, new ConfigDescription("If off, the gizmos will show when you have specified based on configurations. If on, this overrides all configurations about showing, and makes the gizmos never show at all.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 14
				}
			}), synchronizedSetting: false);
			showArcs = config("6 - Gizmos", "Show Rotation Arcs", Toggle.On, new ConfigDescription("If enabled, rotation arcs around the gizmo will be displayed.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 13
				}
			}), synchronizedSetting: false);
			showArrows = config("6 - Gizmos", "Show Axis Arrows", Toggle.On, new ConfigDescription("If enabled, arrows pointing along each axis will be displayed.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 12
				}
			}), synchronizedSetting: false);
			defaultArcScale = config("6 - Gizmos", "Default Arc Scale", 1f, new ConfigDescription("Scale factor for arcs by default.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 11
				}
			}), synchronizedSetting: false);
			activeArcScale = config("6 - Gizmos", "Active Arc Scale", 1.2f, new ConfigDescription("Scale factor for arcs when an axis is active.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 10
				}
			}), synchronizedSetting: false);
			inactiveArcScale = config("6 - Gizmos", "Inactive Arc Scale", 0.8f, new ConfigDescription("Scale factor for arcs when an axis is inactive.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 9
				}
			}), synchronizedSetting: false);
			extraRadiusMargin = config("6 - Gizmos", "Arc Radius Margin", 0.5f, new ConfigDescription("Additional margin added to the calculated arc radius for better visibility.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 8
				}
			}), synchronizedSetting: false);
			arrowLineLength = config("6 - Gizmos", "Arrow Line Length", 2f, new ConfigDescription("Length of the line before the arrow tip.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 7
				}
			}), synchronizedSetting: false);
			arrowTipLength = config("6 - Gizmos", "Arrow Tip Length", 0.85f, new ConfigDescription("Length of the arrow tip portion.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 6
				}
			}), synchronizedSetting: false);
			arrowTipScale = config("6 - Gizmos", "Arrow Tip Scale", 0.2f, new ConfigDescription("Scale (width) factor of the arrow tip.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 5
				}
			}), synchronizedSetting: false);
			xAxisGizmoColor = config<Color>("6 - Gizmos", "Gizmo X Axis Color", new Color(1f, 0f, 0f, 0.502f), new ConfigDescription("Color for the X Axis gizmos.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 3
				}
			}), synchronizedSetting: false);
			yAxisGizmoColor = config<Color>("6 - Gizmos", "Gizmo Y Axis Color", new Color(0f, 1f, 0f, 0.502f), new ConfigDescription("Color for the Y Axis gizmos.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 2
				}
			}), synchronizedSetting: false);
			zAxisGizmoColor = config<Color>("6 - Gizmos", "Gizmo Z Axis Color", new Color(0f, 0f, 1f, 0.502f), new ConfigDescription("Color for the Z Axis gizmos.", (AcceptableValueBase)null, new object[1]
			{
				new ConfigurationManagerAttributes
				{
					Order = 1
				}
			}), synchronizedSetting: false);
			Assembly executingAssembly = Assembly.GetExecutingAssembly();
			_harmony.PatchAll(executingAssembly);
			SetupWatcher();
		}

		private void Start()
		{
			AutoDoc();
			FirstPersonModeCompat.Init();
		}

		internal void AutoDoc()
		{
		}

		private void OnDestroy()
		{
			((BaseUnityPlugin)this).Config.Save();
		}

		private void SetupWatcher()
		{
			FileSystemWatcher fileSystemWatcher = new FileSystemWatcher(Paths.ConfigPath, ConfigFileName);
			fileSystemWatcher.Changed += ReadConfigValues;
			fileSystemWatcher.Created += ReadConfigValues;
			fileSystemWatcher.Renamed += ReadConfigValues;
			fileSystemWatcher.IncludeSubdirectories = true;
			fileSystemWatcher.SynchronizingObject = ThreadingHelper.SynchronizingObject;
			fileSystemWatcher.EnableRaisingEvents = true;
		}

		private void ReadConfigValues(object sender, FileSystemEventArgs e)
		{
			if (!File.Exists(ConfigFileFullPath))
			{
				return;
			}
			try
			{
				PerfectPlacementLogger.LogDebug((object)"ReadConfigValues called");
				((BaseUnityPlugin)this).Config.Reload();
			}
			catch
			{
				PerfectPlacementLogger.LogError((object)("There was an issue loading your " + ConfigFileName));
				PerfectPlacementLogger.LogError((object)"Please check your config entries for spelling and format!");
			}
		}

		internal static void UpdateKeyBindings()
		{
			//IL_0077: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: 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_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bd: 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_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_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_0126: Unknown result type (might be due to invalid IL or missing references)
			//IL_012b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0149: Unknown result type (might be due to invalid IL or missing references)
			//IL_014e: Unknown result type (might be due to invalid IL or missing references)
			//IL_04d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_04de: Unknown result type (might be due to invalid IL or missing references)
			//IL_04fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0501: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d4: Unknown result type (might be due to invalid IL or missing references)
			//IL_02d9: 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_02fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_031a: Unknown result type (might be due to invalid IL or missing references)
			//IL_031f: Unknown result type (might be due to invalid IL or missing references)
			//IL_033d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0342: Unknown result type (might be due to invalid IL or missing references)
			//IL_0360: Unknown result type (might be due to invalid IL or missing references)
			//IL_0365: Unknown result type (might be due to invalid IL or missing references)
			//IL_0383: Unknown result type (might be due to invalid IL or missing references)
			//IL_0388: 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)
			KeyCode value;
			if (ABM.IsInAbmMode())
			{
				string mode = KeyBindingOverlay.FormatBinding("orange", "Advanced Building Mode");
				Dictionary<string, string> obj = new Dictionary<string, string>
				{
					{
						"Left Alt",
						KeyBindingOverlay.FormatBinding("blue", "Rotate on Blue")
					},
					{
						"ScrollWheel",
						KeyBindingOverlay.FormatBinding("green", "Rotate on Green")
					},
					{
						"Left Ctrl",
						KeyBindingOverlay.FormatBinding("red", "Rotate on Red")
					}
				};
				value = abmenterAdvancedBuildingMode.Value;
				obj.Add("Enter Mode", ((object)(KeyCode)(ref value)).ToString());
				value = abmexitAdvancedBuildingMode.Value;
				obj.Add("Exit Mode", ((object)(KeyCode)(ref value)).ToString());
				value = abmresetAdvancedBuildingMode.Value;
				obj.Add("Reset Position/Rotation", ((object)(KeyCode)(ref value)).ToString());
				value = abmcopyObjectRotation.Value;
				obj.Add("Copy Rotation", ((object)(KeyCode)(ref value)).ToString());
				value = abmpasteObjectRotation.Value;
				obj.Add("Paste Rotation", ((object)(KeyCode)(ref value)).ToString());
				value = abmincreaseScrollSpeed.Value;
				obj.Add("Increase Speed", ((object)(KeyCode)(ref value)).ToString());
				value = abmdecreaseScrollSpeed.Value;
				obj.Add("Decrease Speed", ((object)(KeyCode)(ref value)).ToString());
				obj.Add("Move Up [" + KeyBindingOverlay.FormatBinding("green", "Green Arrow") + "]", "Ctrl + ↑");
				obj.Add("Move Down [" + KeyBindingOverlay.FormatBinding("green", "Green Arrow") + "]", "Ctrl + ↓");
				obj.Add("Move Forward [" + KeyBindingOverlay.FormatBinding("blue", "Blue Arrow") + "]", "↑");
				obj.Add("Move Backward [" + KeyBindingOverlay.FormatBinding("blue", "Blue Arrow") + "]", "↓");
				obj.Add("Move Left [" + KeyBindingOverlay.FormatBinding("red", "Red Arrow") + "]", "←");
				obj.Add("Move Right [" + KeyBindingOverlay.FormatBinding("red", "Red Arrow") + "]", "→");
				KeyBindingOverlay.UpdateBindings(mode, obj);
			}
			else if (AEM.IsInAemMode())
			{
				string mode2 = KeyBindingOverlay.FormatBinding("orange", "Advanced Editing Mode");
				Dictionary<string, string> obj2 = new Dictionary<string, string>
				{
					{
						"Left Alt",
						KeyBindingOverlay.FormatBinding("blue", "Rotate on Blue")
					},
					{
						"ScrollWheel",
						KeyBindingOverlay.FormatBinding("green", "Rotate on Green")
					},
					{
						"Left Ctrl",
						KeyBindingOverlay.FormatBinding("red", "Rotate on Red")
					}
				};
				value = aementerAdvancedEditingMode.Value;
				obj2.Add("Enter Mode", ((object)(KeyCode)(ref value)).ToString());
				value = aemabortAndExitAdvancedEditingMode.Value;
				obj2.Add("Exit Mode", ((object)(KeyCode)(ref value)).ToString());
				value = aemconfirmPlacementOfAdvancedEditingMode.Value;
				obj2.Add("Confirm Placement", ((object)(KeyCode)(ref value)).ToString());
				value = aemcopyObjectRotation.Value;
				obj2.Add("Copy Rotation", ((object)(KeyCode)(ref value)).ToString());
				value = aempasteObjectRotation.Value;
				obj2.Add("Paste Rotation", ((object)(KeyCode)(ref value)).ToString());
				value = aemincreaseScrollSpeed.Value;
				obj2.Add("Increase Speed", ((object)(KeyCode)(ref value)).ToString());
				value = aemdecreaseScrollSpeed.Value;
				obj2.Add("Decrease Speed", ((object)(KeyCode)(ref value)).ToString());
				obj2.Add("Move Up [" + KeyBindingOverlay.FormatBinding("green", "Green Arrow") + "]", "Ctrl + ↑");
				obj2.Add("Move Down [" + KeyBindingOverlay.FormatBinding("green", "Green Arrow") + "]", "Ctrl + ↓");
				obj2.Add("Move Forward [" + KeyBindingOverlay.FormatBinding("blue", "Blue Arrow") + "]", "↑");
				obj2.Add("Move Backward [" + KeyBindingOverlay.FormatBinding("blue", "Blue Arrow") + "]", "↓");
				obj2.Add("Move Left [" + KeyBindingOverlay.FormatBinding("red", "Red Arrow") + "]", "←");
				obj2.Add("Move Right [" + KeyBindingOverlay.FormatBinding("red", "Red Arrow") + "]", "→");
				KeyBindingOverlay.UpdateBindings(mode2, obj2);
			}
			else
			{
				string mode3 = KeyBindingOverlay.FormatBinding("orange", "Enter Modes");
				Dictionary<string, string> dictionary = new Dictionary<string, string>();
				value = abmenterAdvancedBuildingMode.Value;
				dictionary.Add("Enter ABM", ((object)(KeyCode)(ref value)).ToString());
				value = aementerAdvancedEditingMode.Value;
				dictionary.Add("Enter AEM \n\t[Without Hammer equipped and looking at existing build piece!]", ((object)(KeyCode)(ref value)).ToString());
				KeyBindingOverlay.UpdateBindings(mode3, dictionary);
			}
		}

		private ConfigEntry<T> config<[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(2)] T>(string group, string name, T value, ConfigDescription description, bool synchronizedSetting = true)
		{
			//IL_002a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0030: Expected O, but got Unknown
			ConfigDescription val = new ConfigDescription(description.Description + (synchronizedSetting ? " [Synced with Server]" : " [Not Synced with Server]"), description.AcceptableValues, description.Tags);
			ConfigEntry<T> val2 = ((BaseUnityPlugin)this).Config.Bind<T>(group, name, value, val);
			ConfigSync.AddConfigEntry<T>(val2).SynchronizedConfig = synchronizedSetting;
			return val2;
		}

		private ConfigEntry<T> config<[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(2)] T>(string group, string name, T value, string description, bool synchronizedSetting = true)
		{
			//IL_000c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0018: Expected O, but got Unknown
			return config(group, name, value, new ConfigDescription(description, (AcceptableValueBase)null, Array.Empty<object>()), synchronizedSetting);
		}

		static PerfectPlacementPlugin()
		{
			string configPath = Paths.ConfigPath;
			char directorySeparatorChar = Path.DirectorySeparatorChar;
			ConfigFileFullPath = configPath + directorySeparatorChar + ConfigFileName;
			ConnectionError = "";
			PerfectPlacementLogger = Logger.CreateLogSource("PerfectPlacement");
			ConfigSync = new ConfigSync("Azumatt_and_ValheimPlusDevs.PerfectPlacement")
			{
				DisplayName = "PerfectPlacement",
				CurrentVersion = "1.2.1",
				MinimumRequiredVersion = "1.2.1"
			};
			PlayersData = new Dictionary<Player, PlayerData>();
			_serverConfigLocked = null;
			fpmIsEnabled = null;
			fpmrotateY = null;
			fpmrotateX = null;
			fpmrotateZ = null;
			fpmcopyRotationParallel = null;
			fpmcopyRotationPerpendicular = null;
			abmIsEnabled = null;
			abmenterAdvancedBuildingMode = null;
			abmresetAdvancedBuildingMode = null;
			abmexitAdvancedBuildingMode = null;
			abmcopyObjectRotation = null;
			abmpasteObjectRotation = null;
			abmincreaseScrollSpeed = null;
			abmdecreaseScrollSpeed = null;
			aemIsEnabled = null;
			aementerAdvancedEditingMode = null;
			aemresetAdvancedEditingMode = null;
			aemabortAndExitAdvancedEditingMode = null;
			aemconfirmPlacementOfAdvancedEditingMode = null;
			aemcopyObjectRotation = null;
			aempasteObjectRotation = null;
			aemincreaseScrollSpeed = null;
			aemdecreaseScrollSpeed = null;
			gridAlignmentEnabled = null;
			alignToGrid = null;
			alignToggle = null;
			changeDefaultAlignment = null;
			onlyShowGizmosInABMOrAEM = null;
			neverShowGizmos = null;
			defaultArcScale = null;
			activeArcScale = null;
			inactiveArcScale = null;
			extraRadiusMargin = null;
			arrowLineLength = null;
			arrowTipLength = null;
			arrowTipScale = null;
			xAxisGizmoColor = null;
			yAxisGizmoColor = null;
			zAxisGizmoColor = null;
			showArrows = null;
			showArcs = null;
		}
	}
	public static class ToggleExtentions
	{
		public static bool IsOn(this PerfectPlacementPlugin.Toggle value)
		{
			return value == PerfectPlacementPlugin.Toggle.On;
		}

		public static bool IsOff(this PerfectPlacementPlugin.Toggle value)
		{
			return value == PerfectPlacementPlugin.Toggle.Off;
		}
	}
}
namespace PerfectPlacement.Patches
{
	public class Util
	{
		internal static Vector3 ClampAngles(Vector3 angles)
		{
			//IL_0000: 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)
			//IL_0016: 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)
			return new Vector3(ClampAngle(angles.x), ClampAngle(angles.y), ClampAngle(angles.z));
		}

		internal static int ClampPlaceRotation(int index)
		{
			if (index < 0)
			{
				index = 16 + index;
			}
			else if (index >= 16)
			{
				index -= 16;
			}
			return index;
		}

		private static float ClampAngle(float angle)
		{
			if (angle < 0f)
			{
				angle = 360f + angle;
			}
			else if (angle >= 360f)
			{
				angle -= 360f;
			}
			return angle;
		}

		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		public static Character getPlayerCharacter(Player __instance)
		{
			return (Character)(object)__instance;
		}
	}
	[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	internal class ABM
	{
		public static bool isActive;

		private static Player PlayerInstance;

		private static bool controlFlag;

		private static bool shiftFlag;

		private static bool altFlag;

		public static bool exitOnNextIteration;

		private static bool blockDefaultFunction;

		private static Piece component;

		private static Quaternion InitialRotation;

		private static Vector3 InitialPosition;

		private const float BASE_TRANSLATION_DISTANCE = 0.1f;

		private const float BASE_ROTATION_ANGLE_DEGREES = 3f;

		private static float currentModificationSpeed = 1f;

		private const float MIN_MODIFICATION_SPEED = 1f;

		private const float MAX_MODIFICATION_SPEED = 30f;

		private static Quaternion savedRotation;

		public static void Run(ref Player __instance)
		{
			//IL_0020: Unknown result type (might be due to invalid IL or missing references)
			//IL_0116: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00eb: Unknown result type (might be due to invalid IL or missing references)
			PlayerInstance = __instance;
			if (AEM.IsInAemMode())
			{
				if (IsInAbmMode())
				{
					exitMode();
				}
				return;
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.abmexitAdvancedBuildingMode.Value))
			{
				if (IsInAbmMode())
				{
					exitMode();
				}
				return;
			}
			if (exitOnNextIteration)
			{
				isActive = false;
				blockDefaultFunction = false;
				exitOnNextIteration = false;
				component = null;
			}
			if (IsInAbmMode() && (Object)(object)component == (Object)null)
			{
				exitMode();
			}
			else if ((Object)(object)selectedPrefab() == (Object)null || (Object)(object)PlayerInstance.m_placementGhost == (Object)null)
			{
				if (IsInAbmMode())
				{
					exitMode();
				}
				if (!AEM.IsInAemMode())
				{
					KeyBindingOverlay.ToggleOverlay(show: false);
				}
			}
			else if (isInBuildMode() && IsHoeOrTerrainTool(selectedPrefab()))
			{
				if (IsInAbmMode())
				{
					exitMode();
				}
			}
			else if (IsInAbmMode())
			{
				if (Vector3.Distance(((Component)PlayerInstance).transform.position, ((Component)component).transform.position) > PlayerInstance.m_maxPlaceDistance)
				{
					exitMode();
				}
				isRunning();
				listenToHotKeysAndDoWork();
			}
			else
			{
				if (Input.GetKeyDown(PerfectPlacementPlugin.abmenterAdvancedBuildingMode.Value))
				{
					startMode();
				}
				PerfectPlacementPlugin.UpdateKeyBindings();
				KeyBindingOverlay.ToggleOverlay(show: true);
			}
		}

		private static void listenToHotKeysAndDoWork()
		{
			//IL_001c: 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_0044: 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_009b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e6: 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_0149: Unknown result type (might be due to invalid IL or missing references)
			//IL_0161: Unknown result type (might be due to invalid IL or missing references)
			//IL_0175: Unknown result type (might be due to invalid IL or missing references)
			//IL_017f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0184: Unknown result type (might be due to invalid IL or missing references)
			//IL_0270: 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_029c: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a6: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ab: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f5: Unknown result type (might be due to invalid IL or missing references)
			//IL_0209: Unknown result type (might be due to invalid IL or missing references)
			//IL_0221: Unknown result type (might be due to invalid IL or missing references)
			//IL_022b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0230: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a4: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cc: Unknown result type (might be due to invalid IL or missing references)
			//IL_01da: Unknown result type (might be due to invalid IL or missing references)
			//IL_01df: 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_03b1: Unknown result type (might be due to invalid IL or missing references)
			//IL_03b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_0394: Unknown result type (might be due to invalid IL or missing references)
			//IL_039b: Unknown result type (might be due to invalid IL or missing references)
			//IL_031c: 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_0348: Unknown result type (might be due to invalid IL or missing references)
			//IL_0352: Unknown result type (might be due to invalid IL or missing references)
			//IL_0357: Unknown result type (might be due to invalid IL or missing references)
			//IL_02cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_02df: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f3: Unknown result type (might be due to invalid IL or missing references)
			//IL_0301: Unknown result type (might be due to invalid IL or missing references)
			//IL_0306: Unknown result type (might be due to invalid IL or missing references)
			//IL_0363: Unknown result type (might be due to invalid IL or missing references)
			//IL_0423: Unknown result type (might be due to invalid IL or missing references)
			//IL_042a: Unknown result type (might be due to invalid IL or missing references)
			//IL_03fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0403: Unknown result type (might be due to invalid IL or missing references)
			//IL_03df: Unknown result type (might be due to invalid IL or missing references)
			//IL_03e6: Unknown result type (might be due to invalid IL or missing references)
			//IL_044a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0451: Unknown result type (might be due to invalid IL or missing references)
			float num = 0f;
			float num2 = 0f;
			float num3 = 0f;
			PerfectPlacementPlugin.UpdateKeyBindings();
			if (Input.GetKeyDown(PerfectPlacementPlugin.abmresetAdvancedBuildingMode.Value))
			{
				resetObjectTransform();
			}
			if (Input.GetKeyDown((KeyCode)306))
			{
				controlFlag = true;
				GizmoManager.CurrentAxis = Vector3.right;
			}
			if (Input.GetKeyUp((KeyCode)306))
			{
				controlFlag = false;
				GizmoManager.CurrentAxis = Vector3.up;
			}
			if (Input.GetKeyDown((KeyCode)304))
			{
				shiftFlag = true;
			}
			if (Input.GetKeyUp((KeyCode)304))
			{
				shiftFlag = false;
			}
			if (Input.GetKeyDown((KeyCode)308))
			{
				altFlag = true;
				GizmoManager.CurrentAxis = Vector3.forward;
			}
			if (Input.GetKeyUp((KeyCode)308))
			{
				altFlag = false;
				GizmoManager.CurrentAxis = Vector3.up;
			}
			changeModificationSpeed();
			if (Input.GetKeyUp(PerfectPlacementPlugin.abmcopyObjectRotation.Value))
			{
				savedRotation = ((Component)component).transform.rotation;
			}
			if (Input.GetKeyUp(PerfectPlacementPlugin.abmpasteObjectRotation.Value))
			{
				((Component)component).transform.rotation = savedRotation;
			}
			float num4 = 3f * currentModificationSpeed;
			if (Input.GetAxis("Mouse ScrollWheel") > 0f)
			{
				Quaternion rotation;
				if (controlFlag)
				{
					num += 1f;
					rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x + num4 * num, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z);
				}
				else if (altFlag)
				{
					num2 += 1f;
					rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z + num4 * num2);
				}
				else
				{
					num3 += 1f;
					rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y + num4 * num3, ((Component)component).transform.eulerAngles.z);
				}
				((Component)component).transform.rotation = rotation;
			}
			if (Input.GetAxis("Mouse ScrollWheel") < 0f)
			{
				Quaternion rotation2;
				if (controlFlag)
				{
					num -= 1f;
					rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x + num4 * num, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z);
				}
				else if (altFlag)
				{
					num2 -= 1f;
					rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z + num4 * num2);
				}
				else
				{
					num3 -= 1f;
					rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y + num4 * num3, ((Component)component).transform.eulerAngles.z);
				}
				((Component)component).transform.rotation = rotation2;
			}
			float num5 = 0.1f * currentModificationSpeed;
			if (Input.GetKeyDown((KeyCode)273))
			{
				if (controlFlag)
				{
					((Component)component).transform.Translate(Vector3.up * num5);
				}
				else
				{
					((Component)component).transform.Translate(Vector3.forward * num5);
				}
			}
			if (Input.GetKeyDown((KeyCode)274))
			{
				if (controlFlag)
				{
					((Component)component).transform.Translate(Vector3.down * num5);
				}
				else
				{
					((Component)component).transform.Translate(Vector3.back * num5);
				}
			}
			if (Input.GetKeyDown((KeyCode)276))
			{
				((Component)component).transform.Translate(Vector3.left * num5);
			}
			if (Input.GetKeyDown((KeyCode)275))
			{
				((Component)component).transform.Translate(Vector3.right * num5);
			}
			try
			{
				isValidPlacement();
			}
			catch
			{
			}
		}

		private static void isValidPlacement()
		{
			//IL_0006: 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)
			//IL_00c3: Unknown result type (might be due to invalid IL or missing references)
			//IL_008b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0128: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_013a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0114: 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_0176: Unknown result type (might be due to invalid IL or missing references)
			//IL_018b: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01f8: Invalid comparison between Unknown and I4
			//IL_01b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_01e3: Unknown result type (might be due to invalid IL or missing references)
			PlayerInstance.m_placementStatus = (PlacementStatus)0;
			if (component.m_groundOnly || component.m_groundPiece || component.m_cultivatedGroundOnly)
			{
				PlayerInstance.m_placementMarkerInstance.SetActive(false);
			}
			StationExtension val = ((Component)component).GetComponent<StationExtension>();
			if ((Object)(object)val != (Object)null)
			{
				CraftingStation val2 = val.FindClosestStationInRange(((Component)component).transform.position);
				if (Object.op_Implicit((Object)(object)val2))
				{
					val.StartConnectionEffect(val2, 1f);
				}
				else
				{
					val.StopConnectionEffect();
					PlayerInstance.m_placementStatus = (PlacementStatus)7;
				}
				if (val.OtherExtensionInRange(component.m_spaceRequirement))
				{
					PlayerInstance.m_placementStatus = (PlacementStatus)5;
				}
			}
			if (component.m_onlyInTeleportArea && !Object.op_Implicit((Object)(object)EffectArea.IsPointInsideArea(((Component)component).transform.position, (Type)16, 0f)))
			{
				PlayerInstance.m_placementStatus = (PlacementStatus)6;
			}
			if (!component.m_allowedInDungeons && ((Component)component).transform.position.y > 3000f)
			{
				PlayerInstance.m_placementStatus = (PlacementStatus)11;
			}
			if (Location.IsInsideNoBuildLocation(PlayerInstance.m_placementGhost.transform.position))
			{
				PlayerInstance.m_placementStatus = (PlacementStatus)3;
			}
			float num = (Object.op_Implicit((Object)(object)((Component)component).GetComponent<PrivateArea>()) ? ((Component)component).GetComponent<PrivateArea>().m_radius : 0f);
			if (!PrivateArea.CheckAccess(PlayerInstance.m_placementGhost.transform.position, num, true, false))
			{
				PlayerInstance.m_placementStatus = (PlacementStatus)4;
			}
			if (WardIsLovePlugin.IsLoaded() && WardIsLovePlugin.WardEnabled().Value && WardMonoscript.CheckInWardMonoscript(PlayerInstance.m_placementGhost.transform.position) && !WardMonoscript.CheckAccess(PlayerInstance.m_placementGhost.transform.position, num))
			{
				PlayerInstance.m_placementStatus = (PlacementStatus)4;
			}
			component.SetInvalidPlacementHeightlight((int)PlayerInstance.m_placementStatus > 0);
		}

		private static void startMode()
		{
			//IL_0035: 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_0049: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Unknown result type (might be due to invalid IL or missing references)
			notifyUser("Starting ABM", (MessageType)1);
			isActive = true;
			blockDefaultFunction = true;
			component = PlayerInstance.m_placementGhost.GetComponent<Piece>();
			InitialPosition = ((Component)component).transform.position;
			InitialRotation = ((Component)component).transform.rotation;
			KeyBindingOverlay.ToggleOverlay(show: true);
		}

		private static void exitMode()
		{
			notifyUser("Exiting ABM", (MessageType)1);
			exitOnNextIteration = true;
			isActive = false;
			component = null;
			KeyBindingOverlay.ToggleOverlay(show: false);
		}

		private static bool isInBuildMode()
		{
			return ((Character)PlayerInstance).InPlaceMode();
		}

		public static bool IsInAbmMode()
		{
			return isActive;
		}

		private static void resetObjectTransform()
		{
			//IL_0023: 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)component == (Object)null))
			{
				notifyUser("Object has been reset to initial position & rotation.", (MessageType)1);
				((Component)component).transform.position = InitialPosition;
				((Component)component).transform.rotation = InitialRotation;
			}
		}

		private static GameObject selectedPrefab()
		{
			if ((Object)(object)PlayerInstance.m_buildPieces != (Object)null)
			{
				try
				{
					return PlayerInstance.m_buildPieces.GetSelectedPrefab();
				}
				catch
				{
					return null;
				}
			}
			return null;
		}

		private static bool IsHoeOrTerrainTool(GameObject selectedPrefab)
		{
			string[] source = new string[4] { "paved_road", "mud_road", "raise", "path" };
			string[] source2 = new string[2] { "cultivate", "replant" };
			if (((Object)selectedPrefab).name.ToLower().Contains("sapling"))
			{
				return true;
			}
			if (source.Contains(((Object)selectedPrefab).name) || source2.Contains(((Object)selectedPrefab).name))
			{
				return true;
			}
			return false;
		}

		private static void notifyUser(string Message, MessageType position = 1)
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			MessageHud.instance.ShowMessage(position, "ABM: " + Message, 0, (Sprite)null);
		}

		private static void isRunning()
		{
			if (IsInAbmMode())
			{
				MessageHud.instance.ShowMessage((MessageType)2, "ABM is active", 0, (Sprite)null);
			}
		}

		private static void changeModificationSpeed()
		{
			//IL_0018: 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)
			float num = 1f;
			if (shiftFlag)
			{
				num = 10f;
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.abmincreaseScrollSpeed.Value))
			{
				currentModificationSpeed = Mathf.Clamp(currentModificationSpeed + num, 1f, 30f);
				notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1);
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.abmdecreaseScrollSpeed.Value))
			{
				currentModificationSpeed = Mathf.Clamp(currentModificationSpeed - num, 1f, 30f);
				notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1);
			}
		}
	}
	[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
	[<7c9394e6-3d44-4e55-8044-ef4c85cdd883>Nullable(0)]
	internal class AEM
	{
		public static bool isActive;

		public static Player PlayerInstance;

		private static bool controlFlag;

		private static bool shiftFlag;

		private static bool altFlag;

		public static Vector3 HitPoint;

		public static Vector3 HitNormal;

		public static Piece HitPiece;

		public static GameObject HitObject;

		public static Heightmap HitHeightmap;

		private static Quaternion InitialRotation;

		private static Vector3 InitialPosition;

		private static bool isInExistence;

		private const float BASE_TRANSLATION_DISTANCE = 0.1f;

		private const float BASE_ROTATION_ANGLE_DEGREES = 3f;

		private static float currentModificationSpeed = 1f;

		private const float MIN_MODIFICATION_SPEED = 1f;

		private const float MAX_MODIFICATION_SPEED = 30f;

		private static Quaternion savedRotation;

		public static bool forceExitNextIteration;

		public static bool ExecuteRayCast(Player playerInstance)
		{
			//IL_0011: 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_0069: 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_0084: Unknown result type (might be due to invalid IL or missing references)
			//IL_0089: Unknown result type (might be due to invalid IL or missing references)
			//IL_0090: 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_00d7: Unknown result type (might be due to invalid IL or missing references)
			//IL_00dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_00eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00f0: Unknown result type (might be due to invalid IL or missing references)
			int placeRayMask = playerInstance.m_placeRayMask;
			RaycastHit val = default(RaycastHit);
			if (Physics.Raycast(((Component)GameCamera.instance).transform.position, ((Component)GameCamera.instance).transform.forward, ref val, 50f, placeRayMask) && Object.op_Implicit((Object)(object)((RaycastHit)(ref val)).collider) && !Object.op_Implicit((Object)(object)((RaycastHit)(ref val)).collider.attachedRigidbody) && Vector3.Distance(Util.getPlayerCharacter(playerInstance).m_eye.position, ((RaycastHit)(ref val)).point) < playerInstance.m_maxPlaceDistance)
			{
				HitPoint = ((RaycastHit)(ref val)).point;
				HitNormal = ((RaycastHit)(ref val)).normal;
				HitPiece = ((Component)((RaycastHit)(ref val)).collider).GetComponentInParent<Piece>();
				HitObject = ((Component)((RaycastHit)(ref val)).collider).gameObject;
				HitHeightmap = ((Component)((RaycastHit)(ref val)).collider).GetComponent<Heightmap>();
				InitialRotation = ((Component)HitPiece).transform.rotation;
				InitialPosition = ((Component)HitPiece).transform.position;
				return isValidRayCastTarget();
			}
			resetObjectInfo();
			return false;
		}

		public static bool checkForObject()
		{
			if ((Object)(object)PlayerInstance == (Object)null)
			{
				return false;
			}
			if (!ExecuteRayCast(PlayerInstance))
			{
				return false;
			}
			return true;
		}

		public static void run()
		{
			//IL_0075: 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)
			if (forceExitNextIteration)
			{
				forceExitNextIteration = false;
				resetObjectInfo();
				isActive = false;
				return;
			}
			if (isInBuildMode())
			{
				if (IsInAemMode())
				{
					exitMode();
					resetObjectTransform();
				}
				return;
			}
			if (ABM.IsInAbmMode())
			{
				if (IsInAemMode())
				{
					exitMode();
					resetObjectTransform();
				}
				return;
			}
			if (!IsInAemMode() && Input.GetKeyDown(PerfectPlacementPlugin.aementerAdvancedEditingMode.Value))
			{
				if (checkForObject())
				{
					startMode();
				}
				return;
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.aemabortAndExitAdvancedEditingMode.Value))
			{
				exitMode();
				resetObjectTransform();
			}
			if (!IsInAemMode())
			{
				return;
			}
			if (hitPieceStillExists())
			{
				try
				{
					if ((Object)(object)((Component)HitPiece).GetComponent<ZNetView>() == (Object)null)
					{
						PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)"AEM: Error, network object empty. Code: 2.");
						exitMode();
						return;
					}
				}
				catch
				{
					PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)"AEM: Error, network object empty. Code: 3.");
					exitMode();
				}
				isRunning();
				listenToHotKeysAndDoWork();
			}
			else
			{
				exitMode();
			}
		}

		private static void listenToHotKeysAndDoWork()
		{
			//IL_001c: 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_0061: 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_0090: Unknown result type (might be due to invalid IL or missing references)
			//IL_009f: Unknown result type (might be due to invalid IL or missing references)
			//IL_018d: Unknown result type (might be due to invalid IL or missing references)
			//IL_01b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a3: Unknown result type (might be due to invalid IL or missing references)
			//IL_01a8: Unknown result type (might be due to invalid IL or missing references)
			//IL_01dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_01eb: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c8: Unknown result type (might be due to invalid IL or missing references)
			//IL_0232: Unknown result type (might be due to invalid IL or missing references)
			//IL_0237: Unknown result type (might be due to invalid IL or missing references)
			//IL_024e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0266: Unknown result type (might be due to invalid IL or missing references)
			//IL_027a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0284: Unknown result type (might be due to invalid IL or missing references)
			//IL_0289: Unknown result type (might be due to invalid IL or missing references)
			//IL_0377: Unknown result type (might be due to invalid IL or missing references)
			//IL_037c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0393: 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)
			//IL_03bf: Unknown result type (might be due to invalid IL or missing references)
			//IL_03c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_03ce: Unknown result type (might be due to invalid IL or missing references)
			//IL_02f2: 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_030e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0322: Unknown result type (might be due to invalid IL or missing references)
			//IL_033a: 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_0297: Unknown result type (might be due to invalid IL or missing references)
			//IL_029c: Unknown result type (might be due to invalid IL or missing references)
			//IL_02b3: Unknown result type (might be due to invalid IL or missing references)
			//IL_02c7: Unknown result type (might be due to invalid IL or missing references)
			//IL_02db: Unknown result type (might be due to invalid IL or missing references)
			//IL_02e9: Unknown result type (might be due to invalid IL or missing references)
			//IL_02ee: 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_04e8: Unknown result type (might be due to invalid IL or missing references)
			//IL_04ef: Unknown result type (might be due to invalid IL or missing references)
			//IL_04cb: Unknown result type (might be due to invalid IL or missing references)
			//IL_04d2: Unknown result type (might be due to invalid IL or missing references)
			//IL_0437: Unknown result type (might be due to invalid IL or missing references)
			//IL_043c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0453: Unknown result type (might be due to invalid IL or missing references)
			//IL_0467: Unknown result type (might be due to invalid IL or missing references)
			//IL_047f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0489: Unknown result type (might be due to invalid IL or missing references)
			//IL_048e: Unknown result type (might be due to invalid IL or missing references)
			//IL_03dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_03e1: Unknown result type (might be due to invalid IL or missing references)
			//IL_03f8: Unknown result type (might be due to invalid IL or missing references)
			//IL_040c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0420: Unknown result type (might be due to invalid IL or missing references)
			//IL_042e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0433: Unknown result type (might be due to invalid IL or missing references)
			//IL_049a: Unknown result type (might be due to invalid IL or missing references)
			//IL_055a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0561: Unknown result type (might be due to invalid IL or missing references)
			//IL_0533: Unknown result type (might be due to invalid IL or missing references)
			//IL_053a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0516: Unknown result type (might be due to invalid IL or missing references)
			//IL_051d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0581: Unknown result type (might be due to invalid IL or missing references)
			//IL_0588: Unknown result type (might be due to invalid IL or missing references)
			float num = 0f;
			float num2 = 0f;
			float num3 = 0f;
			PerfectPlacementPlugin.UpdateKeyBindings();
			if (Input.GetKeyDown(PerfectPlacementPlugin.aemresetAdvancedEditingMode.Value))
			{
				resetObjectTransform();
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.aemconfirmPlacementOfAdvancedEditingMode.Value))
			{
				if (isContainer())
				{
					dropContainerContents();
				}
				GameObject val = Object.Instantiate<GameObject>(((Component)HitPiece).gameObject, ((Component)HitPiece).transform.position, ((Component)HitPiece).transform.rotation);
				HitPiece.m_placeEffect.Create(((Component)HitPiece).transform.position, ((Component)HitPiece).transform.rotation, val.transform, 1f, -1);
				ZNetView component = ((Component)HitPiece).GetComponent<ZNetView>();
				if ((Object)(object)component == (Object)null)
				{
					PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)"AEM: Error, network object empty.");
					resetObjectTransform();
					exitMode();
				}
				else
				{
					component.ClaimOwnership();
					ZNetScene.instance.Destroy(((Component)HitPiece).gameObject);
					PerfectPlacementPlugin.PerfectPlacementLogger.LogInfo((object)"AEM: Executed.");
					exitMode();
				}
				return;
			}
			if (Input.GetKeyDown((KeyCode)306))
			{
				controlFlag = true;
			}
			if (Input.GetKeyUp((KeyCode)306))
			{
				controlFlag = false;
			}
			if (Input.GetKeyDown((KeyCode)304))
			{
				shiftFlag = true;
			}
			if (Input.GetKeyUp((KeyCode)304))
			{
				shiftFlag = false;
			}
			if (Input.GetKeyDown((KeyCode)308))
			{
				altFlag = true;
			}
			if (Input.GetKeyUp((KeyCode)308))
			{
				altFlag = false;
			}
			changeModificationSpeed();
			if (Input.GetKeyUp(PerfectPlacementPlugin.aemcopyObjectRotation.Value))
			{
				savedRotation = ((Component)HitPiece).transform.rotation;
			}
			if (Input.GetKeyUp(PerfectPlacementPlugin.aempasteObjectRotation.Value))
			{
				((Component)HitPiece).transform.rotation = savedRotation;
			}
			if (Vector3.Distance(((Component)PlayerInstance).transform.position, ((Component)HitPiece).transform.position) > PlayerInstance.m_maxPlaceDistance)
			{
				resetObjectTransform();
				exitMode();
			}
			float num4 = 3f * currentModificationSpeed;
			if (Input.GetAxis("Mouse ScrollWheel") > 0f)
			{
				Quaternion rotation;
				if (controlFlag)
				{
					GizmoManager.CurrentAxis = Vector3.right;
					num += 1f;
					rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x + num4 * num, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z);
				}
				else if (altFlag)
				{
					GizmoManager.CurrentAxis = Vector3.forward;
					num2 += 1f;
					rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z + num4 * num2);
				}
				else
				{
					GizmoManager.CurrentAxis = Vector3.up;
					num3 += 1f;
					rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y + num4 * num3, ((Component)HitPiece).transform.eulerAngles.z);
				}
				((Component)HitPiece).transform.rotation = rotation;
			}
			if (Input.GetAxis("Mouse ScrollWheel") < 0f)
			{
				Quaternion rotation2;
				if (controlFlag)
				{
					GizmoManager.CurrentAxis = Vector3.right;
					num -= 1f;
					rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x + num4 * num, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z);
				}
				else if (altFlag)
				{
					GizmoManager.CurrentAxis = Vector3.forward;
					num2 -= 1f;
					rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z + num4 * num2);
				}
				else
				{
					GizmoManager.CurrentAxis = Vector3.up;
					num3 -= 1f;
					rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y + num4 * num3, ((Component)HitPiece).transform.eulerAngles.z);
				}
				((Component)HitPiece).transform.rotation = rotation2;
			}
			float num5 = 0.1f * currentModificationSpeed;
			if (Input.GetKeyDown((KeyCode)273))
			{
				if (controlFlag)
				{
					((Component)HitPiece).transform.Translate(Vector3.up * num5);
				}
				else
				{
					((Component)HitPiece).transform.Translate(Vector3.forward * num5);
				}
			}
			if (Input.GetKeyDown((KeyCode)274))
			{
				if (controlFlag)
				{
					((Component)HitPiece).transform.Translate(Vector3.down * num5);
				}
				else
				{
					((Component)HitPiece).transform.Translate(Vector3.back * num5);
				}
			}
			if (Input.GetKeyDown((KeyCode)276))
			{
				((Component)HitPiece).transform.Translate(Vector3.left * num5);
			}
			if (Input.GetKeyDown((KeyCode)275))
			{
				((Component)HitPiece).transform.Translate(Vector3.right * num5);
			}
		}

		private static bool hitPieceStillExists()
		{
			try
			{
				if (IsInAemMode())
				{
					isInExistence = true;
				}
			}
			catch
			{
				isInExistence = false;
			}
			return isInExistence;
		}

		private static bool isValidRayCastTarget()
		{
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_0065: Unknown result type (might be due to invalid IL or missing references)
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d3: 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)
			bool result = true;
			if (HitPiece.m_onlyInTeleportArea && !Object.op_Implicit((Object)(object)EffectArea.IsPointInsideArea(((Component)HitPiece).transform.position, (Type)16, 0f)))
			{
				result = false;
			}
			if (!HitPiece.m_allowedInDungeons && ((Component)HitPiece).transform.position.y > 3000f)
			{
				result = false;
			}
			if (Location.IsInsideNoBuildLocation(((Component)HitPiece).transform.position))
			{
				result = false;
			}
			float num = (Object.op_Implicit((Object)(object)((Component)HitPiece).GetComponent<PrivateArea>()) ? ((Component)HitPiece).GetComponent<PrivateArea>().m_radius : 0f);
			if (!PrivateArea.CheckAccess(((Component)HitPiece).transform.position, num, true, false))
			{
				result = false;
			}
			if (WardIsLovePlugin.IsLoaded() && WardIsLovePlugin.WardEnabled().Value && WardMonoscript.CheckInWardMonoscript(((Component)HitPiece).transform.position) && !WardMonoscript.CheckAccess(((Component)HitPiece).transform.position, num))
			{
				result = false;
			}
			return result;
		}

		private static bool isInBuildMode()
		{
			return ((Character)PlayerInstance).InPlaceMode();
		}

		public static bool IsInAemMode()
		{
			return isActive;
		}

		private static void resetObjectTransform()
		{
			//IL_0023: 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)HitPiece == (Object)null))
			{
				notifyUser("Object has been reset to initial position & rotation.", (MessageType)1);
				((Component)HitPiece).transform.position = InitialPosition;
				((Component)HitPiece).transform.rotation = InitialRotation;
			}
		}

		private static void resetObjectInfo()
		{
			//IL_0000: 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_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_002b: 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)
			HitPoint = Vector3.zero;
			HitNormal = Vector3.zero;
			HitObject = null;
			HitPiece = null;
			HitHeightmap = null;
			InitialRotation = default(Quaternion);
			InitialPosition = default(Vector3);
		}

		private static void startMode()
		{
			notifyUser("Entering AEM", (MessageType)1);
			isActive = true;
			KeyBindingOverlay.ToggleOverlay(show: true);
		}

		private static void exitMode()
		{
			notifyUser("Exiting AEM", (MessageType)1);
			forceExitNextIteration = true;
			KeyBindingOverlay.ToggleOverlay(show: false);
		}

		private static void notifyUser(string Message, MessageType position = 1)
		{
			//IL_0005: Unknown result type (might be due to invalid IL or missing references)
			MessageHud.instance.ShowMessage(position, "AEM: " + Message, 0, (Sprite)null);
		}

		private static void isRunning()
		{
			if (IsInAemMode())
			{
				MessageHud.instance.ShowMessage((MessageType)2, "AEM is active", 0, (Sprite)null);
			}
		}

		private static bool isContainer()
		{
			return (Object)(object)((Component)HitPiece).GetComponent<Container>() != (Object)null;
		}

		private static void dropContainerContents()
		{
			((Component)HitPiece).GetComponent<Container>().DropAllItems();
		}

		private static void changeModificationSpeed()
		{
			//IL_0018: 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)
			float num = 1f;
			if (shiftFlag)
			{
				num = 10f;
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.aemincreaseScrollSpeed.Value))
			{
				currentModificationSpeed = Mathf.Clamp(currentModificationSpeed + num, 1f, 30f);
				notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1);
			}
			if (Input.GetKeyDown(PerfectPlacementPlugin.aemdecreaseScrollSpeed.Value))
			{
				currentModificationSpeed = Mathf.Clamp(currentModificationSpeed - num, 1f, 30f);
				notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1);
			}
		}
	}
	[HarmonyPatch(typeof(Player), "CanRotatePiece")]
	internal static class OverridePlayerInPlaceModePatch
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Postfix(Player __instance, ref bool __result)
		{
			if (AEM.IsInAemMode())
			{
				__result = true;
			}
		}
	}
	[HarmonyPatch(typeof(GameCamera), "Awake")]
	internal static class CachedCameraDistance
	{
		internal static float cachedCameraDistanceMax;

		internal static float cachedCameraDistanceMin;

		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Prefix(GameCamera __instance)
		{
			cachedCameraDistanceMax = __instance.m_maxDistance;
			cachedCameraDistanceMin = __instance.m_minDistance;
		}
	}
	[HarmonyPatch(typeof(GameCamera), "UpdateCamera")]
	public static class BlockCameraScrollInAEM
	{
		[<e5b64376-848c-44b5-ad84-53dd18df5967>NullableContext(1)]
		private static void Prefix(GameCamera __instance)
		{
			if (AEM.IsInAemMode())
			{
				__instance.m_maxDistance = __instance.m_distance;
				__instance.m_minDistance = __instance.m_distance;
			}
			else if (!FirstPersonModeCompat.IsFirstPerson)
			{
				__instance.m_maxDistance = CachedCameraDistance.cachedCameraDistanceMax;
				__instance.m_minDistance = CachedCameraDistance.