Decompiled source of ElementalStorms v1.0.0

ElementalStorms.dll

Decompiled 2 days ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Text;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using UnityEngine;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("ElementalStorms")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyDescription("A progression-driven storm system that adds dynamic hazards and atmospheric effects based on boss progression")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("ElementalStorms")]
[assembly: AssemblyTitle("ElementalStorms")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.Embedded]
	internal sealed class EmbeddedAttribute : Attribute
	{
	}
}
namespace System.Runtime.CompilerServices
{
	[CompilerGenerated]
	[Microsoft.CodeAnalysis.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 ElementalStorms
{
	[BepInPlugin("com.ruijven.elementalstorms", "ElementalStorms", "1.0.0")]
	internal class ElementalStormsPlugin : BaseUnityPlugin
	{
		private class StormClonerRunner : MonoBehaviour
		{
			private void Update()
			{
				if ((Object)(object)Player.m_localPlayer != (Object)null && (Object)(object)EnvMan.instance != (Object)null)
				{
					StormEnvironmentCloner.Initialize();
					Object.Destroy((Object)(object)((Component)this).gameObject);
				}
			}
		}

		public const string PluginGUID = "com.ruijven.elementalstorms";

		public const string PluginName = "ElementalStorms";

		public const string PluginVersion = "1.0.0";

		internal static ManualLogSource Logger;

		public static ConfigEntry<bool> EnableMod;

		public static ConfigEntry<bool> EnableStructuralDamage;

		public static ConfigEntry<float> DungeonProtectionAltitude;

		public static ConfigEntry<float> StructuralDamageAmount;

		public static float s_hudMessageTimer;

		public static bool s_hudMessageActive;

		public const float HUD_MESSAGE_DURATION = 5f;

		internal static ElementalStormsPlugin Instance { get; private set; }

		private void Awake()
		{
			//IL_0040: Unknown result type (might be due to invalid IL or missing references)
			//IL_0046: Expected O, but got Unknown
			Instance = this;
			Logger = ((BaseUnityPlugin)this).Logger;
			InitializeConfig();
			ScheduleStormCloning();
			ProjectileSpawner.Initialize();
			StatusEffectManager.Initialize();
			CreateUpdaterComponents();
			CreateStormEventManager();
			Harmony val = new Harmony("com.ruijven.elementalstorms");
			val.PatchAll(Assembly.GetExecutingAssembly());
			Logger.LogInfo((object)"ElementalStorms v1.0.0 loaded successfully!");
			Logger.LogInfo((object)"Progression-driven storm hazards activated!");
		}

		private void CreateUpdaterComponents()
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Expected O, but got Unknown
			GameObject val = new GameObject("ElementalWeather_Updaters");
			Object.DontDestroyOnLoad((Object)(object)val);
			val.AddComponent<LightningSystemUpdater>();
			val.AddComponent<HUDMessageUpdater>();
		}

		private void CreateStormEventManager()
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Expected O, but got Unknown
			GameObject val = new GameObject("ElementalStorms_StormEventManager");
			Object.DontDestroyOnLoad((Object)(object)val);
			val.AddComponent<ElementalStormManager>();
		}

		private void ScheduleStormCloning()
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Expected O, but got Unknown
			GameObject val = new GameObject("ElementalWeather_StormCloner");
			Object.DontDestroyOnLoad((Object)(object)val);
			val.AddComponent<StormClonerRunner>();
		}

		private void InitializeConfig()
		{
			//IL_001d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0027: Expected O, but got Unknown
			//IL_0048: Unknown result type (might be due to invalid IL or missing references)
			//IL_0052: Expected O, but got Unknown
			//IL_0085: Unknown result type (might be due to invalid IL or missing references)
			//IL_008f: Expected O, but got Unknown
			//IL_00c2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00cc: Expected O, but got Unknown
			EnableMod = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "EnableMod", true, new ConfigDescription("Master toggle for the entire ElementalWeather mod.", (AcceptableValueBase)null, Array.Empty<object>()));
			EnableStructuralDamage = ((BaseUnityPlugin)this).Config.Bind<bool>("Structural Damage", "EnableStructuralDamage", true, new ConfigDescription("Enable wind damage to exposed structures.", (AcceptableValueBase)null, Array.Empty<object>()));
			DungeonProtectionAltitude = ((BaseUnityPlugin)this).Config.Bind<float>("General", "DungeonProtectionAltitude", 2000f, new ConfigDescription("Altitude threshold above which weather hazards are disabled (protects dungeons).", (AcceptableValueBase)(object)new AcceptableValueRange<float>(1000f, 5000f), Array.Empty<object>()));
			StructuralDamageAmount = ((BaseUnityPlugin)this).Config.Bind<float>("Structural Damage", "StructuralDamageAmount", 0.5f, new ConfigDescription("Damage dealt to structures per update when conditions are met.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(0.1f, 10f), Array.Empty<object>()));
		}

		public static bool IsInDungeonAltitude()
		{
			//IL_0055: Unknown result type (might be due to invalid IL or missing references)
			if (EnableMod == null)
			{
				return false;
			}
			if (!EnableMod.Value)
			{
				return false;
			}
			if (DungeonProtectionAltitude == null)
			{
				return false;
			}
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer == (Object)null)
			{
				return false;
			}
			return ((Component)localPlayer).transform.position.y > DungeonProtectionAltitude.Value;
		}

		public static bool IsBossDefeated(string bossKey)
		{
			if ((Object)(object)ZoneSystem.instance == (Object)null)
			{
				return false;
			}
			return ZoneSystem.instance.GetGlobalKey(bossKey);
		}

		public static void ShowWeatherWarning(string message)
		{
			if ((Object)(object)MessageHud.instance != (Object)null)
			{
				MessageHud.instance.ShowMessage((MessageType)2, message, 0, (Sprite)null, false);
			}
		}

		public static void ShowWeatherWarningTopLeft(string message)
		{
			if ((Object)(object)MessageHud.instance != (Object)null)
			{
				MessageHud.instance.ShowMessage((MessageType)1, message, 0, (Sprite)null, false);
				s_hudMessageActive = true;
				s_hudMessageTimer = 0f;
			}
		}

