using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using UnityEngine;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyMetadata("PluginGUID", "com.luizbag.sailwind.boatstatushud")]
[assembly: AssemblyMetadata("PluginName", "BoatStatusHUD")]
[assembly: AssemblyCompany("BoatStatusHUD")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.8.0.0")]
[assembly: AssemblyInformationalVersion("1.8.0+66bc7d1a6a3c6df9f28430569bb9eb2d18877a6f")]
[assembly: AssemblyProduct("BoatStatusHUD")]
[assembly: AssemblyTitle("BoatStatusHUD")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.8.0.0")]
[module: UnverifiableCode]
namespace BoatStatusHUD;
[BepInPlugin("com.luizbag.sailwind.boatstatushud", "BoatStatusHUD", "0.0.0")]
public class BoatStatusHUDPlugin : BaseUnityPlugin
{
public static BoatDamage CurrentBoatDamage;
private ConfigEntry<bool> _hudVisible;
private ConfigEntry<KeyCode> _hudToggleKey;
private List<HUDPanel> _panels;
private void Awake()
{
//IL_0129: Unknown result type (might be due to invalid IL or missing references)
try
{
Utils.ParseProfilesString(((BaseUnityPlugin)this).Config.Bind<string>("ShipProfiles", "Profiles", "Kakam=400;Cog=700;Dhow=800;Junk=4000;Sanbuq=6000;Brig=10000;Jong=17000;Gallus=400;Caelanor=2000;Clipper=10000;Gloriana=12000;Chronian=17000;Leopard=20000;Shroud Small=600;Shroud Large=9000;BOAT CUTTER=250;DNG=150", "List of ship profiles and their max carrying capacities (Format: Key=Capacity;)").Value);
_panels = new List<HUDPanel>
{
new InstrumentsPanel(),
new CargoPanel(),
new SoundingPanel(),
new StatusPanel(),
new WeatherPanel()
};
((object)((BaseUnityPlugin)this).Info.Metadata).GetType().GetProperty("Version")?.SetValue(((BaseUnityPlugin)this).Info.Metadata, new Version(PluginInfo.Version));
_hudVisible = ((BaseUnityPlugin)this).Config.Bind<bool>("HUDSections", "HudVisible", true, "Master switch for the whole overlay.");
_hudToggleKey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("HUDSections", "HudToggleKey", (KeyCode)289, "The key that flips the HUD visibility at sea.");
foreach (HUDPanel panel in _panels)
{
panel.BindConfig(((BaseUnityPlugin)this).Config);
}
new Harmony(PluginInfo.GUID).PatchAll();
((BaseUnityPlugin)this).Logger.LogInfo((object)("[" + PluginInfo.Name + "] Telemetry system successfully initialized."));
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("[" + PluginInfo.Name + "] Critical failure hook mapping: " + ex.Message));
}
}
private void OnGUI()
{
//IL_003e: Unknown result type (might be due to invalid IL or missing references)
//IL_0043: Unknown result type (might be due to invalid IL or missing references)
//IL_005f: Unknown result type (might be due to invalid IL or missing references)
//IL_006e: Unknown result type (might be due to invalid IL or missing references)
//IL_0077: Unknown result type (might be due to invalid IL or missing references)
//IL_0081: Expected O, but got Unknown
//IL_0081: Unknown result type (might be due to invalid IL or missing references)
//IL_0088: Unknown result type (might be due to invalid IL or missing references)
//IL_0099: Unknown result type (might be due to invalid IL or missing references)
//IL_009e: Unknown result type (might be due to invalid IL or missing references)
//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
//IL_00b0: Unknown result type (might be due to invalid IL or missing references)
//IL_00b7: Unknown result type (might be due to invalid IL or missing references)
//IL_00bf: Expected O, but got Unknown
//IL_0111: Expected O, but got Unknown
if (!_hudVisible.Value || !GameState.playing || GameState.justStarted || (Object)(object)GameState.lastBoat == (Object)null)
{
return;
}
BoatDamage component = ((Component)GameState.lastBoat).GetComponent<BoatDamage>();
GUIStyle val = new GUIStyle(GUI.skin.box);
val.normal.background = Utils.MakeTexture(2, 2, new Color(0.29f, 0.35f, 0.41f, 0.25f));
val.padding = new RectOffset(10, 10, 10, 10);
val.stretchWidth = true;
val.stretchHeight = true;
GUIStyle defaultStyle = new GUIStyle(GUI.skin.label)
{
fontSize = HUDPanel.FontSize,
richText = true,
wordWrap = false,
clipping = (TextClipping)0
};
GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>());
GUILayout.Space(20f);
GUILayout.BeginVertical(Array.Empty<GUILayoutOption>());
GUILayout.Space(20f);
GUILayout.BeginVertical(val, (GUILayoutOption[])(object)new GUILayoutOption[3]
{
GUILayout.MinWidth(200f),
GUILayout.ExpandWidth(true),
GUILayout.ExpandHeight(true)
});
foreach (HUDPanel panel in _panels)
{
panel.DrawLines(defaultStyle, component);
}
GUILayout.EndVertical();
GUILayout.EndVertical();
GUILayout.FlexibleSpace();
GUILayout.EndHorizontal();
}
private void Update()
{
//IL_0015: Unknown result type (might be due to invalid IL or missing references)
if (!GameState.playing || GameState.justStarted)
{
return;
}
if (Input.GetKeyDown(_hudToggleKey.Value))
{
_hudVisible.Value = !_hudVisible.Value;
}
if (!_hudVisible.Value || !((Object)(object)GameState.lastBoat != (Object)null))
{
return;
}
BoatDamage component = ((Component)GameState.lastBoat).GetComponent<BoatDamage>();
foreach (HUDPanel panel in _panels)
{
panel.UpdateTelemetry(component);
}
}
}
public class CargoPanel : HUDPanel
{
private enum BurdenLevel
{
Light,
Normal,
Loaded,
Overloaded
}
private float _calculatedDeadweight;
private float _nextCheckTime;
private ConfigFile _configFile;
private string _lastCachedBoatName = "";
private ConfigEntry<float> _activeMaxCapacity;
private ConfigEntry<float> _activeMaxFreeboard;
private float _currentWaterLevel;
public override void BindConfig(ConfigFile config)
{
IsEnabled = config.Bind<bool>("HUDSections", "ShowCargo", true, "Master switch for the Cargo panel.");
_configFile = config;
}
public override void UpdateTelemetry(BoatDamage currentBoat)
{
if (!IsEnabled.Value || (Object)(object)currentBoat == (Object)null)
{
return;
}
_currentWaterLevel = currentBoat.waterLevel;
if (!(Time.time >= _nextCheckTime))
{
return;
}
_nextCheckTime = Time.time + 1f;
if (((Object)currentBoat).name != _lastCachedBoatName && _configFile != null)
{
_lastCachedBoatName = ((Object)currentBoat).name;
SetupActiveBoatConfig(((Object)currentBoat).name);
}
BoatMass component = ((Component)currentBoat).GetComponent<BoatMass>();
if (!((Object)(object)component != (Object)null))
{
return;
}
FieldInfo field = typeof(BoatMass).GetField("partsMass", BindingFlags.Instance | BindingFlags.NonPublic);
FieldInfo field2 = typeof(BoatMass).GetField("itemsOnBoat", BindingFlags.Instance | BindingFlags.NonPublic);
float num = 0f;
if (field != null)
{
num += (float)field.GetValue(component);
}
if (field2 != null && field2.GetValue(component) is List<ItemRigidbody> list)
{
foreach (ItemRigidbody item in list)
{
if ((Object)(object)item != (Object)null && (Object)(object)item.GetCurrentInventorySlot() == (Object)null)
{
num += item.GetBody().mass;
}
}
}
if ((Object)(object)GameState.lastBoat == (Object)(object)((Component)currentBoat).gameObject && (Object)(object)GameState.currentBoat != (Object)null && (Object)(object)GameState.currentBoat.parent == (Object)(object)((Component)currentBoat).transform)
{
num += 160f;
}
float num2 = currentBoat.waterLevel * currentBoat.waterUnitsCapacity;
num += num2;
_calculatedDeadweight = num;
}
private void SetupActiveBoatConfig(string boatName)
{
ShipProfile profile = Utils.GetProfile(boatName);
string text = "Cargo - " + ((profile != null) ? profile.DisplayName : boatName);
float num = profile?.MaxCapacity ?? 4000f;
float num2 = profile?.MaxFreeboard ?? 1.5f;
_activeMaxCapacity = _configFile.Bind<float>(text, "MaxCapacity", num, "Maximum safe carrying capacity in lbs.");
_activeMaxFreeboard = _configFile.Bind<float>(text, "MaxFreeboard", num2, "Target empty freeboard height in meters.");
}
public override void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat)
{
if (IsEnabled.Value && !((Object)(object)currentBoat == (Object)null) && _activeMaxCapacity != null)
{
BeginPanel();
DrawHUDLine($"<color={ColorLabel}>Deadweight:</color> {_calculatedDeadweight:F0}lbs", defaultStyle);
float value = _activeMaxFreeboard.Value;
float value2 = _activeMaxCapacity.Value;
float num = _calculatedDeadweight / value2 * (value * 0.5f);
float num2 = value - num - _currentWaterLevel * value;
if (num2 < 0f)
{
num2 = 0f;
}
string arg = ColorLabel;
if (num2 <= 0.3f || _currentWaterLevel > 0.7f)
{
arg = ColorDanger;
}
else if (num2 <= 0.6f || _currentWaterLevel > 0.3f)
{
arg = "#bd7f2e";
}
DrawHUDLine($"<color={arg}>Freeboard:</color> {num2:F1}m", defaultStyle);
float num3 = _calculatedDeadweight / value2;
string text;
string text2;
if (num3 > 1f || _currentWaterLevel >= 0.9f)
{
text = BurdenLevel.Overloaded.ToString();
text2 = ColorDanger;
}
else if (num3 > 0.75f || _currentWaterLevel > 0.4f)
{
text = BurdenLevel.Loaded.ToString();
text2 = "#bd7f2e";
}
else if (num3 > 0.25f)
{
text = BurdenLevel.Normal.ToString();
text2 = "#ffffff";
}
else
{
text = BurdenLevel.Light.ToString();
text2 = ColorMuted;
}
DrawHUDLine("<color=" + ColorLabel + ">Burden:</color> <color=" + text2 + ">" + text + "</color>", defaultStyle);
EndPanel();
}
}
}
public abstract class HUDPanel
{
protected ConfigEntry<bool> IsEnabled;
protected readonly Color BackgroundColor = new Color(0.047f, 0.035f, 0.02f, 0.3f);
protected readonly string ColorLabel = "#F5EEDCE0";
protected readonly string ColorMuted = "#A19B8EE0";
protected readonly string ColorDanger = "#ff3333";
public static Font Font { get; private set; }
public static int FontSize { get; set; } = 14;
protected HUDPanel()
{
//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)
Font = GetGameFont();
}
protected void BeginPanel()
{
//IL_000a: Unknown result type (might be due to invalid IL or missing references)
//IL_000f: Unknown result type (might be due to invalid IL or missing references)
//IL_0018: 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_002c: Unknown result type (might be due to invalid IL or missing references)
//IL_0036: Expected O, but got Unknown
//IL_0036: Unknown result type (might be due to invalid IL or missing references)
//IL_003f: Unknown result type (might be due to invalid IL or missing references)
//IL_0049: Expected O, but got Unknown
//IL_0049: 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_0081: Expected O, but got Unknown
GUIStyle val = new GUIStyle(GUI.skin.box);
val.normal.background = Utils.MakeTexture(2, 2, BackgroundColor);
val.margin = new RectOffset(0, 0, 0, 8);
val.padding = new RectOffset(12, 12, 12, 12);
val.stretchWidth = true;
val.stretchHeight = true;
GUILayout.BeginVertical(val, (GUILayoutOption[])(object)new GUILayoutOption[3]
{
GUILayout.MinWidth(200f),
GUILayout.ExpandWidth(true),
GUILayout.ExpandHeight(true)
});
}
protected void EndPanel()
{
GUILayout.EndVertical();
}
private Font GetGameFont()
{
Font result = null;
Object[] array = Resources.FindObjectsOfTypeAll(typeof(Font));
foreach (Object obj in array)
{
Font val = (Font)(object)((obj is Font) ? obj : null);
if (!((Object)(object)val == (Object)null))
{
string text = ((Object)val).name ?? "";
if (text.IndexOf("Arial", StringComparison.OrdinalIgnoreCase) < 0 && text.Length > 0)
{
result = val;
break;
}
}
}
return result;
}
public abstract void BindConfig(ConfigFile config);
public abstract void UpdateTelemetry(BoatDamage currentBoat);
public abstract void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat);
protected void DrawHUDLine(string text, GUIStyle style)
{
if (style != null)
{
style.fontSize = FontSize;
style.font = Font;
style.richText = true;
}
GUILayout.Label(text, style, Array.Empty<GUILayoutOption>());
}
}
public class InstrumentsPanel : HUDPanel
{
private ConfigEntry<bool> _requireChipLog;
private ConfigEntry<bool> _requireCompass;
private bool _hasChipLog;
private bool _hasCompass;
private float _nextCheckTime;
public override void BindConfig(ConfigFile config)
{
IsEnabled = config.Bind<bool>("HUDSections", "ShowInstruments", true, "Master switch for the Instruments panel.");
_requireChipLog = config.Bind<bool>("EquipmentRequirements", "RequireChipLogForSpeed", true, "Speed appears only with a chip log aboard.");
_requireCompass = config.Bind<bool>("EquipmentRequirements", "RequireCompassForHeading", true, "Heading appears only with a compass aboard.");
}
public override void UpdateTelemetry(BoatDamage currentBoat)
{
if (!IsEnabled.Value || (Object)(object)currentBoat == (Object)null || !(Time.time >= _nextCheckTime))
{
return;
}
_nextCheckTime = Time.time + 1f;
_hasChipLog = !_requireChipLog.Value;
_hasCompass = !_requireCompass.Value;
Transform[] componentsInChildren = ((Component)currentBoat).GetComponentsInChildren<Transform>(true);
CheckTransforms(componentsInChildren);
if ((_requireCompass.Value && !_hasCompass) || (_requireChipLog.Value && !_hasChipLog))
{
GameObject val = GameObject.FindGameObjectWithTag("Player");
if ((Object)(object)val != (Object)null)
{
Transform[] componentsInChildren2 = val.GetComponentsInChildren<Transform>(true);
CheckTransforms(componentsInChildren2);
}
}
}
private void CheckTransforms(Transform[] transforms)
{
foreach (Transform val in transforms)
{
if (!((Object)(object)val == (Object)null))
{
string text = ((Object)val).name.ToLower();
if (_requireCompass.Value && (text.Contains("compass") || text.Contains("bussola")))
{
_hasCompass = true;
}
if (_requireChipLog.Value && (text.Contains("chip log") || text.Contains("chiplog")))
{
_hasChipLog = true;
}
}
}
}
public override void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat)
{
//IL_0037: Unknown result type (might be due to invalid IL or missing references)
//IL_0042: Unknown result type (might be due to invalid IL or missing references)
//IL_00b3: Unknown result type (might be due to invalid IL or missing references)
//IL_011f: Unknown result type (might be due to invalid IL or missing references)
//IL_0124: Unknown result type (might be due to invalid IL or missing references)
//IL_0135: Unknown result type (might be due to invalid IL or missing references)
if (!IsEnabled.Value || (Object)(object)currentBoat == (Object)null)
{
return;
}
Rigidbody component = ((Component)currentBoat).GetComponent<Rigidbody>();
if ((Object)(object)component == (Object)null)
{
return;
}
BeginPanel();
if (_hasChipLog)
{
float num = Vector3.Dot(component.velocity, ((Component)currentBoat).transform.forward) * 1.94384f;
if (Mathf.Abs(num) < 0.1f)
{
num = 0f;
}
DrawHUDLine($"<color={ColorLabel}>Speed: </color>{num:F1}kts", defaultStyle);
}
else
{
DrawHUDLine("<color=" + ColorMuted + ">Speed: </color>[Requires Chip Log]", defaultStyle);
}
if (_hasCompass)
{
float num2 = ((Component)currentBoat).transform.eulerAngles.y;
if (num2 < 0f)
{
num2 += 360f;
}
string compassDirection = Utils.GetCompassDirection(num2);
DrawHUDLine($"<color={ColorLabel}>Heading: </color>{num2:F0}° {compassDirection}", defaultStyle);
}
else
{
DrawHUDLine("<color=" + ColorMuted + ">Heading: </color>[Requires Compass]", defaultStyle);
}
float num3 = Vector3.Angle(((Component)currentBoat).transform.up, Vector3.up);
float num4 = ((Component)currentBoat).transform.localEulerAngles.z;
if (num4 > 180f)
{
num4 -= 360f;
}
string text = "";
if (num3 > 0.5f)
{
text = ((num4 > 0f) ? "P" : "S");
}
string text2 = ((num3 > currentBoat.safeAngleLimit) ? ColorDanger : ColorLabel);
DrawHUDLine($"<color={text2}>Heel Angle: </color>{num3:F1}° {text}/{currentBoat.safeAngleLimit:F0}°", defaultStyle);
EndPanel();
}
}
public static class PluginInfo
{
public static readonly string GUID = ((AssemblyMetadataAttribute)Attribute.GetCustomAttributes(typeof(BoatStatusHUDPlugin).Assembly, typeof(AssemblyMetadataAttribute)).FirstOrDefault((Attribute x) => ((AssemblyMetadataAttribute)x).Key == "PluginGUID"))?.Value ?? "com.luizbag.sailwind.boatstatushud";
public static readonly string Name = ((AssemblyMetadataAttribute)Attribute.GetCustomAttributes(typeof(BoatStatusHUDPlugin).Assembly, typeof(AssemblyMetadataAttribute)).FirstOrDefault((Attribute x) => ((AssemblyMetadataAttribute)x).Key == "PluginName"))?.Value ?? "BoatStatusHUD";
public static readonly string Version = typeof(BoatStatusHUDPlugin).Assembly.GetName().Version.ToString(3);
}
public class ShipProfile
{
public string Key;
public string DisplayName;
public float MaxCapacity;
public float MaxFreeboard;
}
public class ShipProfileList
{
public ShipProfile[] Profiles;
}
public class SoundingPanel : HUDPanel
{
private float _seaDepth = 300f;
private float _keelClearance = 300f;
private float _nextCheckTime;
public override void BindConfig(ConfigFile config)
{
IsEnabled = config.Bind<bool>("HUDSections", "ShowSounding", true, "Master switch for the Sounding panel.");
}
public override void UpdateTelemetry(BoatDamage currentBoat)
{
//IL_003d: Unknown result type (might be due to invalid IL or missing references)
//IL_0042: Unknown result type (might be due to invalid IL or missing references)
//IL_0047: 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)
if (!IsEnabled.Value || (Object)(object)currentBoat == (Object)null || !(Time.time >= _nextCheckTime))
{
return;
}
_nextCheckTime = Time.time + 0.5f;
Vector3 position = GameState.lastBoat.position;
Vector3 down = Vector3.down;
float num = 300f;
RaycastHit val = default(RaycastHit);
if (Physics.Raycast(position, down, ref val, num))
{
_seaDepth = ((RaycastHit)(ref val)).distance;
_keelClearance = _seaDepth - 1.5f;
if (_seaDepth < 0f)
{
_seaDepth = 0f;
}
if (_keelClearance < 0f)
{
_keelClearance = 0f;
}
}
else
{
_seaDepth = 300f;
_keelClearance = 300f;
}
}
public override void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat)
{
if (IsEnabled.Value && !((Object)(object)currentBoat == (Object)null))
{
BeginPanel();
DrawHUDLine($"<color={ColorLabel}>Sea Depth: </color>{_seaDepth:F1}m", defaultStyle);
if (_keelClearance <= 0.1f)
{
DrawHUDLine($"<color={ColorDanger}>Keel Clearance: </color>{_keelClearance:F1}m", defaultStyle);
}
else if (_keelClearance <= 2f)
{
DrawHUDLine($"<color=#bd7f2e>Keel Clearance: </color>{_keelClearance:F1}m", defaultStyle);
}
else
{
DrawHUDLine($"<color={ColorLabel}>Keel Clearance: </color>{_keelClearance:F1}m", defaultStyle);
}
EndPanel();
}
}
}
public class StatusPanel : HUDPanel
{
private float _hullIntegrityPercent = 100f;
private float _bilgeWaterPercent;
private float _nextCheckTime;
public override void BindConfig(ConfigFile config)
{
IsEnabled = config.Bind<bool>("HUDSections", "ShowStatus", true, "Master switch for the Status panel.");
}
public override void UpdateTelemetry(BoatDamage currentBoat)
{
if (IsEnabled.Value && !((Object)(object)currentBoat == (Object)null) && Time.time >= _nextCheckTime)
{
_nextCheckTime = Time.time + 0.5f;
_hullIntegrityPercent = (1f - currentBoat.hullDamage) * 100f;
if (_hullIntegrityPercent < 0f)
{
_hullIntegrityPercent = 0f;
}
_bilgeWaterPercent = currentBoat.waterLevel * 100f;
}
}
public override void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat)
{
if (IsEnabled.Value && !((Object)(object)currentBoat == (Object)null))
{
BeginPanel();
string arg = ColorLabel;
if (_hullIntegrityPercent <= 30f)
{
arg = ColorDanger;
}
else if (_hullIntegrityPercent <= 75f)
{
arg = "#bd7f2e";
}
DrawHUDLine($"<color={arg}>Hull Integrity: </color>{_hullIntegrityPercent:F1}%", defaultStyle);
string arg2 = ColorLabel;
if (_bilgeWaterPercent >= 50f)
{
arg2 = ColorDanger;
}
else if (_bilgeWaterPercent > 15f)
{
arg2 = "#bd7f2e";
}
DrawHUDLine($"<color={arg2}>Bilge Water: </color>{_bilgeWaterPercent:F1}%", defaultStyle);
EndPanel();
}
}
}
public static class Utils
{
private static Dictionary<string, ShipProfile> _profileCache = new Dictionary<string, ShipProfile>();
public static Texture2D MakeTexture(int width, int height, Color col)
{
//IL_000f: Unknown result type (might be due to invalid IL or missing references)
//IL_0010: Unknown result type (might be due to invalid IL or missing references)
//IL_0021: 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_002d: Unknown result type (might be due to invalid IL or missing references)
//IL_0034: Expected O, but got Unknown
Color[] array = (Color[])(object)new Color[width * height];
for (int i = 0; i < array.Length; i++)
{
array[i] = col;
}
Texture2D val = new Texture2D(width, height);
val.SetPixels(array);
val.Apply();
return val;
}
public static void ParseProfilesString(string profilesRawData)
{
_profileCache.Clear();
if (string.IsNullOrEmpty(profilesRawData))
{
return;
}
string[] array = profilesRawData.Split(new char[1] { ';' }, StringSplitOptions.RemoveEmptyEntries);
for (int i = 0; i < array.Length; i++)
{
string[] array2 = array[i].Split(new char[1] { '=' });
if (array2.Length != 2)
{
continue;
}
string text = array2[0].Trim();
if (float.TryParse(array2[1].Trim(), out var result))
{
float num = 1f + result / 10000f;
if (num > 2.8f)
{
num = 2.8f;
}
_profileCache[text.ToLower()] = new ShipProfile
{
Key = text,
DisplayName = text,
MaxCapacity = result,
MaxFreeboard = num
};
}
}
}
public static ShipProfile GetProfile(string gameObjectName)
{
if (string.IsNullOrEmpty(gameObjectName))
{
return null;
}
string text = gameObjectName.ToLower();
foreach (KeyValuePair<string, ShipProfile> item in _profileCache)
{
if (text.Contains(item.Key))
{
return item.Value;
}
}
return null;
}
public static string GetCompassDirection(float degrees)
{
string[] obj = new string[16]
{
"N", "NNE", "NE", "ENE", "E", "ESE", "SE", "SSE", "S", "SSW",
"SW", "WSW", "W", "WNW", "NW", "NNW"
};
int num = Mathf.RoundToInt(degrees / 22.5f) % 16;
return obj[num];
}
}
public class WeatherPanel : HUDPanel
{
private bool _hasWindIndicator;
private ConfigEntry<bool> _requireWindicator;
private string _windString = "Calm";
private string _conditionsString = "Fair";
private string _conditionsColor = "#ffffff";
private float _nextCheckTime;
public override void BindConfig(ConfigFile config)
{
IsEnabled = config.Bind<bool>("HUDSections", "ShowWeather", true, "Master switch for the Weather panel.");
_requireWindicator = config.Bind<bool>("EquipmentRequirements", "RequireWindicatorForWind", true, "Wind speed and direction appear only with a windicator aboard.");
}
public override void UpdateTelemetry(BoatDamage currentBoat)
{
//IL_0050: Unknown result type (might be due to invalid IL or missing references)
//IL_0055: Unknown result type (might be due to invalid IL or missing references)
//IL_00e2: 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_00c6: Unknown result type (might be due to invalid IL or missing references)
//IL_00cb: Unknown result type (might be due to invalid IL or missing references)
//IL_00d0: 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)
//IL_00df: Unknown result type (might be due to invalid IL or missing references)
if (!IsEnabled.Value || (Object)(object)currentBoat == (Object)null || !(Time.time >= _nextCheckTime))
{
return;
}
_nextCheckTime = Time.time + 1f;
_hasWindIndicator = CheckForWindIndicators(currentBoat);
if (_hasWindIndicator)
{
Vector3 wind = Vector3.zero;
if ((Object)(object)Weather.instance != (Object)null)
{
FieldInfo field = typeof(Weather).GetField("wind", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
if (field != null)
{
wind = (Vector3)field.GetValue(Weather.instance);
}
else
{
float num = (((Object)(object)Sun.sun != (Object)null) ? Sun.sun.localTime : 12f) * 15f;
wind = Quaternion.Euler(0f, num, 0f) * Vector3.forward * 6f;
}
}
_windString = ConvertWindToSailorTerms(wind);
}
UpdateWeatherConditions();
}
private bool CheckForWindIndicators(BoatDamage boat)
{
if (!_requireWindicator.Value)
{
return true;
}
BoatCustomParts component = ((Component)boat).GetComponent<BoatCustomParts>();
if ((Object)(object)component != (Object)null && component.availableParts != null)
{
foreach (BoatPart availablePart in component.availableParts)
{
if (availablePart == null)
{
continue;
}
BoatPartOption activeOption = availablePart.GetActiveOption();
if (!((Object)(object)activeOption == (Object)null))
{
string text = ((Object)((Component)activeOption).gameObject).name.ToLower();
if (text.Contains("windicator") || text.Contains("tell tale") || text.Contains("wind compass"))
{
return true;
}
}
}
}
return false;
}
private string ConvertWindToSailorTerms(Vector3 wind)
{
//IL_0016: 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)
float magnitude = ((Vector3)(ref wind)).magnitude;
if (magnitude < 0.1f)
{
return "Calm";
}
float num = Mathf.Atan2(wind.x, wind.z) * 57.29578f;
if (num < 0f)
{
num += 360f;
}
string compassDirection = Utils.GetCompassDirection(num);
string text = ((magnitude < 2f) ? "Light Air" : ((magnitude < 5f) ? "Breeze" : ((magnitude < 10f) ? "Fresh Breeze" : ((!(magnitude < 18f)) ? "Gale" : "Strong Wind"))));
return compassDirection + " " + text;
}
private void UpdateWeatherConditions()
{
float rainIntensity = GameState.rainIntensity;
if (rainIntensity > 0.6f)
{
_conditionsString = "Tempest";
_conditionsColor = ColorDanger;
}
else if (rainIntensity > 0.1f)
{
_conditionsString = "Squally";
_conditionsColor = "#bd7f2e";
}
else if (rainIntensity > 0f)
{
_conditionsString = "Moderate";
_conditionsColor = "#ffffff";
}
else
{
_conditionsString = "Fair";
_conditionsColor = "#44cc44";
}
}
public override void DrawLines(GUIStyle defaultStyle, BoatDamage currentBoat)
{
if (IsEnabled.Value && !((Object)(object)currentBoat == (Object)null))
{
BeginPanel();
if (_hasWindIndicator)
{
DrawHUDLine("<color=" + ColorLabel + ">Wind: </color>" + _windString, defaultStyle);
}
else
{
DrawHUDLine("<color=" + ColorMuted + ">Wind: </color>No Indicator Aboard", defaultStyle);
}
DrawHUDLine("<color=" + ColorLabel + ">Conditions: </color><color=" + _conditionsColor + ">" + _conditionsString + "</color>", defaultStyle);
EndPanel();
}
}
}