Decompiled source of HardHeim v0.0.8

HardHeim.dll

Decompiled a day ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using Jotunn;
using Jotunn.Managers;
using Jotunn.Utils;
using Microsoft.CodeAnalysis;
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.SceneManagement;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.6.2", FrameworkDisplayName = ".NET Framework 4.6.2")]
[assembly: AssemblyCompany("HardHeim")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("0.0.8")]
[assembly: AssemblyInformationalVersion("0.0.8+423bc1333dbe953c6e943321e6fc7aacd1efa3c0")]
[assembly: AssemblyProduct("HardHeim")]
[assembly: AssemblyTitle("HardHeim")]
[assembly: AssemblyVersion("0.0.8.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Embedded]
	internal sealed class IsReadOnlyAttribute : Attribute
	{
	}
	[CompilerGenerated]
	[Embedded]
	[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace HardHeim
{
	[BepInPlugin("com.valheim.hardheim", "HardHeim", "0.0.8")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[NetworkCompatibility(/*Could not decode attribute arguments.*/)]
	public class HardHeim : BaseUnityPlugin
	{
		[HarmonyPatch(typeof(Player), "FixedUpdate")]
		public static class CryptEntryPatch
		{
			private static void Postfix()
			{
				if ((Object)(object)EnvMan.instance != (Object)null)
				{
					CryptEnvironmentPatch.Refresh(EnvMan.instance);
				}
			}
		}

		[HarmonyPatch(typeof(MonsterAI), "SetEventCreature")]
		public static class RaidCreaturePatch
		{
			private static void Postfix(MonsterAI __instance, bool despawn)
			{
				if (despawn)
				{
					ZNetView val = ((__instance != null) ? ((Component)__instance).GetComponent<ZNetView>() : null);
					if (!((Object)(object)val == (Object)null) && val.IsValid())
					{
						val.GetZDO().Set("HardHeim_RaidSpawn", true);
					}
				}
			}
		}

		[HarmonyPatch(typeof(CharacterDrop), "GenerateDropList")]
		public static class RaidLootPatch
		{
			private static bool Prefix(CharacterDrop __instance, ref List<KeyValuePair<GameObject, int>> __result)
			{
				if (BlockRaidDrops == null || !BlockRaidDrops.Value || (Object)(object)__instance == (Object)null)
				{
					return true;
				}
				ZNetView component = ((Component)__instance).GetComponent<ZNetView>();
				bool num = (Object)(object)component != (Object)null && component.IsValid() && component.GetZDO().GetBool("HardHeim_RaidSpawn", false);
				MonsterAI component2 = ((Component)__instance).GetComponent<MonsterAI>();
				bool flag = (Object)(object)component2 != (Object)null && component2.IsEventCreature();
				if (!num && !flag)
				{
					return true;
				}
				__result = new List<KeyValuePair<GameObject, int>>();
				return false;
			}
		}

		[HarmonyPatch(typeof(Ship), "CustomFixedUpdate")]
		public static class StormShipDamagePatch
		{
			private static readonly Dictionary<int, float> nextDamageTime = new Dictionary<int, float>();

			private static void Postfix(Ship __instance)
			{
				//IL_0047: 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_0138: Unknown result type (might be due to invalid IL or missing references)
				//IL_013d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0140: Unknown result type (might be due to invalid IL or missing references)
				//IL_015a: Unknown result type (might be due to invalid IL or missing references)
				//IL_015c: 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_0168: Unknown result type (might be due to invalid IL or missing references)
				//IL_0173: Unknown result type (might be due to invalid IL or missing references)
				//IL_017d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0182: Unknown result type (might be due to invalid IL or missing references)
				//IL_0187: Unknown result type (might be due to invalid IL or missing references)
				//IL_018c: Unknown result type (might be due to invalid IL or missing references)
				//IL_018d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0192: Unknown result type (might be due to invalid IL or missing references)
				//IL_0197: Unknown result type (might be due to invalid IL or missing references)
				//IL_01a0: Expected O, but got Unknown
				//IL_01e2: Unknown result type (might be due to invalid IL or missing references)
				if ((Object)(object)__instance == (Object)null || StormShipDamageEnabled == null || !StormShipDamageEnabled.Value || StormShipDamagePerSecond == null || StormShipDamagePerSecond.Value <= 0f || (Object)(object)EnvMan.instance == (Object)null)
				{
					return;
				}
				Vector3 windForce = EnvMan.instance.GetWindForce();
				float magnitude = ((Vector3)(ref windForce)).magnitude;
				ZNetView component = ((Component)__instance).GetComponent<ZNetView>();
				WearNTear component2 = ((Component)__instance).GetComponent<WearNTear>();
				if ((Object)(object)component == (Object)null || (Object)(object)component2 == (Object)null || !component.IsValid() || !component.IsOwner() || magnitude < StormWindThreshold.Value)
				{
					return;
				}
				int instanceID = ((Object)__instance).GetInstanceID();
				if ((!nextDamageTime.TryGetValue(instanceID, out var value) || !(Time.time < value)) && (!(StormShallowWaterDepth.Value > 0f) || !IsInShallowWater(__instance)))
				{
					nextDamageTime[instanceID] = Time.time + 1f;
					float num = ((StormWindThreshold.Value >= 1f) ? 1f : Mathf.Clamp01((magnitude - StormWindThreshold.Value) / (1f - StormWindThreshold.Value)));
					float num2 = Mathf.Lerp(1f, StormMaxDamageMultiplier.Value, num);
					HitData val = new HitData
					{
						m_damage = new DamageTypes
						{
							m_blunt = StormShipDamagePerSecond.Value * num2
						},
						m_point = ((Component)__instance).transform.position + ((Component)__instance).transform.right * 1.5f,
						m_dir = Vector3.up,
						m_dodgeable = false
					};
					component2.Damage(val);
					if ((Object)(object)GameCamera.instance != (Object)null && StormShakeStrength.Value > 0f && StormShakeRange.Value > 0f)
					{
						GameCamera.instance.AddShake(((Component)__instance).transform.position, StormShakeRange.Value, StormShakeStrength.Value, false);
					}
				}
			}

			private static bool IsInShallowWater(Ship ship)
			{
				//IL_0022: 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)
				if ((Object)(object)ship == (Object)null || StormShallowWaterDepth.Value <= 0f)
				{
					return false;
				}
				Heightmap val = Heightmap.FindHeightmap(((Component)ship).transform.position);
				if ((Object)(object)val == (Object)null)
				{
					return false;
				}
				float oceanDepth = val.GetOceanDepth(((Component)ship).transform.position);
				float num = StormShallowWaterDepth.Value + 1.5f;
				if (oceanDepth >= 0f)
				{
					return oceanDepth <= num;
				}
				return false;
			}
		}

		[HarmonyPatch]
		public static class LightningStrikePatch
		{
			private sealed class LightningFlashEffect : MonoBehaviour
			{
				private const float HoldDuration = 2f;

				private const float FadeDuration = 1f;

				private const float StartIntensity = 6f;

				private float elapsed;

				private Light flashLight;

				private void Awake()
				{
					flashLight = ((Component)this).GetComponent<Light>();
				}

				private void Update()
				{
					elapsed += Time.deltaTime;
					if ((Object)(object)flashLight != (Object)null)
					{
						float num = Mathf.Clamp01((elapsed - 2f) / 1f);
						flashLight.intensity = Mathf.Lerp(6f, 0f, num);
					}
					if (elapsed >= 3f)
					{
						Object.Destroy((Object)(object)((Component)this).gameObject);
					}
				}
			}

			private const string RpcName = "HardHeim_LightningStrike";

			private static readonly int RoofRaycastMask = ~LayerMask.GetMask(new string[4] { "Character", "character_trigger", "character_noenv", "Default_small" });

			private static float nextCheckTime;

			private static float nextStrikeAllowedTime;

			private static bool rpcRegistered;

			private static readonly string[] BoltShaderNames = new string[3] { "Unlit/Color", "Sprites/Default", "Standard" };

			private static void EnsureRpcRegistered()
			{
				if (!rpcRegistered && ZRoutedRpc.instance != null)
				{
					ZRoutedRpc.instance.Register<Vector3, string>("HardHeim_LightningStrike", (Action<long, Vector3, string>)OnLightningStrikeRpc);
					rpcRegistered = true;
					Logger.LogInfo((object)"HardHeim: lightning RPC registered.");
				}
			}

			[HarmonyPostfix]
			[HarmonyPatch(typeof(Player), "FixedUpdate")]
			private static void OnPlayerFixedUpdate()
			{
				EnsureRpcRegistered();
				Player localPlayer = Player.m_localPlayer;
				if ((Object)(object)localPlayer == (Object)null || LightningEnabled == null || !LightningEnabled.Value || Time.time < nextCheckTime)
				{
					return;
				}
				nextCheckTime = Time.time + Mathf.Max(0.1f, LightningCheckInterval.Value);
				if (!(Time.time < nextStrikeAllowedTime) && IsThunderstorm() && !HasRoofOverhead(localPlayer))
				{
					float num = (((Object)(object)((Component)localPlayer).GetComponentInParent<Ship>() != (Object)null) ? LightningShipChance.Value : LightningLandChance.Value);
					if (!(Random.Range(0f, 100f) >= num))
					{
						StrikePlayer(localPlayer);
					}
				}
			}

			private static bool IsThunderstorm()
			{
				EnvMan instance = EnvMan.instance;
				EnvSetup environment = ((instance != null) ? instance.GetCurrentEnvironment() : null);
				if (environment == null || string.IsNullOrEmpty(LightningWeatherNames.Value))
				{
					return false;
				}
				return (from name in LightningWeatherNames.Value.Split(new char[1] { ',' })
					select name.Trim()).Any((string name) => string.Equals(name, environment.m_name, StringComparison.OrdinalIgnoreCase));
			}

			private static bool HasRoofOverhead(Player player)
			{
				//IL_0006: Unknown result type (might be due to invalid IL or missing references)
				//IL_000b: Unknown result type (might be due to invalid IL or missing references)
				//IL_0015: 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)
				return Physics.Raycast(((Component)player).transform.position + Vector3.up * 0.5f, Vector3.up, 300f, RoofRaycastMask);
			}

			private static void StrikePlayer(Player player)
			{
				//IL_005b: 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)
				nextStrikeAllowedTime = Time.time + Mathf.Max(0f, LightningCooldownSeconds.Value);
				((Character)player).SetHealth(10f);
				((Character)player).Message((MessageType)2, "Thor's wrath has struck you down!", 0, (Sprite)null, false);
				((MonoBehaviour)player).StartCoroutine(ClearCenterMessageAfter(3f));
				Logger.LogInfo((object)$"HardHeim: lightning struck {player.GetPlayerName()} at {((Component)player).transform.position}, sending RPC.");
				ZRoutedRpc.instance.InvokeRoutedRPC(0L, "HardHeim_LightningStrike", new object[2]
				{
					((Component)player).transform.position,
					player.GetPlayerName()
				});
			}

			private static IEnumerator ClearCenterMessageAfter(float delay)
			{
				yield return (object)new WaitForSeconds(delay);
				MessageHud instance = MessageHud.instance;
				if (instance != null)
				{
					instance.ShowMessage((MessageType)2, string.Empty, 0, (Sprite)null, false, true);
				}
			}

			private static void OnLightningStrikeRpc(long sender, Vector3 position, string playerName)
			{
				//IL_0006: 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)
				Logger.LogInfo((object)$"HardHeim: lightning RPC received for {playerName} at {position}.");
				SpawnLightningVisual(position);
				if ((Object)(object)Player.m_localPlayer != (Object)null && !string.Equals(Player.m_localPlayer.GetPlayerName(), playerName, StringComparison.Ordinal))
				{
					MessageHud instance = MessageHud.instance;
					if (instance != null)
					{
						instance.ShowMessage((MessageType)1, "Thor struck " + playerName + " down!", 0, (Sprite)null, false, true);
					}
				}
			}

			private static void SpawnLightningVisual(Vector3 position)
			{
				//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_0010: 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_0033: Unknown result type (might be due to invalid IL or missing references)
				//IL_005f: 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_006a: 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_0074: 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_009c: Unknown result type (might be due to invalid IL or missing references)
				//IL_00a6: Expected O, but got Unknown
				//IL_00a6: Unknown result type (might be due to invalid IL or missing references)
				//IL_00b3: Unknown result type (might be due to invalid IL or missing references)
				//IL_00bd: Expected O, but got Unknown
				//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
				GameObject val = new GameObject("HardHeim_LightningBolt");
				val.transform.position = position;
				Light obj = val.AddComponent<Light>();
				obj.type = (LightType)2;
				obj.color = new Color(0.75f, 0.85f, 1f);
				obj.intensity = 6f;
				obj.range = 20f;
				obj.shadows = (LightShadows)0;
				Shader shader = ResolveBoltShader();
				Vector3[] points = GenerateBoltPoints(position + Vector3.up * 40f, position);
				CreateBoltLine(val, "Glow", points, shader, 0.6f, new Color(0.6f, 0.8f, 1f, 0.35f));
				CreateBoltLine(val, "Core", points, shader, 0.12f, Color.white);
				val.AddComponent<LightningFlashEffect>();
				if ((Object)(object)GameCamera.instance != (Object)null)
				{
					GameCamera.instance.AddShake(position, 15f, 0.3f, false);
				}
			}

			private static Vector3[] GenerateBoltPoints(Vector3 start, Vector3 end)
			{
				//IL_000a: 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_0013: Unknown result type (might be due to invalid IL or missing references)
				//IL_0014: 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_0027: 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_0060: Unknown result type (might be due to invalid IL or missing references)
				//IL_0067: Unknown result type (might be due to invalid IL or missing references)
				//IL_0071: Unknown result type (might be due to invalid IL or missing references)
				//IL_0076: Unknown result type (might be due to invalid IL or missing references)
				//IL_007a: 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_007d: Unknown result type (might be due to invalid IL or missing references)
				//IL_0082: Unknown result type (might be due to invalid IL or missing references)
				Vector3[] array = (Vector3[])(object)new Vector3[11]
				{
					start,
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					default(Vector3),
					end
				};
				for (int i = 1; i < 10; i++)
				{
					float num = (float)i / 10f;
					Vector3 val = Vector3.Lerp(start, end, num);
					float num2 = Mathf.Sin(num * (float)Math.PI);
					Vector3 val2 = new Vector3(Random.Range(-1f, 1f), 0f, Random.Range(-1f, 1f)) * num2 * 1.5f;
					array[i] = val + val2;
				}
				return array;
			}

			private static void CreateBoltLine(GameObject parent, string childName, Vector3[] points, Shader shader, float width, Color color)
			{
				//IL_0001: Unknown result type (might be due to invalid IL or missing references)
				//IL_0006: Unknown result type (might be due to invalid IL or missing references)
				//IL_004c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0054: 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_0062: 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_0076: 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_0090: Unknown result type (might be due to invalid IL or missing references)
				//IL_0091: Unknown result type (might be due to invalid IL or missing references)
				//IL_009d: Expected O, but got Unknown
				GameObject val = new GameObject(childName);
				val.transform.SetParent(parent.transform, true);
				LineRenderer val2 = val.AddComponent<LineRenderer>();
				val2.positionCount = points.Length;
				val2.SetPositions(points);
				val2.startWidth = width;
				val2.endWidth = width * 0.3f;
				val2.useWorldSpace = true;
				val2.startColor = color;
				val2.endColor = new Color(color.r, color.g, color.b, color.a * 0.5f);
				if ((Object)(object)shader != (Object)null)
				{
					((Renderer)val2).material = new Material(shader)
					{
						color = color
					};
				}
			}

			private static Shader ResolveBoltShader()
			{
				string[] boltShaderNames = BoltShaderNames;
				for (int i = 0; i < boltShaderNames.Length; i++)
				{
					Shader val = Shader.Find(boltShaderNames[i]);
					if ((Object)(object)val != (Object)null)
					{
						return val;
					}
				}
				return null;
			}
		}

		[HarmonyPatch]
		public static class CryptLootPatch
		{
			private static bool wasInsideCrypt;

			[HarmonyPostfix]
			[HarmonyPatch(typeof(Player), "FixedUpdate")]
			private static void OnPlayerFixedUpdate()
			{
				if (!((Object)(object)Player.m_localPlayer == (Object)null))
				{
					if (!((Character)Player.m_localPlayer).InInterior())
					{
						wasInsideCrypt = false;
					}
					else if (!wasInsideCrypt)
					{
						wasInsideCrypt = true;
						ProcessCurrentCrypt();
					}
				}
			}

			private static void ProcessCurrentCrypt()
			{
				//IL_0030: 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)
				ItemDrop surtlingCore = Cache.GetPrefab<ItemDrop>("SurtlingCore");
				if ((Object)(object)surtlingCore == (Object)null)
				{
					return;
				}
				Vector3 playerPos = ((Component)Player.m_localPlayer).transform.position;
				List<Pickable> list = Object.FindObjectsByType<Pickable>((FindObjectsSortMode)0).Where(delegate(Pickable p)
				{
					//IL_0006: Unknown result type (might be due to invalid IL or missing references)
					//IL_000b: Unknown result type (might be due to invalid IL or missing references)
					//IL_0033: Unknown result type (might be due to invalid IL or missing references)
					//IL_0039: Unknown result type (might be due to invalid IL or missing references)
					Scene scene = ((Component)p).gameObject.scene;
					return ((Scene)(ref scene)).IsValid() && (Object)(object)p.m_itemPrefab == (Object)(object)((Component)surtlingCore).gameObject && Vector3.Distance(((Component)p).transform.position, playerPos) <= 80f;
				}).ToList();
				if (list.Count == 0)
				{
					return;
				}
				float num = Random.Range(0f, 100f);
				float num2 = ((cryptSurtlingCoreChance != null) ? cryptSurtlingCoreChance.Value : 30f);
				IEnumerable<Pickable> enumerable2;
				if (!(num < num2))
				{
					IEnumerable<Pickable> enumerable = list;
					enumerable2 = enumerable;
				}
				else
				{
					enumerable2 = list.Skip(1);
				}
				foreach (Pickable item in enumerable2)
				{
					GameObject gameObject = ((Component)item).gameObject;
					if ((Object)(object)ZNetScene.instance != (Object)null)
					{
						ZNetScene.instance.Destroy(gameObject);
					}
					else
					{
						Object.Destroy((Object)(object)gameObject);
					}
				}
			}
		}

		[HarmonyPatch(typeof(Skills), "LowerAllSkills")]
		public static class DeathPenaltyPatch
		{
			public static bool Prefix(Skills __instance, float factor)
			{
				if (factor <= 0f)
				{
					return false;
				}
				foreach (Skill skill in __instance.GetSkillList())
				{
					skill.m_level = CalculatePenaltyLevel(skill.m_level, factor);
					skill.m_accumulator = 0f;
				}
				return false;
			}

			private static float CalculatePenaltyLevel(float currentLevel, float factor)
			{
				if (currentLevel >= 60f)
				{
					return Mathf.Max(0f, currentLevel - 1f);
				}
				if (currentLevel >= 50f)
				{
					return Mathf.Max(0f, currentLevel - 2f);
				}
				return currentLevel * (1f - factor);
			}
		}

		[HarmonyPatch(typeof(EnvMan), "UpdateEnvironment")]
		public static class CryptEnvironmentPatch
		{
			private static bool darknessApplied;

			private static AmbientMode originalAmbientMode;

			private static SphericalHarmonicsL2 originalAmbientProbe;

			private static Color originalAmbientLight;

			private static float originalAmbientIntensity;

			private static float originalReflectionIntensity;

			private static Color originalFogColor;

			private static float originalFogDensity;

			private static EnvSetup darkEnvironment;

			private static Color originalEnvironmentAmbientColorDay;

			private static Color originalEnvironmentAmbientColorNight;

			private static float originalEnvironmentLightIntensityDay;

			private static float originalEnvironmentLightIntensityNight;

			private static Color originalEnvironmentFogColorDay;

			private static Color originalEnvironmentFogColorNight;

			private static float originalEnvironmentFogDensityDay;

			private static float originalEnvironmentFogDensityNight;

			public static bool IsDarkDungeon { get; private set; }

			private static void Postfix(EnvMan __instance)
			{
				Refresh(__instance);
			}

			public static void Refresh(EnvMan environmentManager)
			{
				if ((Object)(object)environmentManager == (Object)null || (Object)(object)Player.m_localPlayer == (Object)null)
				{
					RestoreLighting();
					return;
				}
				if (!((Character)Player.m_localPlayer).InInterior())
				{
					RestoreLighting();
					return;
				}
				IsDarkDungeon = true;
				ApplyEnvironmentDarkness(environmentManager.GetCurrentEnvironment());
				ApplyDarkness();
				DungeonLightPatch.DisableDungeonLights();
				PlayerLightPatch.BoostPlayerLights();
			}

			private static void ApplyEnvironmentDarkness(EnvSetup environment)
			{
				//IL_0018: Unknown result type (might be due to invalid IL or missing references)
				//IL_001d: 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_0028: 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_0049: Unknown result type (might be due to invalid IL or missing references)
				//IL_004f: Unknown result type (might be due to invalid IL or missing references)
				//IL_0054: 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_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_0080: Unknown result type (might be due to invalid IL or missing references)
				//IL_009c: Unknown result type (might be due to invalid IL or missing references)
				//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
				//IL_00a7: Unknown result type (might be due to invalid IL or missing references)
				//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
				if (environment != null && darkEnvironment != environment)
				{
					RestoreEnvironmentLighting();
					darkEnvironment = environment;
					originalEnvironmentAmbientColorDay = environment.m_ambColorDay;
					originalEnvironmentAmbientColorNight = environment.m_ambColorNight;
					originalEnvironmentLightIntensityDay = environment.m_lightIntensityDay;
					originalEnvironmentLightIntensityNight = environment.m_lightIntensityNight;
					originalEnvironmentFogColorDay = environment.m_fogColorDay;
					originalEnvironmentFogColorNight = environment.m_fogColorNight;
					originalEnvironmentFogDensityDay = environment.m_fogDensityDay;
					originalEnvironmentFogDensityNight = environment.m_fogDensityNight;
					environment.m_ambColorDay = Color.black;
					environment.m_ambColorNight = Color.black;
					environment.m_lightIntensityDay = 0f;
					environment.m_lightIntensityNight = 0f;
					environment.m_fogColorDay = Color.black;
					environment.m_fogColorNight = Color.black;
					environment.m_fogDensityDay = 1f;
					environment.m_fogDensityNight = 1f;
				}
			}

			private static void ApplyDarkness()
			{
				//IL_0059: 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_0075: Unknown result type (might be due to invalid IL or missing references)
				//IL_0085: Unknown result type (might be due to invalid IL or missing references)
				//IL_0007: Unknown result type (might be due to invalid IL or missing references)
				//IL_000c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0011: Unknown result type (might be due to invalid IL or missing references)
				//IL_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_0020: Unknown result type (might be due to invalid IL or missing references)
				//IL_0039: Unknown result type (might be due to invalid IL or missing references)
				//IL_003e: Unknown result type (might be due to invalid IL or missing references)
				if (!darknessApplied)
				{
					originalAmbientMode = RenderSettings.ambientMode;
					originalAmbientProbe = RenderSettings.ambientProbe;
					originalAmbientLight = RenderSettings.ambientLight;
					originalAmbientIntensity = RenderSettings.ambientIntensity;
					originalReflectionIntensity = RenderSettings.reflectionIntensity;
					originalFogColor = RenderSettings.fogColor;
					originalFogDensity = RenderSettings.fogDensity;
					darknessApplied = true;
				}
				RenderSettings.ambientMode = (AmbientMode)3;
				RenderSettings.ambientLight = Color.black;
				RenderSettings.ambientIntensity = 0f;
				RenderSettings.ambientProbe = default(SphericalHarmonicsL2);
				RenderSettings.reflectionIntensity = 0f;
				RenderSettings.fogColor = Color.black;
				RenderSettings.fogDensity = 0.1f;
			}

			private static void RestoreLighting()
			{
				//IL_0008: 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_001c: 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)
				if (darknessApplied)
				{
					RenderSettings.ambientMode = originalAmbientMode;
					RenderSettings.ambientProbe = originalAmbientProbe;
					RenderSettings.ambientLight = originalAmbientLight;
					RenderSettings.ambientIntensity = originalAmbientIntensity;
					RenderSettings.reflectionIntensity = originalReflectionIntensity;
					RenderSettings.fogColor = originalFogColor;
					RenderSettings.fogDensity = originalFogDensity;
					RestoreEnvironmentLighting();
					PlayerLightPatch.RestorePlayerLights();
					darknessApplied = false;
					IsDarkDungeon = false;
				}
			}

			private static void RestoreEnvironmentLighting()
			{
				//IL_000d: 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_001c: Unknown result type (might be due to invalid IL or missing references)
				//IL_0021: Unknown result type (might be due to invalid IL or missing references)
				//IL_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)
				//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)
				if (darkEnvironment != null)
				{
					darkEnvironment.m_ambColorDay = originalEnvironmentAmbientColorDay;
					darkEnvironment.m_ambColorNight = originalEnvironmentAmbientColorNight;
					darkEnvironment.m_lightIntensityDay = originalEnvironmentLightIntensityDay;
					darkEnvironment.m_lightIntensityNight = originalEnvironmentLightIntensityNight;
					darkEnvironment.m_fogColorDay = originalEnvironmentFogColorDay;
					darkEnvironment.m_fogColorNight = originalEnvironmentFogColorNight;
					darkEnvironment.m_fogDensityDay = originalEnvironmentFogDensityDay;
					darkEnvironment.m_fogDensityNight = originalEnvironmentFogDensityNight;
					darkEnvironment = null;
				}
			}
		}

		public static class DungeonLightPatch
		{
			public static void DisableDungeonLights()
			{
				Light[] array = Object.FindObjectsByType<Light>((FindObjectsSortMode)0);
				for (int i = 0; i < array.Length; i++)
				{
					DisableDungeonLight(array[i]);
				}
			}

			private static void DisableDungeonLight(Light light)
			{
				if (!((Object)(object)light == (Object)null) && IsDungeonLight(light))
				{
					((Behaviour)light).enabled = false;
					light.intensity = 0f;
					ParticleSystem[] componentsInChildren = ((Component)((Component)light).transform.root).GetComponentsInChildren<ParticleSystem>();
					foreach (ParticleSystem obj in componentsInChildren)
					{
						obj.Stop();
						obj.Clear();
					}
				}
			}

			public static bool IsDungeonLight(Light light)
			{
				string text = ((Object)((Component)light).transform.root).name.ToLowerInvariant();
				if (text.Contains("player") || text.Contains("character"))
				{
					return false;
				}
				string text2 = ((Object)((Component)light).gameObject).name.ToLowerInvariant();
				if (!text.Contains("torch") && !text.Contains("sconce") && !text.Contains("brazier") && !text.Contains("fire") && !text.Contains("flame") && !text2.Contains("torch") && !text2.Contains("sconce") && !text2.Contains("brazier") && !text2.Contains("fire"))
				{
					return text2.Contains("flame");
				}
				return true;
			}
		}

		public static class PlayerLightPatch
		{
			private readonly struct LightSettings
			{
				public float Intensity { get; }

				public float Range { get; }

				public LightSettings(float intensity, float range)
				{
					Intensity = intensity;
					Range = range;
				}
			}

			private const float IntensityMultiplier = 0.25f;

			private const float RangeMultiplier = 0.8f;

			private static readonly Dictionary<Light, LightSettings> originalLights = new Dictionary<Light, LightSettings>();

			public static void BoostPlayerLights()
			{
				if ((Object)(object)Player.m_localPlayer == (Object)null)
				{
					return;
				}
				Light[] array = Object.FindObjectsByType<Light>((FindObjectsSortMode)0);
				foreach (Light val in array)
				{
					if (!DungeonLightPatch.IsDungeonLight(val) && IsPlayerLight(val))
					{
						if (!originalLights.ContainsKey(val))
						{
							originalLights[val] = new LightSettings(val.intensity, val.range);
						}
						LightSettings lightSettings = originalLights[val];
						val.intensity = lightSettings.Intensity * 0.25f;
						val.range = lightSettings.Range * 0.8f;
					}
				}
			}

			public static void BoostAttachedLights(Component component)
			{
				if (!CryptEnvironmentPatch.IsDarkDungeon || (Object)(object)component == (Object)null || (Object)(object)Player.m_localPlayer == (Object)null || !component.transform.IsChildOf(((Component)Player.m_localPlayer).transform))
				{
					return;
				}
				Light[] componentsInChildren = component.GetComponentsInChildren<Light>(true);
				foreach (Light light in componentsInChildren)
				{
					if (!DungeonLightPatch.IsDungeonLight(light))
					{
						BoostLight(light);
					}
				}
			}

			private static void BoostLight(Light light)
			{
				if (!originalLights.ContainsKey(light))
				{
					originalLights[light] = new LightSettings(light.intensity, light.range);
				}
				LightSettings lightSettings = originalLights[light];
				light.intensity = lightSettings.Intensity * 0.25f;
				light.range = lightSettings.Range * 0.8f;
			}

			private static bool IsPlayerLight(Light light)
			{
				if ((Object)(object)Player.m_localPlayer != (Object)null)
				{
					return ((Component)light).transform.IsChildOf(((Component)Player.m_localPlayer).transform);
				}
				return false;
			}

			public static void RestorePlayerLights()
			{
				foreach (KeyValuePair<Light, LightSettings> originalLight in originalLights)
				{
					if (!((Object)(object)originalLight.Key == (Object)null))
					{
						originalLight.Key.intensity = originalLight.Value.Intensity;
						originalLight.Key.range = originalLight.Value.Range;
					}
				}
				originalLights.Clear();
			}
		}

		[HarmonyPatch(typeof(LightFlicker), "Awake")]
		public static class LightFlickerPatch
		{
			private static void Postfix(LightFlicker __instance)
			{
				PlayerLightPatch.BoostAttachedLights((Component)(object)__instance);
			}
		}

		[HarmonyPatch(typeof(ParticleIntensityScaler), "Start")]
		public static class ParticleLightPatch
		{
			private static void Postfix(ParticleIntensityScaler __instance)
			{
				PlayerLightPatch.BoostAttachedLights((Component)(object)__instance);
			}
		}

		[HarmonyPatch(typeof(Behaviour), "set_enabled")]
		public static class DungeonLightEnabledPatch
		{
			private static void Prefix(Behaviour __instance, ref bool value)
			{
				if (value && CryptEnvironmentPatch.IsDarkDungeon)
				{
					Light val = (Light)(object)((__instance is Light) ? __instance : null);
					if (val != null && DungeonLightPatch.IsDungeonLight(val))
					{
						value = false;
					}
				}
			}
		}

		public const string PluginGUID = "com.valheim.hardheim";

		public const string PluginName = "HardHeim";

		private ConfigEntry<float> copperOreWeight;

		private ConfigEntry<float> surtlingCoreWeight;

		private ConfigEntry<float> stormWindThreshold;

		private ConfigEntry<float> stormShipDamagePerSecond;

		private ConfigEntry<float> stormMaxDamageMultiplier;

		private ConfigEntry<float> stormShakeStrength;

		private ConfigEntry<float> stormShakeRange;

		private ConfigEntry<float> stormShallowWaterDepth;

		private ConfigEntry<float> clubDamage;

		private ConfigEntry<float> flintKnifeDamage;

		private ConfigEntry<float> stoneAxeDamage;

		private ConfigEntry<float> flintSpearDamage;

		private ConfigEntry<float> crudeBowDamage;

		private ConfigEntry<int> torchWoodCost;

		private ConfigEntry<int> torchResinCost;

		private ConfigEntry<int> torchHitsToBreak;

		private ConfigEntry<bool> blockRaidDrops;

		internal static ConfigEntry<float> cryptSurtlingCoreChance;

		internal static ConfigEntry<bool> StormShipDamageEnabled;

		internal static ConfigEntry<float> StormWindThreshold;

		internal static ConfigEntry<float> StormShipDamagePerSecond;

		internal static ConfigEntry<float> StormMaxDamageMultiplier;

		internal static ConfigEntry<float> StormShakeStrength;

		internal static ConfigEntry<float> StormShakeRange;

		internal static ConfigEntry<float> StormShallowWaterDepth;

		internal static ConfigEntry<bool> BlockRaidDrops;

		internal static ConfigEntry<bool> LightningEnabled;

		internal static ConfigEntry<float> LightningLandChance;

		internal static ConfigEntry<float> LightningShipChance;

		internal static ConfigEntry<float> LightningCheckInterval;

		internal static ConfigEntry<float> LightningCooldownSeconds;

		internal static ConfigEntry<string> LightningWeatherNames;

		private static Harmony harmony;

		private const string RaidSpawnZdoKey = "HardHeim_RaidSpawn";

		private void Awake()
		{
			//IL_0032: 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)
			//IL_003f: Expected O, but got Unknown
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0049: Expected O, but got Unknown
			//IL_0080: Unknown result type (might be due to invalid IL or missing references)
			//IL_0085: Unknown result type (might be due to invalid IL or missing references)
			//IL_008d: Expected O, but got Unknown
			//IL_008d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0097: Expected O, but got Unknown
			//IL_00ce: 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_00db: Expected O, but got Unknown
			//IL_00db: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e5: Expected O, but got Unknown
			//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_0129: Expected O, but got Unknown
			//IL_0129: Unknown result type (might be due to invalid IL or missing references)
			//IL_0133: Expected O, but got Unknown
			//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_0177: Expected O, but got Unknown
			//IL_0177: Unknown result type (might be due to invalid IL or missing references)
			//IL_0181: Expected O, but got Unknown
			//IL_01b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_01bd: Unknown result type (might be due to invalid IL or missing references)
			//IL_01c5: Expected O, but got Unknown
			//IL_01c5: Unknown result type (might be due to invalid IL or missing references)
			//IL_01cf: Expected O, but got Unknown
			//IL_0206: Unknown result type (might be due to invalid IL or missing references)
			//IL_020b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0213: Expected O, but got Unknown
			//IL_0213: Unknown result type (might be due to invalid IL or missing references)
			//IL_021d: Expected O, but got Unknown
			//IL_0249: 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_0256: Expected O, but got Unknown
			//IL_0256: Unknown result type (might be due to invalid IL or missing references)
			//IL_0260: Expected O, but got Unknown
			//IL_028c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0291: Unknown result type (might be due to invalid IL or missing references)
			//IL_0299: Expected O, but got Unknown
			//IL_0299: Unknown result type (might be due to invalid IL or missing references)
			//IL_02a3: Expected O, but got Unknown
			//IL_02cf: 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_02dc: Expected O, but got Unknown
			//IL_02dc: Unknown result type (might be due to invalid IL or missing references)
			//IL_02e6: Expected O, but got Unknown
			//IL_031c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0321: Unknown result type (might be due to invalid IL or missing references)
			//IL_0329: Expected O, but got Unknown
			//IL_0329: Unknown result type (might be due to invalid IL or missing references)
			//IL_0333: Expected O, but got Unknown
			//IL_036a: Unknown result type (might be due to invalid IL or missing references)
			//IL_036f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0377: Expected O, but got Unknown
			//IL_0377: Unknown result type (might be due to invalid IL or missing references)
			//IL_0381: Expected O, but got Unknown
			//IL_03a5: Unknown result type (might be due to invalid IL or missing references)
			//IL_03aa: Unknown result type (might be due to invalid IL or missing references)
			//IL_03b2: Expected O, but got Unknown
			//IL_03b2: Unknown result type (might be due to invalid IL or missing references)
			//IL_03bc: Expected O, but got Unknown
			//IL_03f3: 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_0400: Expected O, but got Unknown
			//IL_0400: Unknown result type (might be due to invalid IL or missing references)
			//IL_040a: Expected O, but got Unknown
			//IL_0441: Unknown result type (might be due to invalid IL or missing references)
			//IL_0446: Unknown result type (might be due to invalid IL or missing references)
			//IL_044e: Expected O, but got Unknown
			//IL_044e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0458: Expected O, but got Unknown
			//IL_048f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0494: Unknown result type (might be due to invalid IL or missing references)
			//IL_049c: Expected O, but got Unknown
			//IL_049c: Unknown result type (might be due to invalid IL or missing references)
			//IL_04a6: Expected O, but got Unknown
			//IL_04dd: Unknown result type (might be due to invalid IL or missing references)
			//IL_04e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_04ea: Expected O, but got Unknown
			//IL_04ea: Unknown result type (might be due to invalid IL or missing references)
			//IL_04f4: Expected O, but got Unknown
			//IL_052b: Unknown result type (might be due to invalid IL or missing references)
			//IL_0530: Unknown result type (might be due to invalid IL or missing references)
			//IL_0538: Expected O, but got Unknown
			//IL_0538: Unknown result type (might be due to invalid IL or missing references)
			//IL_0542: Expected O, but got Unknown
			//IL_05a9: Unknown result type (might be due to invalid IL or missing references)
			//IL_05ae: Unknown result type (might be due to invalid IL or missing references)
			//IL_05b6: Expected O, but got Unknown
			//IL_05b6: Unknown result type (might be due to invalid IL or missing references)
			//IL_05c0: Expected O, but got Unknown
			//IL_05ef: Unknown result type (might be due to invalid IL or missing references)
			//IL_05f4: Unknown result type (might be due to invalid IL or missing references)
			//IL_05fc: Expected O, but got Unknown
			//IL_05fc: Unknown result type (might be due to invalid IL or missing references)
			//IL_0606: Expected O, but got Unknown
			//IL_063c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0641: Unknown result type (might be due to invalid IL or missing references)
			//IL_0649: Expected O, but got Unknown
			//IL_0649: Unknown result type (might be due to invalid IL or missing references)
			//IL_0653: Expected O, but got Unknown
			//IL_0689: Unknown result type (might be due to invalid IL or missing references)
			//IL_068e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0696: Expected O, but got Unknown
			//IL_0696: Unknown result type (might be due to invalid IL or missing references)
			//IL_06a0: Expected O, but got Unknown
			//IL_06d6: Unknown result type (might be due to invalid IL or missing references)
			//IL_06db: Unknown result type (might be due to invalid IL or missing references)
			//IL_06e3: Expected O, but got Unknown
			//IL_06e3: Unknown result type (might be due to invalid IL or missing references)
			//IL_06ed: Expected O, but got Unknown
			//IL_0715: Unknown result type (might be due to invalid IL or missing references)
			//IL_071a: Unknown result type (might be due to invalid IL or missing references)
			//IL_0722: Expected O, but got Unknown
			//IL_0722: Unknown result type (might be due to invalid IL or missing references)
			//IL_072c: Expected O, but got Unknown
			//IL_0762: Unknown result type (might be due to invalid IL or missing references)
			//IL_0767: Unknown result type (might be due to invalid IL or missing references)
			//IL_076f: Expected O, but got Unknown
			//IL_076f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0779: Expected O, but got Unknown
			//IL_0783: Unknown result type (might be due to invalid IL or missing references)
			//IL_078d: Expected O, but got Unknown
			copperOreWeight = ((BaseUnityPlugin)this).Config.Bind<float>("Ore Weights", "CopperOre", 50f, new ConfigDescription("Weight of one copper ore.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.1f, 1000f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			surtlingCoreWeight = ((BaseUnityPlugin)this).Config.Bind<float>("Ore Weights", "SurtlingCore", 150f, new ConfigDescription("Weight of one surtling core.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.1f, 1000f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			clubDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Weapon Balance", "ClubDamage", 8f, new ConfigDescription("Blunt damage dealt by the Club.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			flintKnifeDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Weapon Balance", "FlintKnifeDamage", 8f, new ConfigDescription("Total damage dealt by the Flint Knife, split between slash and pierce.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stoneAxeDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Weapon Balance", "StoneAxeDamage", 9f, new ConfigDescription("Slash damage dealt by the Stone Axe.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			flintSpearDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Weapon Balance", "FlintSpearDamage", 12f, new ConfigDescription("Pierce damage dealt by the Flint Spear.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			crudeBowDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Weapon Balance", "CrudeBowDamage", 14f, new ConfigDescription("Pierce damage dealt by the Crude Bow before arrow damage.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			torchWoodCost = ((BaseUnityPlugin)this).Config.Bind<int>("Weapon Balance", "TorchWoodCost", 2, new ConfigDescription("Wood required to craft a Torch.", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 20), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			torchResinCost = ((BaseUnityPlugin)this).Config.Bind<int>("Weapon Balance", "TorchResinCost", 5, new ConfigDescription("Resin required to craft a Torch.", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 20), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			torchHitsToBreak = ((BaseUnityPlugin)this).Config.Bind<int>("Weapon Balance", "TorchHitsToBreak", 2, new ConfigDescription("Number of melee hits before a Torch breaks, in addition to its normal timed burn-out.", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 20), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			cryptSurtlingCoreChance = ((BaseUnityPlugin)this).Config.Bind<float>("Crypt Loot", "SurtlingCoreChance", 30f, new ConfigDescription("Percent chance (0-100) to find a Surtling Core in a Burial Chamber (0 or 1 total per crypt).", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormWindThreshold = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "WindThreshold", 0.8f, new ConfigDescription("Minimum wind force required for storms to damage ships.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 1f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			StormShipDamageEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Storm Ship Damage", "Enabled", true, new ConfigDescription("Enable storm damage to ships.", (AcceptableValueBase)null, new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormShipDamagePerSecond = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "DamagePerSecond", 7f, new ConfigDescription("Blunt damage dealt to ships per second during storms.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormMaxDamageMultiplier = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "MaxDamageMultiplier", 2f, new ConfigDescription("Maximum damage multiplier at the strongest wind.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(1f, 10f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormShakeStrength = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "ShakeStrength", 0.2f, new ConfigDescription("Camera shake strength when a wave damages the ship.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 2f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormShakeRange = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "ShakeRange", 20f, new ConfigDescription("Maximum distance at which storm ship impacts shake the camera.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			stormShallowWaterDepth = ((BaseUnityPlugin)this).Config.Bind<float>("Storm Ship Damage", "ShallowWaterDepth", 15f, new ConfigDescription("Ships do not take storm damage when the seabed is this close below them.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 40f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			StormWindThreshold = stormWindThreshold;
			StormShipDamagePerSecond = stormShipDamagePerSecond;
			StormMaxDamageMultiplier = stormMaxDamageMultiplier;
			StormShakeStrength = stormShakeStrength;
			StormShakeRange = stormShakeRange;
			StormShallowWaterDepth = stormShallowWaterDepth;
			blockRaidDrops = ((BaseUnityPlugin)this).Config.Bind<bool>("Raid Loot", "BlockRaidDrops", true, new ConfigDescription("Prevent creatures spawned by raids from dropping loot.", (AcceptableValueBase)null, new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			BlockRaidDrops = blockRaidDrops;
			LightningEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Lightning Strikes", "Enabled", true, new ConfigDescription("Enable lightning strikes on players during thunderstorms.", (AcceptableValueBase)null, new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			LightningLandChance = ((BaseUnityPlugin)this).Config.Bind<float>("Lightning Strikes", "LandChancePercent", 0.5f, new ConfigDescription("Percent chance (0-100) per check to be struck while on land during a thunderstorm.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			LightningShipChance = ((BaseUnityPlugin)this).Config.Bind<float>("Lightning Strikes", "ShipChancePercent", 1f, new ConfigDescription("Percent chance (0-100) per check to be struck while on a ship during a thunderstorm.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 100f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			LightningCheckInterval = ((BaseUnityPlugin)this).Config.Bind<float>("Lightning Strikes", "CheckIntervalSeconds", 130f, new ConfigDescription("How often (in seconds) the strike chance is rolled per player.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.1f, 240f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			LightningWeatherNames = ((BaseUnityPlugin)this).Config.Bind<string>("Lightning Strikes", "ThunderstormEnvironments", "ThunderStorm", new ConfigDescription("Comma-separated environment names that count as a thunderstorm.", (AcceptableValueBase)null, new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			LightningCooldownSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("Lightning Strikes", "CooldownSeconds", 120f, new ConfigDescription("Minimum time after being struck before a player can be struck again.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0f, 3600f), new object[1] { (object)new ConfigurationManagerAttributes
			{
				IsAdminOnly = true
			} }));
			harmony = new Harmony("com.valheim.hardheim");
			try
			{
				harmony.PatchAll();
			}
			catch (Exception arg)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)$"Failed to install Harmony patches: {arg}");
				throw;
			}
			((BaseUnityPlugin)this).Logger.LogInfo((object)"HardHeim started.");
			Logger.LogInfo((object)"HardHeim started through Jotunn.");
			LogConfiguration();
			ItemManager.OnItemsRegistered += SetItemWeights;
			SynchronizationManager.OnConfigurationSynchronized += OnConfigurationSynchronized;
		}

		private void LogConfiguration()
		{
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Copper ore weight set to {copperOreWeight.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Surtling core weight set to {surtlingCoreWeight.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Crypt Surtling Core chance set to {cryptSurtlingCoreChance.Value}%.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm ship damage enabled set to {StormShipDamageEnabled.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm wind threshold set to {StormWindThreshold.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm ship damage per second set to {StormShipDamagePerSecond.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm max damage multiplier set to {StormMaxDamageMultiplier.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm shake strength set to {StormShakeStrength.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm shake range set to {StormShakeRange.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Storm shallow water depth set to {StormShallowWaterDepth.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Club damage set to {clubDamage.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Flint Knife damage set to {flintKnifeDamage.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Stone Axe damage set to {stoneAxeDamage.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Flint Spear damage set to {flintSpearDamage.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Crude Bow damage set to {crudeBowDamage.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Torch recipe cost set to {torchWoodCost.Value} Wood, {torchResinCost.Value} Resin.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Torch hits to break set to {torchHitsToBreak.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Raid drops blocked set to {BlockRaidDrops.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Lightning strikes enabled set to {LightningEnabled.Value}.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Lightning land chance set to {LightningLandChance.Value}%.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Lightning ship chance set to {LightningShipChance.Value}%.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Lightning check interval set to {LightningCheckInterval.Value} seconds.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Lightning cooldown set to {LightningCooldownSeconds.Value} seconds.");
			((BaseUnityPlugin)this).Logger.LogInfo((object)("Lightning thunderstorm environments set to " + LightningWeatherNames.Value + "."));
		}

		private void SetItemWeights()
		{
			ItemDrop prefab = Cache.GetPrefab<ItemDrop>("CopperOre");
			if ((Object)(object)prefab == (Object)null)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Could not find the CopperOre prefab.");
				return;
			}
			prefab.m_itemData.m_shared.m_weight = copperOreWeight.Value;
			ItemDrop prefab2 = Cache.GetPrefab<ItemDrop>("SurtlingCore");
			if ((Object)(object)prefab2 == (Object)null)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Could not find the SurtlingCore prefab.");
				return;
			}
			prefab2.m_itemData.m_shared.m_weight = surtlingCoreWeight.Value;
			SetWeaponBalance();
		}

		private void SetWeaponBalance()
		{
			SetWeaponDamage("Club", clubDamage.Value);
			SetWeaponDamage("KnifeFlint", flintKnifeDamage.Value);
			SetWeaponDamage("AxeStone", stoneAxeDamage.Value);
			SetWeaponDamage("SpearFlint", flintSpearDamage.Value);
			SetWeaponDamage("BowCrude", crudeBowDamage.Value);
			SetTorchRecipeCost();
			SetTorchHitsToBreak();
		}

		private void SetTorchHitsToBreak()
		{
			ItemDrop prefab = Cache.GetPrefab<ItemDrop>("Torch");
			if ((Object)(object)prefab == (Object)null || prefab.m_itemData?.m_shared == null)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Could not find the Torch weapon prefab.");
				return;
			}
			SharedData shared = prefab.m_itemData.m_shared;
			shared.m_useDurability = true;
			shared.m_useDurabilityDrain = shared.m_maxDurability / (float)torchHitsToBreak.Value;
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Torch hits to break set to {torchHitsToBreak.Value}.");
		}

		private void SetTorchRecipeCost()
		{
			Recipe val = ObjectDB.instance?.m_recipes.Find((Recipe r) => (Object)(object)r.m_item != (Object)null && ((Object)r.m_item).name == "Torch");
			if ((Object)(object)val == (Object)null)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Could not find the Torch recipe.");
				return;
			}
			Requirement[] resources = val.m_resources;
			foreach (Requirement val2 in resources)
			{
				if (!((Object)(object)val2.m_resItem == (Object)null))
				{
					if (((Object)val2.m_resItem).name == "Wood")
					{
						val2.m_amount = torchWoodCost.Value;
					}
					else if (((Object)val2.m_resItem).name == "Resin")
					{
						val2.m_amount = torchResinCost.Value;
					}
				}
			}
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Torch recipe cost set to {torchWoodCost.Value} Wood, {torchResinCost.Value} Resin.");
		}

		private void SetWeaponDamage(string prefabName, float damage)
		{
			//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_00d9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00da: Unknown result type (might be due to invalid IL or missing references)
			ItemDrop prefab = Cache.GetPrefab<ItemDrop>(prefabName);
			if ((Object)(object)prefab == (Object)null || prefab.m_itemData?.m_shared == null)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)("Could not find the " + prefabName + " weapon prefab."));
				return;
			}
			DamageTypes damages = prefab.m_itemData.m_shared.m_damages;
			switch (prefabName)
			{
			case "Club":
				damages.m_blunt = damage;
				break;
			case "KnifeFlint":
				damages.m_slash = damage / 2f;
				damages.m_pierce = damage / 2f;
				break;
			case "AxeStone":
				damages.m_slash = damage;
				break;
			case "SpearFlint":
			case "BowCrude":
				damages.m_pierce = damage;
				break;
			}
			prefab.m_itemData.m_shared.m_damages = damages;
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"{prefabName} damage set to {damage}.");
		}

		private void OnConfigurationSynchronized(object sender, ConfigurationSynchronizationEventArgs args)
		{
			SetItemWeights();
		}

		private void OnDestroy()
		{
			Harmony obj = harmony;
			if (obj != null)
			{
				obj.UnpatchSelf();
			}
		}
	}
	internal static class PluginInfo
	{
		public const string PluginVersion = "0.0.8";
	}
}