		public static void ShowWeatherWarningTopCenter(string message)
		{
			if ((Object)(object)MessageHud.instance != (Object)null)
			{
				MessageHud.instance.ShowMessage((MessageType)2, message, 0, (Sprite)null, false);
				s_hudMessageActive = true;
				s_hudMessageTimer = 0f;
			}
		}
	}
	public class HUDMessageUpdater : MonoBehaviour
	{
		private void Update()
		{
			if (!ElementalStormsPlugin.s_hudMessageActive)
			{
				return;
			}
			ElementalStormsPlugin.s_hudMessageTimer += Time.deltaTime;
			if (ElementalStormsPlugin.s_hudMessageTimer >= 5f)
			{
				ElementalStormsPlugin.s_hudMessageActive = false;
				ElementalStormsPlugin.s_hudMessageTimer = 0f;
				if ((Object)(object)MessageHud.instance != (Object)null)
				{
					MessageHud.instance.ShowMessage((MessageType)1, "", 0, (Sprite)null, false);
				}
			}
		}
	}
	public class ElementalStormManager : MonoBehaviour
	{
		private float checkTimer = 0f;

		private const float CheckInterval = 1656f;

		private const float TriggerChance = 0.2f;

		private void Awake()
		{
		}

		private void Update()
		{
			if (Object.op_Implicit((Object)(object)ZNet.instance) && ZNet.instance.IsServer())
			{
				checkTimer += Time.deltaTime;
				if (checkTimer >= 1656f)
				{
					checkTimer = 0f;
					TryTriggerElementalStorm();
				}
			}
		}

		private void TryTriggerElementalStorm()
		{
			if (Random.value > 0.2f)
			{
				return;
			}
			List<string> list = new List<string>();
			if (ZoneSystem.instance.GetGlobalKey("defeated_eikthyr"))
			{
				list.Add("ES_Eikthyr");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_gdking"))
			{
				list.Add("ES_Elder");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_bonemass"))
			{
				list.Add("ES_Bonemass");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_moder"))
			{
				list.Add("ES_Moder");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_goblinking"))
			{
				list.Add("ES_Yagluth");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_thequeen"))
			{
				list.Add("ES_Queen");
			}
			if (ZoneSystem.instance.GetGlobalKey("defeated_fader"))
			{
				list.Add("ES_Fader");
			}
			if (list.Count == 0)
			{
				return;
			}
			string stormName = list[Random.Range(0, list.Count)];
			Player randomActivePlayer = GetRandomActivePlayer();
			if ((Object)(object)randomActivePlayer != (Object)null)
			{
				if (IsNearActiveBoss(randomActivePlayer))
				{
					ElementalStormsPlugin.Logger.LogInfo((object)"ElementalStorm: Aborted trigger. Target player is in a boss fight.");
				}
				else
				{
					TriggerStormForPlayer(randomActivePlayer, stormName);
				}
			}
		}

		private bool IsNearActiveBoss(Player player)
		{
			//IL_0013: Unknown result type (might be due to invalid IL or missing references)
			float num = 150f;
			List<Character> list = new List<Character>();
			Character.GetCharactersInRange(((Component)player).transform.position, num, list);
			foreach (Character item in list)
			{
				if (item.IsBoss() && !item.IsDead())
				{
					return true;
				}
			}
			return false;
		}

		private Player GetRandomActivePlayer()
		{
			List<Player> list = new List<Player>();
			foreach (Player allPlayer in Player.GetAllPlayers())
			{
				if ((Object)(object)allPlayer != (Object)null)
				{
					list.Add(allPlayer);
				}
			}
			if (list.Count == 0)
			{
				return null;
			}
			return list[Random.Range(0, list.Count)];
		}

		private void TriggerStormForPlayer(Player player, string stormName)
		{
			if ((Object)(object)EnvMan.instance != (Object)null)
			{
				EnvSetup customStorm = StormEnvironmentCloner.GetCustomStorm(stormName);
				if (customStorm != null)
				{
					EnvMan.instance.SetEnv(customStorm, 0f, 0f, 0f, 0f, 0f);
					ElementalStormsPlugin.Logger.LogInfo((object)("ElementalStorm: Triggered " + stormName + " for player " + player.GetPlayerName()));
					ElementalStormsPlugin.ShowWeatherWarningTopCenter(stormName.Replace("ES_", "") + "'s storm is approaching!");
				}
				else
				{
					ElementalStormsPlugin.Logger.LogWarning((object)("ElementalStorm: Could not find storm environment " + stormName));
				}
			}
		}
	}
	public class LightningSystem
	{
		private static LightningSystem s_instance;

		private float m_lightningTimer = 0f;

		private float m_nextLightningTime = 0f;

		private bool m_isActive = false;

		public static LightningSystem Instance
		{
			get
			{
				if (s_instance == null)
				{
					s_instance = new LightningSystem();
				}
				return s_instance;
			}
		}

		private LightningSystem()
		{
			ResetTimer();
		}

		public void Update(float dt)
		{
			if (ElementalStormsPlugin.EnableMod == null)
			{
				return;
			}
			if (!ElementalStormsPlugin.EnableMod.Value)
			{
				m_isActive = false;
				return;
			}
			if ((Object)(object)Player.m_localPlayer != (Object)null && ((Character)Player.m_localPlayer).IsDead())
			{
				m_isActive = false;
				return;
			}
			bool flag = ShouldBeActive();
			if (flag && !m_isActive)
			{
				m_isActive = true;
				ResetTimer();
				ElementalStormsPlugin.Logger.LogDebug((object)"Lightning system activated");
			}
			else if (!flag && m_isActive)
			{
				m_isActive = false;
				ElementalStormsPlugin.Logger.LogDebug((object)"Lightning system deactivated");
				return;
			}
			if (m_isActive && !ElementalStormsPlugin.IsInDungeonAltitude())
			{
				m_lightningTimer += dt;
				if (m_lightningTimer >= m_nextLightningTime)
				{
					StrikeLightning();
					ResetTimer();
				}
			}
		}

		private bool ShouldBeActive()
		{
			if ((Object)(object)EnvMan.instance == (Object)null)
			{
				return false;
			}
			if (EnvMan.instance.m_currentEnv == null)
			{
				return false;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			return name == "Eikthyr" || name == "ES_Eikthyr";
		}

		private void ResetTimer()
		{
			m_lightningTimer = 0f;
			float num = 4f;
			float num2 = 12f;
			m_nextLightningTime = Random.Range(num, num2);
		}

		private void StrikeLightning()
		{
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer == (Object)null || ((Character)localPlayer).IsDead())
			{
				return;
			}
			float radialDistance = GetRadialDistance();
			if (radialDistance < 0f)
			{
				ElementalStormsPlugin.Logger.LogDebug((object)"Lightning strike skipped (RNG roll)");
				return;
			}
			if (localPlayer.InShelter() && radialDistance < 50f)
			{
				ElementalStormsPlugin.Logger.LogDebug((object)"Lightning strike skipped (player in shelter, distance < 50m)");
				return;
			}
			Vector3 val = CalculateStrikePosition(((Component)localPlayer).transform.position, radialDistance);
			if ((Object)(object)ZoneSystem.instance != (Object)null)
			{
				val.y = ZoneSystem.instance.GetSolidHeight(val);
			}
			CreateLightningEffect(val);
			ApplyLightningDamage(val);
			ElementalStormsPlugin.Logger.LogDebug((object)$"Lightning struck at position: {val}");
		}

		private Vector3 CalculateStrikePosition(Vector3 playerPosition, float distance)
		{
			//IL_002d: 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_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			float num = Random.Range(0f, MathF.PI * 2f);
			Vector3 val = default(Vector3);
			((Vector3)(ref val))..ctor(Mathf.Cos(num) * distance, 0f, Mathf.Sin(num) * distance);
			return playerPosition + val;
		}

		private float GetRadialDistance()
		{
			float num = Random.Range(0f, 1f);
			if (num < 0.05f)
			{
				return Random.Range(0f, 10f);
			}
			if (num < 0.55f)
			{
				return Random.Range(10f, 25f);
			}
			if (num < 0.8f)
			{
				return Random.Range(25f, 35f);
			}
			return -1f;
		}

		private void CreateLightningEffect(Vector3 position)
		{
			//IL_0012: 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_0038: 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)
			if ((Object)(object)ZNetScene.instance == (Object)null)
			{
				CreateFallbackLightningEffect(position);
				return;
			}
			GameObject prefab = ZNetScene.instance.GetPrefab("fx_eikthyr_stomp");
			if ((Object)(object)prefab != (Object)null)
			{
				GameObject val = Object.Instantiate<GameObject>(prefab, position, Quaternion.identity);
				ZNetView component = val.GetComponent<ZNetView>();
				if ((Object)(object)component == (Object)null && (Object)(object)val != (Object)null)
				{
					Object.Destroy((Object)(object)val, 1f);
				}
			}
			else
			{
				CreateFallbackLightningEffect(position);
			}
		}

		private void CreateFallbackLightningEffect(Vector3 position)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Expected O, but got Unknown
			//IL_0012: 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)
			GameObject val = new GameObject("LightningFlash");
			val.transform.position = position;
			Light val2 = val.AddComponent<Light>();
			val2.type = (LightType)2;
			val2.color = Color.white;
			val2.intensity = 10f;
			val2.range = 50f;
			Object.Destroy((Object)(object)val, 0.1f);
		}

		private void ApplyLightningDamage(Vector3 position)
		{
			//IL_0015: 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_005f: Expected O, but got Unknown
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			//IL_008e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0093: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_0102: Expected O, but got Unknown
			//IL_0116: Unknown result type (might be due to invalid IL or missing references)
			//IL_012a: Unknown result type (might be due to invalid IL or missing references)
			//IL_012f: Unknown result type (might be due to invalid IL or missing references)
			float baseDamage = 20f;
			float num = CalculateScaledDamage(baseDamage);
			float num2 = 4f;
			Collider[] array = Physics.OverlapSphere(position, num2);
			Collider[] array2 = array;
			foreach (Collider val in array2)
			{
				Player component = ((Component)val).GetComponent<Player>();
				if ((Object)(object)component != (Object)null && !component.InShelter())
				{
					HitData val2 = new HitData();
					val2.m_damage.m_lightning = num;
					val2.m_attacker = default(ZDOID);
					val2.m_pushForce = 10f;
					Vector3 val3 = ((Component)component).transform.position - position;
					val2.m_dir = ((Vector3)(ref val3)).normalized;
					((Character)component).Damage(val2);
					ElementalStormsPlugin.Logger.LogDebug((object)$"Lightning dealt {num} damage to player");
					continue;
				}
				WearNTear component2 = ((Component)val).GetComponent<WearNTear>();
				if ((Object)(object)component2 != (Object)null && (Object)(object)component2.m_piece != (Object)null)
				{
					HitData val4 = new HitData();
					val4.m_damage.m_lightning = num;
					val4.m_attacker = default(ZDOID);
					val4.m_pushForce = 5f;
					val4.m_dir = Vector3.up;
					component2.Damage(val4);
					ElementalStormsPlugin.Logger.LogDebug((object)$"Lightning dealt {num} damage to structure: {((Object)component2).name}");
				}
			}
		}

		private float CalculateScaledDamage(float baseDamage)
		{
			int num = 0;
			if (ElementalStormsPlugin.IsBossDefeated("defeated_eikthyr"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_gdking"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_bonemass"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_moder"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_goblinking"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_thequeen"))
			{
				num++;
			}
			float num2 = 1f + (float)num * 0.1f;
			return baseDamage * num2;
		}

		public void ForceStrike(Vector3 position)
		{
			//IL_0015: 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)
			if (ElementalStormsPlugin.EnableMod.Value)
			{
				CreateLightningEffect(position);
				ApplyLightningDamage(position);
			}
		}

		public string GetDebugInfo()
		{
			return $"Lightning System - Active: {m_isActive}, Timer: {m_lightningTimer:F1}s/{m_nextLightningTime:F1}s";
		}
	}
	public class FireballSystem
	{
		private static FireballSystem s_instance;

		private float m_fireballTimer = 0f;

		private float m_nextFireballTime = 0f;

		private bool m_isActive = false;

		public static FireballSystem Instance
		{
			get
			{
				if (s_instance == null)
				{
					s_instance = new FireballSystem();
				}
				return s_instance;
			}
		}

		private FireballSystem()
		{
			ResetTimer();
		}

		public void Update(float dt)
		{
			if (ElementalStormsPlugin.EnableMod == null)
			{
				return;
			}
			if (!ElementalStormsPlugin.EnableMod.Value)
			{
				m_isActive = false;
				return;
			}
			if ((Object)(object)Player.m_localPlayer != (Object)null && ((Character)Player.m_localPlayer).IsDead())
			{
				m_isActive = false;
				return;
			}
			bool flag = ShouldBeActive();
			if (flag && !m_isActive)
			{
				m_isActive = true;
				ResetTimer();
				ElementalStormsPlugin.Logger.LogDebug((object)"Fireball system activated");
			}
			else if (!flag && m_isActive)
			{
				m_isActive = false;
				ElementalStormsPlugin.Logger.LogDebug((object)"Fireball system deactivated");
				return;
			}
			if (m_isActive && !ElementalStormsPlugin.IsInDungeonAltitude())
			{
				m_fireballTimer += dt;
				if (m_fireballTimer >= m_nextFireballTime)
				{
					DropFireball();
					ResetTimer();
				}
			}
		}

		private bool ShouldBeActive()
		{
			if ((Object)(object)EnvMan.instance == (Object)null)
			{
				return false;
			}
			if (EnvMan.instance.m_currentEnv == null)
			{
				return false;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			return name == "Fader" || name == "GoblinKing";
		}

		private void ResetTimer()
		{
			m_fireballTimer = 0f;
			float num = 2f;
			float num2 = 9f;
			m_nextFireballTime = Random.Range(num, num2);
		}

		private void DropFireball()
		{
			//IL_0086: Unknown result type (might be due to invalid IL or missing references)
			//IL_008c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
			Player localPlayer = Player.m_localPlayer;
			if ((Object)(object)localPlayer == (Object)null || ((Character)localPlayer).IsDead())
			{
				return;
			}
			float radialDistance = GetRadialDistance();
			if (radialDistance < 0f)
			{
				ElementalStormsPlugin.Logger.LogDebug((object)"Fireball dropped (RNG roll)");
				return;
			}
			if (localPlayer.InShelter() && radialDistance < 10f)
			{
				ElementalStormsPlugin.Logger.LogDebug((object)"Meteor skipped (player in shelter, distance < 10m)");
				return;
			}
			Vector3 val = CalculateDropPosition(((Component)localPlayer).transform.position, radialDistance);
			if ((Object)(object)ZoneSystem.instance != (Object)null)
			{
				val.y = ZoneSystem.instance.GetSolidHeight(val);
			}
			CreateFireballEffect(val);
			ElementalStormsPlugin.Logger.LogDebug((object)$"Meteor dropped at position: {val}");
		}

		private Vector3 CalculateDropPosition(Vector3 playerPosition, float distance)
		{
			//IL_002d: 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_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0034: Unknown result type (might be due to invalid IL or missing references)
			//IL_0037: Unknown result type (might be due to invalid IL or missing references)
			float num = Random.Range(0f, MathF.PI * 2f);
			Vector3 val = default(Vector3);
			((Vector3)(ref val))..ctor(Mathf.Cos(num) * distance, 0f, Mathf.Sin(num) * distance);
			return playerPosition + val;
		}

		private float GetRadialDistance()
		{
			float num = Random.Range(0f, 1f);
			if (num < 0.01f)
			{
				return Random.Range(0f, 10f);
			}
			if (num < 0.16f)
			{
				return Random.Range(10f, 50f);
			}
			if (num < 0.36f)
			{
				return Random.Range(50f, 100f);
			}
			return -1f;
		}

		private void CreateFireballEffect(Vector3 position)
		{
			//IL_0012: Unknown result type (might be due to invalid IL or missing references)
			//IL_0143: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00e3: Unknown result type (might be due to invalid IL or missing references)
			if ((Object)(object)ZNetScene.instance == (Object)null)
			{
				CreateFallbackFireballEffect(position);
				return;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			GameObject val = null;
			if (name == "GoblinKing")
			{
				val = ZNetScene.instance.GetPrefab("projectile_meteor");
			}
			else if (name == "Fader")
			{
				val = ZNetScene.instance.GetPrefab("projectile_ashlandmeteor");
				if ((Object)(object)val == (Object)null)
				{
					val = ZNetScene.instance.GetPrefab("projectile_ashlandmeteor2");
				}
			}
			if ((Object)(object)val == (Object)null)
			{
				val = ZNetScene.instance.GetPrefab("fx_bonemass_explosion");
			}
			if ((Object)(object)val == (Object)null)
			{
				val = ZNetScene.instance.GetPrefab("fx_eikthyr_stomp");
			}
			if ((Object)(object)val != (Object)null)
			{
				GameObject val2 = Object.Instantiate<GameObject>(val, position, Quaternion.identity);
				ZNetView component = val2.GetComponent<ZNetView>();
				if ((Object)(object)component == (Object)null)
				{
					MeteorSmash component2 = val2.GetComponent<MeteorSmash>();
					if ((Object)(object)component2 == (Object)null && (Object)(object)val2 != (Object)null)
					{
						Object.Destroy((Object)(object)val2, 1f);
					}
				}
			}
			else
			{
				CreateFallbackFireballEffect(position);
			}
		}

		private void CreateFallbackFireballEffect(Vector3 position)
		{
			//IL_0006: Unknown result type (might be due to invalid IL or missing references)
			//IL_000c: Expected O, but got Unknown
			//IL_0012: 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)
			GameObject val = new GameObject("FireballFlash");
			val.transform.position = position;
			Light val2 = val.AddComponent<Light>();
			val2.type = (LightType)2;
			val2.color = Color.red;
			val2.intensity = 10f;
			val2.range = 50f;
			Object.Destroy((Object)(object)val, 0.1f);
		}

		private void ApplyFireballDamage(Vector3 position)
		{
			//IL_0015: 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_005f: Expected O, but got Unknown
			//IL_0073: Unknown result type (might be due to invalid IL or missing references)
			//IL_008e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0093: Unknown result type (might be due to invalid IL or missing references)
			//IL_0094: Unknown result type (might be due to invalid IL or missing references)
			//IL_0099: Unknown result type (might be due to invalid IL or missing references)
			//IL_009d: Unknown result type (might be due to invalid IL or missing references)
			//IL_00a2: Unknown result type (might be due to invalid IL or missing references)
			//IL_00fb: Unknown result type (might be due to invalid IL or missing references)
			//IL_0102: Expected O, but got Unknown
			//IL_0116: Unknown result type (might be due to invalid IL or missing references)
			//IL_012a: Unknown result type (might be due to invalid IL or missing references)
			//IL_012f: Unknown result type (might be due to invalid IL or missing references)
			float baseDamage = 15f;
			float num = CalculateScaledDamage(baseDamage);
			float num2 = 4f;
			Collider[] array = Physics.OverlapSphere(position, num2);
			Collider[] array2 = array;
			foreach (Collider val in array2)
			{
				Player component = ((Component)val).GetComponent<Player>();
				if ((Object)(object)component != (Object)null && !component.InShelter())
				{
					HitData val2 = new HitData();
					val2.m_damage.m_fire = num;
					val2.m_attacker = default(ZDOID);
					val2.m_pushForce = 5f;
					Vector3 val3 = ((Component)component).transform.position - position;
					val2.m_dir = ((Vector3)(ref val3)).normalized;
					((Character)component).Damage(val2);
					ElementalStormsPlugin.Logger.LogDebug((object)$"Fireball dealt {num} fire damage to player");
					continue;
				}
				WearNTear component2 = ((Component)val).GetComponent<WearNTear>();
				if ((Object)(object)component2 != (Object)null && (Object)(object)component2.m_piece != (Object)null)
				{
					HitData val4 = new HitData();
					val4.m_damage.m_fire = num;
					val4.m_attacker = default(ZDOID);
					val4.m_pushForce = 3f;
					val4.m_dir = Vector3.up;
					component2.Damage(val4);
					ElementalStormsPlugin.Logger.LogDebug((object)$"Fireball dealt {num} fire damage to structure: {((Object)component2).name}");
				}
			}
		}

		private float CalculateScaledDamage(float baseDamage)
		{
			int num = 0;
			if (ElementalStormsPlugin.IsBossDefeated("defeated_eikthyr"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_gdking"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_bonemass"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_moder"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_goblinking"))
			{
				num++;
			}
			if (ElementalStormsPlugin.IsBossDefeated("defeated_thequeen"))
			{
				num++;
			}
			float num2 = 1f + (float)num * 0.1f;
			return baseDamage * num2;
		}

		public string GetDebugInfo()
		{
			return $"Fireball System - Active: {m_isActive}, Timer: {m_fireballTimer:F1}s/{m_nextFireballTime:F1}s";
		}
	}
	public class LightningSystemUpdater : MonoBehaviour
	{
		private void Update()
		{
			LightningSystem.Instance.Update(Time.deltaTime);
			FireballSystem.Instance.Update(Time.deltaTime);
		}
	}
	[HarmonyPatch]
	internal class ElementalWeatherPatches
	{
		private static string s_previousWeather;

		[HarmonyPatch(typeof(EnvMan), "SetEnv")]
		[HarmonyPostfix]
		private static void OnEnvironmentChanged()
		{
			if (ElementalStormsPlugin.EnableMod == null || !ElementalStormsPlugin.EnableMod.Value || (Object)(object)EnvMan.instance == (Object)null || EnvMan.instance.m_currentEnv == null || (Object)(object)Player.m_localPlayer == (Object)null)
			{
				return;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			if (s_previousWeather != null && s_previousWeather != name)
			{
				ElementalStormsPlugin.Logger.LogInfo((object)("[DEBUG] Weather system ending: " + s_previousWeather));
				ElementalStormsPlugin.Logger.LogInfo((object)("[DEBUG] Weather system starting: " + name));
			}
			s_previousWeather = name;
			switch (name)
			{
			case "Eikthyr":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_eikthyr"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Eikthyr's Thunderstorm");
				}
				break;
			case "GDKing":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_gdking"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("The Elder's Curse");
				}
				break;
			case "Bonemass":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_bonemass"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Poisoned Rain");
				}
				break;
			case "Moder":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_moder"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Blizzard");
				}
				break;
			case "GoblinKing":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_goblinking"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Yagluth's Curse");
				}
				break;
			case "Queen":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_thequeen"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Creeping Mist");
				}
				break;
			case "Fader":
				if (ElementalStormsPlugin.IsBossDefeated("defeated_fader"))
				{
					ElementalStormsPlugin.ShowWeatherWarningTopCenter("Fader's Tears");
				}
				break;
			}
		}
	}
	public static class PrefabDiscoverySystem
	{
		private class DiscoveryRunner : MonoBehaviour
		{
			private float m_delayTimer = 0f;

			private const float INITIALIZATION_DELAY = 5f;

			private void Update()
			{
				m_delayTimer += Time.deltaTime;
				if (m_delayTimer >= 5f)
				{
					if ((Object)(object)EnvMan.instance != (Object)null && (Object)(object)ZNetScene.instance != (Object)null)
					{
						ElementalStormsPlugin.Logger.LogInfo((object)"Game systems initialized, running prefab discovery...");
						RunDiscovery();
						Object.Destroy((Object)(object)((Component)this).gameObject);
					}
					else if (m_delayTimer >= 15f)
					{
						ElementalStormsPlugin.Logger.LogWarning((object)("Prefab discovery timeout - core systems not available. EnvMan: " + ((Object)(object)EnvMan.instance != (Object)null) + ", ZNetScene: " + ((Object)(object)ZNetScene.instance != (Object)null)));
						Object.Destroy((Object)(object)((Component)this).gameObject);
					}
				}
			}
		}

		private static bool s_hasRun = false;

		private static bool s_hasScheduled = false;

		private static readonly string DISCOVERY_FILE_PATH = Paths.ConfigPath + "/ElementalStorms_PrefabDiscovery.txt";

		public static void ScheduleDiscovery()
		{
			//IL_0038: Unknown result type (might be due to invalid IL or missing references)
			//IL_003e: Expected O, but got Unknown
			if (s_hasScheduled)
			{
				ElementalStormsPlugin.Logger.LogInfo((object)"Prefab discovery already scheduled, skipping.");
				return;
			}
			s_hasScheduled = true;
			ElementalStormsPlugin.Logger.LogInfo((object)"Scheduling prefab discovery system...");
			GameObject val = new GameObject("ElementalWeather_Discovery");
			Object.DontDestroyOnLoad((Object)(object)val);
			val.AddComponent<DiscoveryRunner>();
		}

		public static void RunDiscovery()
		{
			if (s_hasRun)
			{
				ElementalStormsPlugin.Logger.LogInfo((object)"Prefab discovery already run, skipping.");
				return;
			}
			s_hasRun = true;
			ElementalStormsPlugin.Logger.LogInfo((object)"Starting prefab discovery system...");
			try
			{
				StringBuilder stringBuilder = new StringBuilder();
				stringBuilder.AppendLine("=== Elemental Storms - Prefab Discovery Log ===");
				stringBuilder.AppendLine($"Generated: {DateTime.Now:yyyy-MM-dd HH:mm:ss}");
				stringBuilder.AppendLine("Valheim Version: " + Application.version);
				stringBuilder.AppendLine();
				DiscoverEnvironments(stringBuilder);
				DiscoverZNetScenePrefabs(stringBuilder);
				File.WriteAllText(DISCOVERY_FILE_PATH, stringBuilder.ToString());
				ElementalStormsPlugin.Logger.LogInfo((object)("Prefab discovery complete. Log saved to: " + DISCOVERY_FILE_PATH));
			}
			catch (Exception ex)
			{
				ElementalStormsPlugin.Logger.LogError((object)("Prefab discovery failed: " + ex.Message));
				ElementalStormsPlugin.Logger.LogError((object)ex.StackTrace);
			}
		}

		private static void DiscoverEnvironments(StringBuilder logBuilder)
		{
			logBuilder.AppendLine("=== AVAILABLE ENVIRONMENTS ===");
			if ((Object)(object)EnvMan.instance == (Object)null)
			{
				logBuilder.AppendLine("EnvMan.instance is null - cannot discover environments.");
				logBuilder.AppendLine();
				return;
			}
			FieldInfo field = typeof(EnvMan).GetField("m_environments", BindingFlags.Instance | BindingFlags.NonPublic);
			if (field == null)
			{
				logBuilder.AppendLine("Could not access m_environments field via reflection.");
				logBuilder.AppendLine();
				return;
			}
			if (!(field.GetValue(EnvMan.instance) is List<EnvSetup> list))
			{
				logBuilder.AppendLine("m_environments is null or not a List<EnvSetup>.");
				logBuilder.AppendLine();
				return;
			}
			logBuilder.AppendLine($"Total environments found: {list.Count}");
			logBuilder.AppendLine();
			List<EnvSetup> list2 = (from e in list
				where IsBossEnvironment(e.m_name)
				orderby e.m_name
				select e).ToList();
			List<EnvSetup> list3 = (from e in list
				where IsBiomeEnvironment(e.m_name)
				orderby e.m_name
				select e).ToList();
			List<EnvSetup> list4 = (from e in list
				where IsWeatherEnvironment(e.m_name)
				orderby e.m_name
				select e).ToList();
			List<EnvSetup> list5 = (from e in list
				where !IsBossEnvironment(e.m_name) && !IsBiomeEnvironment(e.m_name) && !IsWeatherEnvironment(e.m_name)
				orderby e.m_name
				select e).ToList();
			if (list2.Count > 0)
			{
				logBuilder.AppendLine("--- BOSS ENVIRONMENTS ---");
				foreach (EnvSetup item in list2)
				{
					LogEnvironmentDetails(item, logBuilder);
				}
				logBuilder.AppendLine();
			}
			if (list3.Count > 0)
			{
				logBuilder.AppendLine("--- BIOME ENVIRONMENTS ---");
				foreach (EnvSetup item2 in list3)
				{
					LogEnvironmentDetails(item2, logBuilder);
				}
				logBuilder.AppendLine();
			}
			if (list4.Count > 0)
			{
				logBuilder.AppendLine("--- WEATHER ENVIRONMENTS ---");
				foreach (EnvSetup item3 in list4)
				{
					LogEnvironmentDetails(item3, logBuilder);
				}
				logBuilder.AppendLine();
			}
			if (list5.Count <= 0)
			{
				return;
			}
			logBuilder.AppendLine("--- OTHER ENVIRONMENTS ---");
			foreach (EnvSetup item4 in list5)
			{
				LogEnvironmentDetails(item4, logBuilder);
			}
			logBuilder.AppendLine();
		}

		private static void LogEnvironmentDetails(EnvSetup env, StringBuilder logBuilder)
		{
			logBuilder.AppendLine("Name: " + env.m_name);
			logBuilder.AppendLine($"  Default: {env.m_default}");
			logBuilder.AppendLine($"  Wet: {env.m_isWet}, Freezing: {env.m_isFreezing}, Cold: {env.m_isCold}");
			logBuilder.AppendLine($"  Always Dark: {env.m_alwaysDark}");
			logBuilder.AppendLine($"  Wind Min: {env.m_windMin}, Wind Max: {env.m_windMax}");
			if (env.m_psystems != null && env.m_psystems.Length != 0)
			{
				logBuilder.AppendLine($"  Particle Systems ({env.m_psystems.Length}):");
				for (int i = 0; i < env.m_psystems.Length; i++)
				{
					if ((Object)(object)env.m_psystems[i] != (Object)null)
					{
						logBuilder.AppendLine($"    [{i}] {((Object)env.m_psystems[i]).name}");
					}
				}
			}
			if ((Object)(object)env.m_envObject != (Object)null)
			{
				logBuilder.AppendLine("  Environment Object: " + ((Object)env.m_envObject).name);
			}
			AudioClip ambientLoop = env.m_ambientLoop;
			if (!string.IsNullOrEmpty((ambientLoop != null) ? ((Object)ambientLoop).name : null))
			{
				logBuilder.AppendLine("  Ambient Loop: " + ((Object)env.m_ambientLoop).name);
			}
			logBuilder.AppendLine();
		}

		private static void DiscoverZNetScenePrefabs(StringBuilder logBuilder)
		{
			logBuilder.AppendLine("=== ZNETSCENE PREFABS ===");
			if ((Object)(object)ZNetScene.instance == (Object)null)
			{
				logBuilder.AppendLine("ZNetScene.instance is null - cannot discover prefabs.");
				logBuilder.AppendLine();
				return;
			}
			FieldInfo field = typeof(ZNetScene).GetField("m_namedPrefabs", BindingFlags.Instance | BindingFlags.NonPublic);
			if (field == null)
			{
				logBuilder.AppendLine("Could not access m_namedPrefabs field via reflection.");
				logBuilder.AppendLine();
				return;
			}
			if (!(field.GetValue(ZNetScene.instance) is Dictionary<int, GameObject> dictionary))
			{
				logBuilder.AppendLine("m_namedPrefabs is null or not a Dictionary<int, GameObject>.");
				logBuilder.AppendLine();
				return;
			}
			logBuilder.AppendLine($"Total prefabs found: {dictionary.Count}");
			logBuilder.AppendLine();
			List<GameObject> list = (from p in dictionary.Values
				where (Object)(object)p != (Object)null
				where IsStormRelatedPrefab(((Object)p).name)
				orderby ((Object)p).name
				select p).ToList();
			if (list.Count > 0)
			{
				logBuilder.AppendLine("--- STORM-RELATED PREFABS ---");
				foreach (GameObject item in list)
				{
					logBuilder.AppendLine("  " + ((Object)item).name);
				}
				logBuilder.AppendLine();
			}
			List<GameObject> list2 = (from p in dictionary.Values
				where (Object)(object)p != (Object)null
				where IsBossRelatedPrefab(((Object)p).name)
				orderby ((Object)p).name
				select p).ToList();
			if (list2.Count <= 0)
			{
				return;
			}
			logBuilder.AppendLine("--- BOSS-RELATED PREFABS ---");
			foreach (GameObject item2 in list2)
			{
				logBuilder.AppendLine("  " + ((Object)item2).name);
			}
			logBuilder.AppendLine();
		}

		private static bool IsBossEnvironment(string name)
		{
			if (string.IsNullOrEmpty(name))
			{
				return false;
			}
			string text = name.ToLower();
			return text.Contains("eikthyr") || text.Contains("gdking") || text.Contains("elder") || text.Contains("bonemass") || text.Contains("moder") || text.Contains("dragon") || text.Contains("goblin") || text.Contains("yagluth") || text.Contains("queen") || text.Contains("seeker") || text.Contains("fader");
		}

		private static bool IsBiomeEnvironment(string name)
		{
			if (string.IsNullOrEmpty(name))
			{
				return false;
			}
			string text = name.ToLower();
			return text.Contains("meadow") || text.Contains("forest") || text.Contains("blackforest") || text.Contains("swamp") || text.Contains("mountain") || text.Contains("plains") || text.Contains("mistland") || text.Contains("ashland") || text.Contains("deepnorth") || text.Contains("ocean") || text.Contains("ashlands");
		}

		private static bool IsWeatherEnvironment(string name)
		{
			if (string.IsNullOrEmpty(name))
			{
				return false;
			}
			string text = name.ToLower();
			return text.Contains("rain") || text.Contains("thunder") || text.Contains("snow") || text.Contains("storm") || text.Contains("fog") || text.Contains("mist") || text.Contains("clear") || text.Contains("cinder") || text.Contains("cloud");
		}

		private static bool IsStormRelatedPrefab(string name)
		{
			if (string.IsNullOrEmpty(name))
			{
				return false;
			}
			string text = name.ToLower();
			return text.Contains("meteor") || text.Contains("fireball") || text.Contains("lightning") || text.Contains("thunder") || text.Contains("rain") || text.Contains("snow") || text.Contains("fog") || text.Contains("mist") || text.Contains("storm") || text.Contains("tornado") || text.Contains("wind") || text.Contains("cinder") || text.Contains("ash");
		}

		private static bool IsBossRelatedPrefab(string name)
		{
			if (string.IsNullOrEmpty(name))
			{
				return false;
			}
			string text = name.ToLower();
			return text.Contains("eikthyr") || text.Contains("gd_king") || text.Contains("gdking") || text.Contains("elder") || text.Contains("bonemass") || text.Contains("moder") || text.Contains("dragon") || text.Contains("goblin") || text.Contains("yagluth") || text.Contains("queen") || text.Contains("seeker") || text.Contains("fader") || text.Contains("boss");
		}
	}
	public static class ProjectileSpawner
	{
		public class ProjectileConfig
		{
			public string PrefabName { get; set; }

			public float SpawnInterval { get; set; } = 5f;


			public float MinDistance { get; set; } = 1f;


			public float MaxDistance { get; set; } = 5f;


			public float Damage { get; set; } = 10f;


			public string StormName { get; set; }

			public string BossKey { get; set; }

			public float DamageMultiplier { get; set; } = 1f;


			public float SpawnRadius { get; set; } = 0f;


			public int SpawnCount { get; set; } = 1;


			public bool CheckEnvActive { get; set; } = false;

		}

		private class ProjectileSpawnerUpdater : MonoBehaviour
		{
			private Dictionary<string, Dictionary<string, float>> m_spawnTimers = new Dictionary<string, Dictionary<string, float>>();

			private Dictionary<string, List<GameObject>> m_spawnedObjects = new Dictionary<string, List<GameObject>>();

			private void Start()
			{
				foreach (KeyValuePair<string, List<ProjectileConfig>> s_projectileConfig in s_projectileConfigs)
				{
					m_spawnTimers[s_projectileConfig.Key] = new Dictionary<string, float>();
					foreach (ProjectileConfig item in s_projectileConfig.Value)
					{
						m_spawnTimers[s_projectileConfig.Key][item.PrefabName] = 0f;
					}
					m_spawnedObjects[s_projectileConfig.Key] = new List<GameObject>();
				}
			}

			private void Update()
			{
				string text = (((Object)(object)EnvMan.instance != (Object)null) ? EnvMan.instance.GetCurrentEnvironment().m_name : "");
				if (text == "ES_Queen" && (Object)(object)Player.m_localPlayer != (Object)null && !Object.op_Implicit((Object)(object)((Component)Player.m_localPlayer).GetComponent<QueenStormMistEffect>()))
				{
					TriggerQueenMist();
				}
				foreach (KeyValuePair<string, List<ProjectileConfig>> s_projectileConfig in s_projectileConfigs)
				{
					string key = s_projectileConfig.Key;
					List<ProjectileConfig> value = s_projectileConfig.Value;
					string text2 = ((value.Count > 0) ? value[0].StormName : key);
					if (text != text2)
					{
						if (!m_spawnedObjects.ContainsKey(key))
						{
							continue;
						}
						foreach (GameObject item in m_spawnedObjects[key])
						{
							if ((Object)(object)item != (Object)null)
							{
								Object.Destroy((Object)(object)item);
							}
						}
						m_spawnedObjects[key].Clear();
						continue;
					}
					foreach (ProjectileConfig item2 in value)
					{
						m_spawnTimers[key][item2.PrefabName] += Time.deltaTime;
						if (m_spawnTimers[key][item2.PrefabName] >= item2.SpawnInterval)
						{
							m_spawnTimers[key][item2.PrefabName] = 0f;
							TrySpawnProjectile(item2);
						}
					}
				}
			}

			private void TrySpawnProjectile(ProjectileConfig config)
			{
				if (!ElementalStormsPlugin.IsBossDefeated(config.BossKey))
				{
					ElementalStormsPlugin.Logger.LogDebug((object)("Boss " + config.BossKey + " not defeated, skipping spawn of " + config.PrefabName));
				}
				else
				{
					if ((Object)(object)EnvMan.instance == (Object)null)
					{
						return;
					}
					string name = EnvMan.instance.GetCurrentEnvironment().m_name;
					if (name != config.StormName)
					{
						ElementalStormsPlugin.Logger.LogDebug((object)("Current env " + name + " != " + config.StormName + ", skipping spawn of " + config.PrefabName));
						return;
					}
					if (config.CheckEnvActive)
					{
					}
					Player localPlayer = Player.m_localPlayer;
					if (!((Object)(object)localPlayer == (Object)null))
					{
						float minDistance = (localPlayer.InShelter() ? 20f : config.MinDistance);
						float maxDistance = (localPlayer.InShelter() ? 35f : config.MaxDistance);
						SpawnPrefabNearPlayer(config, localPlayer, minDistance, maxDistance);
					}
				}
			}

			private void SpawnPrefabNearPlayer(ProjectileConfig config, Player player, float minDistance, float maxDistance)
			{
				//IL_0008: 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_000e: 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_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)
				//IL_0037: 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_00ff: Unknown result type (might be due to invalid IL or missing references)
				//IL_011a: Unknown result type (might be due to invalid IL or missing references)
				//IL_011b: Unknown result type (might be due to invalid IL or missing references)
				//IL_0211: Unknown result type (might be due to invalid IL or missing references)
				//IL_01a2: Unknown result type (might be due to invalid IL or missing references)
				try
				{
					Vector3 position = ((Component)player).transform.position;
					Vector3 val = position;
					int num = ((config.SpawnCount <= 0) ? 1 : config.SpawnCount);
					if (config.SpawnRadius > 0f)
					{
						val = position;
						num = 1;
					}
					else
					{
						float num2 = Random.Range(minDistance, maxDistance);
						float num3 = Random.Range(0f, 360f);
						Vector3 val2 = default(Vector3);
						((Vector3)(ref val2))..ctor(Mathf.Cos(num3) * num2, 0f, Mathf.Sin(num3) * num2);
						val = position + val2;
					}
					if ((Object)(object)ZNetScene.instance == (Object)null)
					{
						ElementalStormsPlugin.Logger.LogWarning((object)"ZNetScene.instance is null, cannot spawn prefab.");
						return;
					}
					GameObject prefab = ZNetScene.instance.GetPrefab(StringExtensionMethods.GetStableHashCode(config.PrefabName));
					if ((Object)(object)prefab == (Object)null)
					{
						ElementalStormsPlugin.Logger.LogWarning((object)("Could not find prefab: " + config.PrefabName));
						return;
					}
					ElementalStormsPlugin.Logger.LogDebug((object)$"Spawning prefab {config.PrefabName} at {val}");
					for (int i = 0; i < num; i++)
					{
						GameObject val3 = Object.Instantiate<GameObject>(prefab, val, Quaternion.identity);
						if (config.SpawnRadius > 0f && config.PrefabName == "MistArea")
						{
							Mister val4 = val3.GetComponent<Mister>();
							if ((Object)(object)val4 == (Object)null)
							{
								val4 = val3.AddComponent<Mister>();
								ElementalStormsPlugin.Logger.LogInfo((object)"Added Mister component to MistArea prefab");
							}
							val4.m_radius = config.SpawnRadius;
							ElementalStormsPlugin.Logger.LogInfo((object)$"Set MistArea radius to {config.SpawnRadius}m at {val}");
						}
						if (m_spawnedObjects.ContainsKey(config.StormName))
						{
							m_spawnedObjects[config.StormName].Add(val3);
						}
					}
					ElementalStormsPlugin.Logger.LogDebug((object)$"Spawned {num} {config.PrefabName}(s) at {val}");
				}
				catch (Exception ex)
				{
					ElementalStormsPlugin.Logger.LogError((object)("Failed to spawn prefab " + config.PrefabName + ": " + ex.Message));
				}
			}
		}

		private class QueenStormMistEffect : MonoBehaviour
		{
			private GameObject instantiatedMist;

			private void Start()
			{
				SpawnMist();
			}

			private void Update()
			{
				if ((Object)(object)EnvMan.instance != (Object)null)
				{
					string name = EnvMan.instance.GetCurrentEnvironment().m_name;
					if (name != "ES_Queen")
					{
						RemoveMist();
					}
				}
			}

			private void SpawnMist()
			{
				//IL_002a: Unknown result type (might be due to invalid IL or missing references)
				//IL_002f: Unknown result type (might be due to invalid IL or missing references)
				GameObject prefab = ZNetScene.instance.GetPrefab(StringExtensionMethods.GetStableHashCode("MistArea"));
				if ((Object)(object)prefab != (Object)null)
				{
					instantiatedMist = Object.Instantiate<GameObject>(prefab, ((Component)this).transform.position, Quaternion.identity);
					instantiatedMist.transform.SetParent(((Component)this).transform);
					Mister val = instantiatedMist.GetComponent<Mister>();
					if ((Object)(object)val == (Object)null)
					{
						val = instantiatedMist.AddComponent<Mister>();
					}
					val.m_radius = 20f;
					ElementalStormsPlugin.Logger.LogInfo((object)"Queen mist spawned and attached to player");
				}
				else
				{
					ElementalStormsPlugin.Logger.LogWarning((object)"QueenStormMod: MistArea prefab not found!");
				}
			}

			public void RemoveMist()
			{
				if ((Object)(object)instantiatedMist != (Object)null)
				{
					Object.Destroy((Object)(object)instantiatedMist);
				}
				Object.Destroy((Object)(object)this);
			}

			private void OnDestroy()
			{
				if ((Object)(object)instantiatedMist != (Object)null)
				{
					Object.Destroy((Object)(object)instantiatedMist);
				}
			}
		}

		private static Dictionary<string, List<ProjectileConfig>> s_projectileConfigs = new Dictionary<string, List<ProjectileConfig>>();

		private static GameObject s_spawnerHolder;

		public static void Initialize()
		{
			//IL_0016: Unknown result type (might be due to invalid IL or missing references)
			//IL_0020: Expected O, but got Unknown
			if ((Object)(object)s_spawnerHolder == (Object)null)
			{
				s_spawnerHolder = new GameObject("ElementalStorms_ProjectileSpawner");
				Object.DontDestroyOnLoad((Object)(object)s_spawnerHolder);
			}
			s_projectileConfigs.Clear();
			ConfigureElderProjectiles();
			ConfigureBonemassAOEs();
			ConfigureModerProjectiles();
			ConfigureYagluthMeteors();
			ConfigureFaderMeteors();
			ConfigureQueenMist();
			if ((Object)(object)s_spawnerHolder.GetComponent<ProjectileSpawnerUpdater>() == (Object)null)
			{
				s_spawnerHolder.AddComponent<ProjectileSpawnerUpdater>();
			}
		}

		private static void ConfigureElderProjectiles()
		{
			ProjectileConfig item = new ProjectileConfig
			{
				PrefabName = "TentaRoot",
				SpawnInterval = 2f,
				MinDistance = 1f,
				MaxDistance = 3f,
				Damage = 10f,
				StormName = "ES_Elder",
				BossKey = "defeated_gdking",
				SpawnCount = 1
			};
			s_projectileConfigs["Elder"] = new List<ProjectileConfig> { item };
		}

		private static void ConfigureBonemassAOEs()
		{
			ProjectileConfig item = new ProjectileConfig
			{
				PrefabName = "bonemass_aoe",
				SpawnInterval = 5f,
				MinDistance = 1f,
				MaxDistance = 3f,
				Damage = 0f,
				StormName = "ES_Bonemass",
				BossKey = "defeated_bonemass"
			};
			ProjectileConfig item2 = new ProjectileConfig
			{
				PrefabName = "bee_aoe",
				SpawnInterval = 15f,
				MinDistance = 1f,
				MaxDistance = 3f,
				Damage = 0f,
				StormName = "ES_Bonemass",
				BossKey = "defeated_bonemass",
				CheckEnvActive = true
			};
			s_projectileConfigs["Bonemass"] = new List<ProjectileConfig> { item, item2 };
		}

		private static void ConfigureModerProjectiles()
		{
			s_projectileConfigs["Moder"] = new List<ProjectileConfig>();
		}

		private static void ConfigureYagluthMeteors()
		{
			ProjectileConfig item = new ProjectileConfig
			{
				PrefabName = "DvergerStaffFire_clusterbomb_aoe",
				SpawnInterval = 3f,
				MinDistance = 1f,
				MaxDistance = 10f,
				Damage = 10f,
				StormName = "ES_Yagluth",
				BossKey = "defeated_goblinking",
				DamageMultiplier = 0.33f
			};
			s_projectileConfigs["Yagluth"] = new List<ProjectileConfig> { item };
		}

		private static void ConfigureFaderMeteors()
		{
			ProjectileConfig item = new ProjectileConfig
			{
				PrefabName = "Fader_DroppedFire_AOE",
				SpawnInterval = 5f,
				MinDistance = 3f,
				MaxDistance = 10f,
				Damage = 10f,
				StormName = "ES_Fader",
				BossKey = "defeated_fader",
				DamageMultiplier = 0.33f
			};
			s_projectileConfigs["Fader"] = new List<ProjectileConfig> { item };
		}

		private static void ConfigureQueenMist()
		{
			ProjectileConfig item = new ProjectileConfig
			{
				PrefabName = "MistArea",
				SpawnInterval = 10f,
				MinDistance = 0f,
				MaxDistance = 0f,
				Damage = 0f,
				StormName = "ES_Queen",
				BossKey = "defeated_thequeen",
				SpawnRadius = 20f
			};
			s_projectileConfigs["Queen"] = new List<ProjectileConfig> { item };
		}

		public static List<ProjectileConfig> GetConfigs(string name)
		{
			if (s_projectileConfigs.TryGetValue(name, out var value))
			{
				return value;
			}
			return null;
		}

		public static void UpdateConfig(string name, Action<ProjectileConfig> updateAction)
		{
			if (!s_projectileConfigs.TryGetValue(name, out var value))
			{
				return;
			}
			foreach (ProjectileConfig item in value)
			{
				updateAction(item);
			}
		}

		public static void TriggerQueenMist()
		{
			if ((Object)(object)Player.m_localPlayer != (Object)null && !Object.op_Implicit((Object)(object)((Component)Player.m_localPlayer).GetComponent<QueenStormMistEffect>()))
			{
				((Component)Player.m_localPlayer).gameObject.AddComponent<QueenStormMistEffect>();
				ElementalStormsPlugin.Logger.LogInfo((object)"Queen mist effect triggered on player");
			}
		}
	}
	public class SE_GaleExposure : StatusEffect
	{
		private float m_originalStaminaRegenTimeMultiplier = 1f;

		private bool m_shouldRemove = false;

		public SE_GaleExposure()
		{
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Expected O, but got Unknown
			//IL_004f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Expected O, but got Unknown
			((Object)this).name = "Moder's Blizzard";
			base.m_icon = null;
			base.m_tooltip = "Moder's Blizzard: Severe winds are draining your stamina.";
			base.m_ttl = 0f;
			base.m_startEffects = new EffectList();
			base.m_stopEffects = new EffectList();
		}

		public override void Setup(Character character)
		{
			((StatusEffect)this).Setup(character);
			Player val = (Player)(object)((character is Player) ? character : null);
			if (val != null)
			{
				m_originalStaminaRegenTimeMultiplier = val.m_staminaRegenTimeMultiplier;
				ElementalStormsPlugin.Logger.LogDebug((object)("SE_GaleExposure applied to player, storing original stamina regen multiplier: " + m_originalStaminaRegenTimeMultiplier));
			}
		}

		public override void UpdateStatusEffect(float dt)
		{
			((StatusEffect)this).UpdateStatusEffect(dt);
			if (m_shouldRemove)
			{
				Character character = base.m_character;
				RestoreStaminaRegen((Player)(object)((character is Player) ? character : null));
				base.m_ttl = 0f;
			}
			else
			{
				if (ElementalStormsPlugin.EnableMod == null || !ElementalStormsPlugin.EnableMod.Value)
				{
					return;
				}
				Character character2 = base.m_character;
				Player val = (Player)(object)((character2 is Player) ? character2 : null);
				if (val != null)
				{
					if (val.InShelter())
					{
						ElementalStormsPlugin.Logger.LogDebug((object)"Player found shelter, removing Gale Exposure");
						m_shouldRemove = true;
					}
					else
					{
						ApplyStaminaPenalty(val);
					}
				}
			}
		}

		private void ApplyStaminaPenalty(Player player)
		{
			float num = 0.4f;
			player.m_staminaRegenTimeMultiplier = m_originalStaminaRegenTimeMultiplier * (1f + num);
		}

		private void RestoreStaminaRegen(Player player)
		{
			player.m_staminaRegenTimeMultiplier = m_originalStaminaRegenTimeMultiplier;
		}
	}
	public class SE_ForestRain : StatusEffect
	{
		private float m_originalStaminaRegenTimeMultiplier = 1f;

		private bool m_shouldRemove = false;

		public SE_ForestRain()
		{
			//IL_0044: Unknown result type (might be due to invalid IL or missing references)
			//IL_004e: Expected O, but got Unknown
			//IL_004f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0059: Expected O, but got Unknown
			((Object)this).name = "The Elder's Curse";
			base.m_icon = null;
			base.m_tooltip = "The Elder's Curse: The Elder's curse makes you weary.";
			base.m_ttl = 0f;
			base.m_startEffects = new EffectList();
			base.m_stopEffects = new EffectList();
		}

		public override void Setup(Character character)
		{
			((StatusEffect)this).Setup(character);
			Player val = (Player)(object)((character is Player) ? character : null);
			if (val != null)
			{
				m_originalStaminaRegenTimeMultiplier = val.m_staminaRegenTimeMultiplier;
				ElementalStormsPlugin.Logger.LogDebug((object)("SE_ForestRain applied to player, storing original stamina regen multiplier: " + m_originalStaminaRegenTimeMultiplier));
			}
		}

		public override void UpdateStatusEffect(float dt)
		{
			((StatusEffect)this).UpdateStatusEffect(dt);
			if (m_shouldRemove)
			{
				Character character = base.m_character;
				RestoreStaminaRegen((Player)(object)((character is Player) ? character : null));
				base.m_ttl = 0f;
			}
			else
			{
				if (ElementalStormsPlugin.EnableMod == null || !ElementalStormsPlugin.EnableMod.Value)
				{
					return;
				}
				Character character2 = base.m_character;
				Player val = (Player)(object)((character2 is Player) ? character2 : null);
				if (val != null)
				{
					if (val.InShelter())
					{
						ElementalStormsPlugin.Logger.LogDebug((object)"Player found shelter, removing Forest Rain");
						m_shouldRemove = true;
					}
					else
					{
						ApplyStaminaPenalty(val);
					}
				}
			}
		}

		private void ApplyStaminaPenalty(Player player)
		{
			float num = 0.5f;
			player.m_staminaRegenTimeMultiplier = m_originalStaminaRegenTimeMultiplier * (1f + num);
		}

		private void RestoreStaminaRegen(Player player)
		{
			player.m_staminaRegenTimeMultiplier = m_originalStaminaRegenTimeMultiplier;
		}
	}
	public static class StatusEffectManager
	{
		private static SE_GaleExposure s_galeExposureTemplate;

		private static SE_ForestRain s_forestRainTemplate;

		public static void Initialize()
		{
			s_galeExposureTemplate = ScriptableObject.CreateInstance<SE_GaleExposure>();
			s_forestRainTemplate = ScriptableObject.CreateInstance<SE_ForestRain>();
		}

		public static void ApplyGaleExposure(Character character)
		{
			if (ElementalStormsPlugin.EnableMod != null && ElementalStormsPlugin.EnableMod.Value && !((Object)(object)character == (Object)null) && !character.IsDead())
			{
				int stableHashCode = StringExtensionMethods.GetStableHashCode("Moder's Blizzard");
				if (!((Object)(object)character.GetSEMan().GetStatusEffect(stableHashCode) != (Object)null))
				{
					SE_GaleExposure sE_GaleExposure = Object.Instantiate<SE_GaleExposure>(s_galeExposureTemplate);
					character.GetSEMan().AddStatusEffect((StatusEffect)(object)sE_GaleExposure, false, 0, 0f);
					ElementalStormsPlugin.Logger.LogDebug((object)("Applied Moder's Blizzard to: " + ((Object)character).name));
				}
			}
		}

		public static void ApplyForestRain(Character character)
		{
			if (ElementalStormsPlugin.EnableMod != null && ElementalStormsPlugin.EnableMod.Value && !((Object)(object)character == (Object)null) && !character.IsDead())
			{
				int stableHashCode = StringExtensionMethods.GetStableHashCode("The Elder's Curse");
				if (!((Object)(object)character.GetSEMan().GetStatusEffect(stableHashCode) != (Object)null))
				{
					SE_ForestRain sE_ForestRain = Object.Instantiate<SE_ForestRain>(s_forestRainTemplate);
					character.GetSEMan().AddStatusEffect((StatusEffect)(object)sE_ForestRain, false, 0, 0f);
					ElementalStormsPlugin.Logger.LogDebug((object)("Applied The Elder's Curse to: " + ((Object)character).name));
				}
			}
		}

		public static void RemoveAllCustomEffects(Character character)
		{
			if ((Object)(object)character == (Object)null)
			{
				return;
			}
			SEMan sEMan = character.GetSEMan();
			if (sEMan != null)
			{
				int stableHashCode = StringExtensionMethods.GetStableHashCode("Moder's Blizzard");
				StatusEffect statusEffect = sEMan.GetStatusEffect(stableHashCode);
				if ((Object)(object)statusEffect != (Object)null)
				{
					sEMan.RemoveStatusEffect(statusEffect, false);
				}
				int stableHashCode2 = StringExtensionMethods.GetStableHashCode("The Elder's Curse");
				StatusEffect statusEffect2 = sEMan.GetStatusEffect(stableHashCode2);
				if ((Object)(object)statusEffect2 != (Object)null)
				{
					sEMan.RemoveStatusEffect(statusEffect2, false);
				}
			}
		}
	}
	public static class StormEnvironmentCloner
	{
		private class PoisonMonitor : MonoBehaviour
		{
			private const float CHECK_INTERVAL = 0.5f;

			private float m_checkTimer = 0f;

			private void Update()
			{
				if (!((Object)(object)EnvMan.instance == (Object)null) && !((Object)(object)Player.m_localPlayer == (Object)null))
				{
					m_checkTimer += Time.deltaTime;
					if (!(m_checkTimer < 0.5f))
					{
						m_checkTimer = 0f;
						Player localPlayer = Player.m_localPlayer;
						string name = EnvMan.instance.GetCurrentEnvironment().m_name;
						bool flag = name == "ES_Bonemass";
					}
				}
			}
		}

		private static Dictionary<string, EnvSetup> s_customEnvironments = new Dictionary<string, EnvSetup>();

		public static void Initialize()
		{
			//IL_0036: Unknown result type (might be due to invalid IL or missing references)
			//IL_003c: Expected O, but got Unknown
			if ((Object)(object)EnvMan.instance == (Object)null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"EnvMan not available, cannot initialize storm environments yet.");
				return;
			}
			try
			{
				CreateCustomStorms();
				RegisterCustomEnvironments();
				GameObject val = new GameObject("ES_PoisonMonitor");
				val.AddComponent<PoisonMonitor>();
				Object.DontDestroyOnLoad((Object)(object)val);
			}
			catch (Exception ex)
			{
				ElementalStormsPlugin.Logger.LogError((object)("Failed to initialize storm environment cloner: " + ex.Message));
				ElementalStormsPlugin.Logger.LogError((object)ex.StackTrace);
			}
		}

		private static void CreateCustomStorms()
		{
			if ((Object)(object)EnvMan.instance == (Object)null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"EnvMan.instance is null, cannot create custom storms.");
				return;
			}
			CreateEikthyrStorm();
			CreateElderStorm();
			CreateBonemassStorm();
			CreateModerStorm();
			CreateYagluthStorm();
			CreateQueenStorm();
			CreateFaderStorm();
		}

		private static void CreateEikthyrStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("ThunderStorm");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find ThunderStorm environment, trying Eikthyr.");
				env = EnvMan.instance.GetEnv("Eikthyr");
				if (env == null)
				{
					ElementalStormsPlugin.Logger.LogWarning((object)"Could not find Eikthyr environment for cloning.");
					return;
				}
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Eikthyr";
			val.m_windMin = 1.4f;
			val.m_windMax = 2f;
			s_customEnvironments["ES_Eikthyr"] = val;
		}

		private static void CreateElderStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("Darklands_dark");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find Darklands_dark environment, trying GDKing.");
				env = EnvMan.instance.GetEnv("GDKing");
				if (env == null)
				{
					ElementalStormsPlugin.Logger.LogWarning((object)"Could not find GDKing environment for cloning.");
					return;
				}
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Elder";
			val.m_isWet = true;
			val.m_windMin = 0.8f;
			val.m_windMax = 1.6f;
			s_customEnvironments["ES_Elder"] = val;
		}

		private static void CreateBonemassStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("Bonemass");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find Bonemass environment for cloning.");
				return;
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Bonemass";
			val.m_isWet = true;
			val.m_windMin = 0.6f;
			val.m_windMax = 1.4f;
			s_customEnvironments["ES_Bonemass"] = val;
		}

		private static void CreateModerStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("SnowStorm");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find SnowStorm environment for cloning.");
				return;
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Moder";
			val.m_isFreezing = true;
			val.m_isFreezingAtNight = true;
			val.m_isCold = true;
			val.m_windMin = 1.6f;
			val.m_windMax = 2f;
			s_customEnvironments["ES_Moder"] = val;
		}

		private static void CreateYagluthStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("GoblinKing");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find GoblinKing environment for cloning.");
				return;
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Yagluth";
			val.m_windMin = 1.4f;
			val.m_windMax = 2f;
			s_customEnvironments["ES_Yagluth"] = val;
		}

		private static void CreateQueenStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("Mistlands_rain");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find Mistlands_rain environment for cloning.");
				return;
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Queen";
			val.m_windMin = 1.4f;
			val.m_windMax = 2f;
			s_customEnvironments["ES_Queen"] = val;
		}

		private static void CreateFaderStorm()
		{
			EnvSetup env = EnvMan.instance.GetEnv("Fader");
			if (env == null)
			{
				ElementalStormsPlugin.Logger.LogWarning((object)"Could not find Fader environment for cloning.");
				return;
			}
			EnvSetup val = env.Clone();
			val.m_name = "ES_Fader";
			val.m_windMin = 1.6f;
			val.m_windMax = 2f;
			s_customEnvironments["ES_Fader"] = val;
		}

		private static void RegisterCustomEnvironments()
		{
			foreach (KeyValuePair<string, EnvSetup> s_customEnvironment in s_customEnvironments)
			{
				try
				{
					if (EnvMan.instance.GetEnv(s_customEnvironment.Key) == null)
					{
						EnvMan.instance.AppendEnvironment(s_customEnvironment.Value);
						ElementalStormsPlugin.Logger.LogDebug((object)("Registered custom environment: " + s_customEnvironment.Key));
					}
					else
					{
						ElementalStormsPlugin.Logger.LogDebug((object)("Environment " + s_customEnvironment.Key + " already registered, skipping."));
					}
				}
				catch (Exception ex)
				{
					ElementalStormsPlugin.Logger.LogError((object)("Failed to register environment " + s_customEnvironment.Key + ": " + ex.Message));
				}
			}
		}

		public static EnvSetup GetCustomStorm(string stormName)
		{
			if (s_customEnvironments.TryGetValue(stormName, out var value))
			{
				return value;
			}
			return null;
		}

		public static string[] GetCustomStormNames()
		{
			return new List<string>(s_customEnvironments.Keys).ToArray();
		}
	}
	[HarmonyPatch]
	internal class WindSystem
	{
		[HarmonyPatch(typeof(WearNTear), "UpdateWear")]
		[HarmonyPostfix]
		private static void ApplyWindDamage(WearNTear __instance)
		{
			if (ElementalStormsPlugin.EnableMod == null || ElementalStormsPlugin.EnableStructuralDamage == null || !ElementalStormsPlugin.EnableMod.Value || !ElementalStormsPlugin.EnableStructuralDamage.Value || ElementalStormsPlugin.IsInDungeonAltitude() || (Object)(object)__instance.m_piece == (Object)null || (Object)(object)EnvMan.instance == (Object)null || EnvMan.instance.m_currentEnv == null)
			{
				return;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			if (name.StartsWith("ES_"))
			{
				float windIntensity = EnvMan.instance.GetWindIntensity();
				if (!float.IsNaN(windIntensity))
				{
					windIntensity = GetEqualWindIntensity(windIntensity);
					ElementalStormsPlugin.Logger.LogDebug((object)$"Structural wind intensity: {windIntensity:F2}");
					ApplyWindStructuralDamage(__instance);
				}
			}
		}

		private static float GetEqualWindIntensity(float baseIntensity)
		{
			if ((Object)(object)EnvMan.instance == (Object)null || EnvMan.instance.m_currentEnv == null)
			{
				return baseIntensity;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			if (name.StartsWith("ES_"))
			{
				return Mathf.Max(baseIntensity, 0.7f);
			}
			return baseIntensity;
		}

		private static void ApplyWindStructuralDamage(WearNTear wearNTear)
		{
			//IL_0025: Unknown result type (might be due to invalid IL or missing references)
			//IL_002b: Expected O, but got Unknown
			//IL_003d: 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_005c: 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)
			if (ElementalStormsPlugin.StructuralDamageAmount != null)
			{
				float value = ElementalStormsPlugin.StructuralDamageAmount.Value;
				value *= 0.2f;
				HitData val = new HitData();
				val.m_damage.m_pickaxe = value;
				val.m_attacker = default(ZDOID);
				val.m_pushForce = 0f;
				val.m_dir = (((Object)(object)EnvMan.instance != (Object)null) ? EnvMan.instance.GetWindDir() : Vector3.up);
				wearNTear.Damage(val);
				ElementalStormsPlugin.Logger.LogDebug((object)$"Applied wind damage: {value:F1} to {((Object)wearNTear).name}");
			}
		}
	}
	[HarmonyPatch]
	internal class WeatherStatusEffects
	{
		private static float m_statusCheckTimer;

		private const float STATUS_CHECK_INTERVAL = 1f;

		[HarmonyPatch(typeof(Player), "Update")]
		[HarmonyPostfix]
		private static void CheckWeatherStatusEffects(Player __instance)
		{
			if (ElementalStormsPlugin.EnableMod == null || !ElementalStormsPlugin.EnableMod.Value || (Object)(object)__instance != (Object)(object)Player.m_localPlayer || ElementalStormsPlugin.IsInDungeonAltitude())
			{
				return;
			}
			m_statusCheckTimer += Time.deltaTime;
			if (m_statusCheckTimer < 1f)
			{
				return;
			}
			m_statusCheckTimer = 0f;
			if ((Object)(object)EnvMan.instance == (Object)null || EnvMan.instance.m_currentEnv == null)
			{
				return;
			}
			string name = EnvMan.instance.m_currentEnv.m_name;
			if (!string.IsNullOrEmpty(name))
			{
				switch (name)
				{
				case "ES_Eikthyr":
					HandleEikthyr(__instance);
					break;
				case "ES_Bonemass":
					break;
				case "ES_Moder":
					HandleModer(__instance);
					break;
				case "ES_Yagluth":
					HandleGoblinKing(__instance);
					break;
				case "ES_Queen":
					HandleQueen(__instance);
					break;
				case "ES_Fader":
					HandleFader(__instance);
					break;
				default:
					StatusEffectManager.RemoveAllCustomEffects((Character)(object)__instance);
					break;
				}
			}
		}

		private static void HandleEikthyr(Player player)
		{
		}

		private static void HandleBonemass(Player player)
		{
		}

		private static void HandleModer(Player player)
		{
			if (ElementalStormsPlugin.IsBossDefeated("defeated_moder") && !player.InShelter())
			{
				StatusEffectManager.ApplyGaleExposure((Character)(object)player);
			}
		}

		private static void HandleGoblinKing(Player player)
		{
		}

		private static void HandleQueen(Player player)
		{
		}

		private static void HandleFader(Player player)
		{
		}
	}
}