using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
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 HarmonyLib;
using IBelieveICanFly.Patches;
using IBelieveICanFly.Registration;
using UnityEngine;
using UnityEngine.UI;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("0.0.0.0")]
[module: UnverifiableCode]
namespace Pix.BalancedGliders;
internal static class StableHashExtensions
{
public static int GetStableHashCode(this string str)
{
if (str == null)
{
return 0;
}
int num = 5381;
int num2 = num;
for (int i = 0; i < str.Length && str[i] != 0; i += 2)
{
num = ((num << 5) + num) ^ str[i];
if (i == str.Length - 1 || str[i + 1] == '\0')
{
break;
}
num2 = ((num2 << 5) + num2) ^ str[i + 1];
}
return num + num2 * 1566083941;
}
}
[BepInPlugin("Pix.BalancedGliders", "Balanced Gliders", "0.8.1")]
public class Plugin : BaseUnityPlugin
{
private static class Runtime
{
public static bool HasServerConfig;
public static bool Enabled = true;
public static float CooldownSeconds = 150f;
public static bool DynamicEnabled = true;
public static float DynamicBaseSeconds = 10f;
public static float DynamicPower = 1.2f;
public static float DynamicMultiplier = 2f;
public static float DynamicMinSeconds = 10f;
public static float DynamicMaxSeconds = 150f;
public static float DynamicShortHopThresholdSeconds = 1f;
public static bool ShowStatusEffect = true;
public static bool DebugLogs;
public static bool LeaderboardEnabled = true;
public static KeyCode LeaderboardHotkey = (KeyCode)288;
public static int LeaderboardMaxRows = 20;
public static void LoadFromConfig()
{
//IL_015c: Unknown result type (might be due to invalid IL or missing references)
//IL_0161: Unknown result type (might be due to invalid IL or missing references)
Enabled = _enabled != null && _enabled.Value;
CooldownSeconds = ((_cooldownSeconds != null) ? _cooldownSeconds.Value : 150f);
DynamicEnabled = _dynamicEnabled != null && _dynamicEnabled.Value;
DynamicBaseSeconds = ((_dynamicBaseSeconds != null) ? _dynamicBaseSeconds.Value : 10f);
DynamicPower = ((_dynamicPower != null) ? _dynamicPower.Value : 1.2f);
DynamicMultiplier = ((_dynamicMultiplier != null) ? _dynamicMultiplier.Value : 2f);
DynamicMinSeconds = ((_dynamicMinSeconds != null) ? _dynamicMinSeconds.Value : 10f);
DynamicMaxSeconds = ((_dynamicMaxSeconds != null) ? _dynamicMaxSeconds.Value : 150f);
DynamicShortHopThresholdSeconds = ((_dynamicShortHopThresholdSeconds != null) ? _dynamicShortHopThresholdSeconds.Value : 1f);
ShowStatusEffect = _showStatusEffect != null && _showStatusEffect.Value;
DebugLogs = _debugLogs != null && _debugLogs.Value;
LeaderboardEnabled = _leaderboardEnabled != null && _leaderboardEnabled.Value;
LeaderboardHotkey = (KeyCode)((_leaderboardHotkey == null) ? 288 : ((int)_leaderboardHotkey.Value));
LeaderboardMaxRows = ((_leaderboardMaxRows != null) ? Mathf.Clamp(_leaderboardMaxRows.Value, 5, 100) : 20);
}
}
private struct GlideTrack
{
public Vector3 StartPos;
public long StartMs;
}
private sealed class RecordEntry
{
public long Id;
public string Name;
public float BestDistance;
public float BestAirtime;
public float BestDrop;
public float LatestDistance;
public float LatestAirtime;
public float LatestDrop;
public long UpdatedAtMs;
}
[HarmonyPatch(typeof(ZRoutedRpc))]
private static class ZRoutedRpc_Ctor_Register_Patch
{
[HarmonyPatch(/*Could not decode attribute arguments.*/)]
[HarmonyPostfix]
private static void Postfix(bool server)
{
DetectRoutedRpcInstanceChange();
TryRegisterRpcs();
}
}
public class SE_GliderCooldown : SE_Stats
{
public override string GetIconText()
{
try
{
Character character = ((StatusEffect)this).m_character;
Player val = (Player)(object)((character is Player) ? character : null);
if ((Object)(object)val == (Object)null)
{
return "";
}
if (!IsOnCooldown(val, out var remainingSeconds))
{
return "";
}
return FormatSeconds(remainingSeconds);
}
catch
{
return "";
}
}
}
[HarmonyPatch(typeof(ObjectDB), "Awake")]
private static class ObjectDB_RegisterStatusEffect_Patch
{
private static void Postfix(ObjectDB __instance)
{
EnsureSEInObjectDB(__instance);
}
}
[HarmonyPatch(typeof(ObjectDB), "CopyOtherDB")]
private static class ObjectDB_CopyOtherDB_RegisterStatusEffect_Patch
{
private static void Postfix(ObjectDB __instance)
{
EnsureSEInObjectDB(__instance);
}
}
[HarmonyPatch]
private static class GliderSystemPatches
{
[HarmonyPatch(typeof(GliderSystem), "CanGlide")]
[HarmonyPostfix]
private static void CanGlide_Postfix(Player player, ref bool __result)
{
//IL_00b3: Unknown result type (might be due to invalid IL or missing references)
//IL_00be: Expected O, but got Unknown
//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
try
{
if (!EffectiveEnabled || (Object)(object)player == (Object)null)
{
return;
}
bool flag = __result;
bool flag2 = WasGliding(player);
if (flag2)
{
return;
}
float remainingSeconds = 0f;
bool flag3 = IsOnCooldown(player, out remainingSeconds);
bool flag4 = false;
bool flag5 = false;
int num = -1;
float num2 = 0f;
bool flag6 = false;
bool flag7 = false;
bool flag8 = false;
bool flag9 = false;
bool flag10 = false;
float num3 = 0f;
try
{
flag8 = ((Character)player).IsOnGround();
}
catch
{
}
try
{
flag9 = ((Character)player).InWater();
}
catch
{
}
try
{
flag10 = ((Character)player).IsAttached();
}
catch
{
}
try
{
Rigidbody component = ((Component)player).GetComponent<Rigidbody>();
if ((Object)component != (Object)null)
{
num3 = component.linearVelocity.y;
}
}
catch
{
}
try
{
flag6 = Input.GetKey((KeyCode)32);
flag7 = Input.GetKeyDown((KeyCode)32);
}
catch
{
}
try
{
if (Config.ToggleMode != null)
{
flag4 = Config.ToggleMode.Value;
}
}
catch
{
}
try
{
flag5 = _frToggleModeActive.Invoke((object)null);
}
catch
{
}
try
{
num = _frCurrentWingsIndex.Invoke((object)null);
}
catch
{
}
try
{
int num4 = num;
if (num4 <= 0)
{
num4 = GliderSystem.GetCurrentWingsIndex();
}
if (num4 > 0)
{
num2 = Config.GetWingsMinActivationFallSpeed(num4);
}
}
catch
{
}
if (EffectiveDebug && (flag6 || flag7) && Time.unscaledTime >= _dbgNextCanGlideAt)
{
_dbgNextCanGlideAt = Time.unscaledTime + 0.5f;
bool flag11 = (Object)(object)Player.m_localPlayer != (Object)null && (Object)(object)player == (Object)(object)Player.m_localPlayer;
Dbg("CanGlide hb: " + $"upstream={flag} " + string.Format("cd={0} rem={1:0.00}s veto={2} ", flag3 ? "YES" : "NO", remainingSeconds, flag && flag3) + $"wasGliding={flag2} local={flag11} " + $"grounded={flag8} water={flag9} attached={flag10} " + $"vy={num3:0.00} minFall={num2:0.00} " + $"spaceHeld={flag6} spaceDown={flag7} " + $"toggleCfg={flag4} toggleActive={flag5} wingsIdx={num}");
}
if (flag && flag3)
{
__result = false;
}
}
catch
{
}
}
[HarmonyPatch(typeof(GliderSystem), "StartGliding")]
[HarmonyPostfix]
private static void StartGliding_Postfix(Player player)
{
//IL_0050: Unknown result type (might be due to invalid IL or missing references)
//IL_0056: Expected O, but got Unknown
try
{
if (EffectiveEnabled && !((Object)(object)player == (Object)null))
{
MarkGliding(player, gliding: true);
if (!IsServer() && (Object)(object)player == (Object)(object)Player.m_localPlayer && IsNetConnected() && ZRoutedRpc.instance != null)
{
ZPackage val = new ZPackage();
val.Write(GetNetworkTimeMs());
ZRoutedRpc.instance.InvokeRoutedRPC("BG_GlideStart", new object[1] { val });
}
}
}
catch
{
}
}
[HarmonyPatch(typeof(GliderSystem), "StopGliding")]
[HarmonyPostfix]
private static void StopGliding_Postfix(Player player)
{
//IL_0050: Unknown result type (might be due to invalid IL or missing references)
//IL_0056: Expected O, but got Unknown
try
{
if (EffectiveEnabled && !((Object)(object)player == (Object)null))
{
MarkGliding(player, gliding: false);
if (!IsServer() && (Object)(object)player == (Object)(object)Player.m_localPlayer && IsNetConnected() && ZRoutedRpc.instance != null)
{
ZPackage val = new ZPackage();
val.Write(GetNetworkTimeMs());
ZRoutedRpc.instance.InvokeRoutedRPC("BG_GlideEnd", new object[1] { val });
}
}
}
catch
{
}
}
[HarmonyPatch(typeof(GliderSystem), "IsPlayerGliding")]
[HarmonyPostfix]
private static void IsPlayerGliding_Postfix(Player player, ref bool __result)
{
try
{
if (!((Object)(object)player == (Object)null))
{
MarkGliding(player, __result);
}
}
catch
{
}
}
}
[Serializable]
[CompilerGenerated]
private sealed class <>c
{
public static readonly <>c <>9 = new <>c();
public static Action <>9__95_0;
public static ConsoleEvent <>9__115_0;
public static ConsoleEvent <>9__115_1;
public static Comparison<RecordEntry> <>9__127_0;
internal void <HookServerConfigEvents>b__95_0()
{
Runtime.LoadFromConfig();
BroadcastServerConfig();
}
internal void <TryRegisterCommands>b__115_0(ConsoleEventArgs args)
{
OutputClient(BuildStatusText(), hud: false);
}
internal void <TryRegisterCommands>b__115_1(ConsoleEventArgs args)
{
if (!EffectiveLeaderboard)
{
OutputClient("Balanced Gliders: leaderboard is disabled.", hud: true);
return;
}
_lbVisible = !_lbVisible;
if (_lbVisible)
{
if (string.IsNullOrEmpty(_lbText))
{
_lbText = "Loading leaderboard...";
}
RequestLeaderboardIfClient();
}
}
internal int <BuildLeaderboardText_Server>b__127_0(RecordEntry a, RecordEntry b)
{
return b.BestDistance.CompareTo(a.BestDistance);
}
}
public const string PluginGuid = "Pix.BalancedGliders";
public const string PluginName = "Balanced Gliders";
public const string PluginVersion = "0.8.1";
private Harmony _harmony;
private static ConfigEntry<bool> _enabled;
private static ConfigEntry<float> _cooldownSeconds;
private static ConfigEntry<bool> _dynamicEnabled;
private static ConfigEntry<float> _dynamicBaseSeconds;
private static ConfigEntry<float> _dynamicPower;
private static ConfigEntry<float> _dynamicMultiplier;
private static ConfigEntry<float> _dynamicMinSeconds;
private static ConfigEntry<float> _dynamicMaxSeconds;
private static ConfigEntry<float> _dynamicShortHopThresholdSeconds;
private static ConfigEntry<bool> _showStatusEffect;
private static ConfigEntry<bool> _debugLogs;
private static ConfigEntry<bool> _serverAuthoritativeConfig;
private static ConfigEntry<bool> _lockClientConfig;
private static ConfigEntry<bool> _leaderboardEnabled;
private static ConfigEntry<KeyCode> _leaderboardHotkey;
private static ConfigEntry<int> _leaderboardMaxRows;
private static ConfigEntry<string> _toastVariantsAllTimePB;
private static ConfigEntry<string> _toastVariantsDailyPB;
private static ConfigEntry<string> _toastVariantsNormal;
private static readonly int ZdoKey_CooldownEndMs = "BG_CooldownEndMs".GetStableHashCode();
private static readonly int ZdoKey_GlideStartMs = "BG_GlideStartMs".GetStableHashCode();
private const string Rpc_RequestConfig = "BG_RequestConfig";
private const string Rpc_ReceiveConfig = "BG_Config";
private const string Rpc_GlideStart = "BG_GlideStart";
private const string Rpc_GlideEnd = "BG_GlideEnd";
private const string Rpc_SetCooldown = "BG_SetCooldown";
private const string Rpc_RequestLeaderboard = "BG_LB_Req";
private const string Rpc_ReceiveLeaderboard = "BG_LB_Recv";
private const string Rpc_GlideResult = "BG_GlideResult";
private const string CooldownSEName = "SE_BalancedGliders_Cooldown";
private static readonly int CooldownSEHash = "SE_BalancedGliders_Cooldown".GetStableHashCode();
private static StatusEffect _cooldownSEPrefab;
private static readonly FieldRef<Character, ZNetView> _frNView = AccessTools.FieldRefAccess<Character, ZNetView>("m_nview");
private static readonly FieldRef<object, bool> _frToggleModeActive = AccessTools.FieldRefAccess<bool>(typeof(GliderSystem), "toggleModeActive");
private static readonly FieldRef<object, int> _frCurrentWingsIndex = AccessTools.FieldRefAccess<int>(typeof(GliderSystem), "currentWingsIndex");
private static readonly Dictionary<ZDOID, bool> _wasGlidingByZdo = new Dictionary<ZDOID, bool>();
private static readonly Dictionary<long, bool> _wasGlidingByPlayerId = new Dictionary<long, bool>();
private static readonly Dictionary<ZDOID, GlideTrack> _glideTrackByZdo = new Dictionary<ZDOID, GlideTrack>();
private static readonly Dictionary<long, RecordEntry> _recordsById = new Dictionary<long, RecordEntry>();
private static readonly Dictionary<long, float> _dailyBestById = new Dictionary<long, float>();
private static bool _recordsDirty;
private static float _nextRecordsSaveAt;
private static string _recordsPath;
private float _localCleanupTimer;
private float _patchCheckTimer;
private static bool _rpcsRegistered;
private static bool _serverConfigHooksInstalled;
private static bool _serverBroadcastedInitialConfig;
private static bool _requestedServerConfig;
private static float _requestTimer;
private static bool _wasConnectedLastTick;
private static ZRoutedRpc _lastRoutedRpcInstance;
private static bool _commandsRegistered;
private static bool _lbVisible;
private static float _lbLastRequestAt;
private static string _lbText = "";
private static string _toastText;
private static float _toastUntil;
private static bool _guiInit;
private static GUIStyle _lbTitleStyle;
private static GUIStyle _lbBodyStyle;
private static GUIStyle _lbFooterStyle;
private static GUIStyle _lbPanelStyle;
private static bool _trophyIconTried;
private static Sprite _trophyIconSprite;
private static bool _panelBackingTried;
private static bool _panelBackingHas;
private static Texture2D _panelBackingTex;
private static Rect _panelBackingUv;
private static float _dbgNextCanGlideAt;
private static bool EffectiveEnabled => ShouldUseServerRuntime() ? Runtime.Enabled : (_enabled != null && _enabled.Value);
private static bool EffectiveShowSE => ShouldUseServerRuntime() ? Runtime.ShowStatusEffect : (_showStatusEffect != null && _showStatusEffect.Value);
private static bool EffectiveDebug => ShouldUseServerRuntime() ? Runtime.DebugLogs : (_debugLogs != null && _debugLogs.Value);
private static bool EffectiveLeaderboard => ShouldUseServerRuntime() ? Runtime.LeaderboardEnabled : (_leaderboardEnabled != null && _leaderboardEnabled.Value);
private static KeyCode EffectiveLeaderboardHotkey => (KeyCode)((!ShouldUseServerRuntime()) ? ((_leaderboardHotkey == null) ? 288 : ((int)_leaderboardHotkey.Value)) : ((int)Runtime.LeaderboardHotkey));
private static int EffectiveLeaderboardMaxRows => ShouldUseServerRuntime() ? Runtime.LeaderboardMaxRows : ((_leaderboardMaxRows != null) ? Mathf.Clamp(_leaderboardMaxRows.Value, 5, 100) : 20);
private void Awake()
{
//IL_02b4: Unknown result type (might be due to invalid IL or missing references)
//IL_02be: Expected O, but got Unknown
_serverAuthoritativeConfig = ((BaseUnityPlugin)this).Config.Bind<bool>("Server", "ServerAuthoritativeConfig", true, "If true, the server's config values override clients (no ServerSync dependency).");
_lockClientConfig = ((BaseUnityPlugin)this).Config.Bind<bool>("Server", "LockClientConfig", true, "If true and ServerAuthoritativeConfig is enabled, clients always obey server values when connected.");
_enabled = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "Enabled", true, "Enable cooldown enforcement.");
_cooldownSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("Cooldown", "CooldownSeconds", 150f, "Fixed cooldown seconds after gliding (used when DynamicCooldown is disabled).");
_dynamicEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("DynamicCooldown", "Enabled", true, "Enable dynamic cooldown based on seconds spent gliding (server-enforced).");
_dynamicBaseSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "BaseSeconds", 10f, "Base cooldown seconds added for a glide longer than the short-hop threshold.");
_dynamicPower = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "Power", 1.2f, "Exponent applied to glide duration. Higher = ramps faster for long glides.");
_dynamicMultiplier = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "Multiplier", 2f, "Multiplier applied after exponent. Higher = more cooldown per glide second.");
_dynamicMinSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "MinSeconds", 10f, "Minimum cooldown seconds (also used for short hops).");
_dynamicMaxSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "MaxSeconds", 150f, "Maximum cooldown seconds cap.");
_dynamicShortHopThresholdSeconds = ((BaseUnityPlugin)this).Config.Bind<float>("DynamicCooldown", "ShortHopThresholdSeconds", 1f, "Glides with duration <= this threshold use MinSeconds cooldown.");
_showStatusEffect = ((BaseUnityPlugin)this).Config.Bind<bool>("UI", "ShowStatusEffect", true, "Show a cooldown status effect with a countdown timer.");
_leaderboardEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Leaderboard", "Enabled", true, "Enable server-persistent leaderboard + hotkey.");
_leaderboardHotkey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("Leaderboard", "Hotkey", (KeyCode)288, "Hotkey to toggle leaderboard display (client-side).");
_leaderboardMaxRows = ((BaseUnityPlugin)this).Config.Bind<int>("Leaderboard", "MaxRows", 20, "Rows to show in the leaderboard display.");
_toastVariantsAllTimePB = ((BaseUnityPlugin)this).Config.Bind<string>("UI", "ToastVariantsAllTimePB", "ALL-TIME PB! {dist}m|New ALL-TIME record: {dist}m|Skål! All-time PB: {dist}m|Legendary! ALL-TIME {dist}m", "Client-only: '|' separated toasts for ALL-TIME PB. Placeholders: {dist}, {dist1}, {name}, {when}");
_toastVariantsDailyPB = ((BaseUnityPlugin)this).Config.Bind<string>("UI", "ToastVariantsDailyPB", "Daily PB! {dist}m|New session best: {dist}m|Nice — daily best {dist}m|Fresh start, new PB {dist}m", "Client-only: '|' separated toasts for DAILY (per-login) PB. Placeholders: {dist}, {dist1}, {name}, {when}");
_toastVariantsNormal = ((BaseUnityPlugin)this).Config.Bind<string>("UI", "ToastVariantsGlideComplete", "You traveled {dist}m|Glide complete: {dist}m|Nice run — {dist}m|Distance: {dist}m", "Client-only: '|' separated toasts for normal results. Placeholders: {dist}, {dist1}, {name}, {when}");
_debugLogs = ((BaseUnityPlugin)this).Config.Bind<bool>("Debug", "DebugLogs", false, "Verbose debug logging.");
Runtime.LoadFromConfig();
_recordsPath = Path.Combine(Paths.ConfigPath, "BalancedGliders_Leaderboard.txt");
LoadRecordsFromDisk();
_harmony = new Harmony("Pix.BalancedGliders");
ApplyAllHarmonyPatches();
}
private void ApplyAllHarmonyPatches()
{
try
{
_harmony.PatchAll(typeof(ObjectDB_RegisterStatusEffect_Patch));
_harmony.PatchAll(typeof(ObjectDB_CopyOtherDB_RegisterStatusEffect_Patch));
_harmony.PatchAll(typeof(GliderSystemPatches));
_harmony.PatchAll(typeof(ZRoutedRpc_Ctor_Register_Patch));
}
catch (Exception arg)
{
((BaseUnityPlugin)this).Logger.LogError((object)string.Format("[{0}] PatchAll failed: {1}", "Balanced Gliders", arg));
}
}
private void Update()
{
//IL_0264: Unknown result type (might be due to invalid IL or missing references)
bool flag = IsNetConnected();
if (flag != _wasConnectedLastTick)
{
_wasConnectedLastTick = flag;
_requestedServerConfig = false;
Runtime.HasServerConfig = false;
_requestTimer = 0f;
_wasGlidingByZdo.Clear();
_wasGlidingByPlayerId.Clear();
_dailyBestById.Clear();
if (IsServer())
{
_glideTrackByZdo.Clear();
}
if (!flag)
{
_lbVisible = false;
_lbText = "";
}
_panelBackingTried = false;
_panelBackingHas = false;
_panelBackingTex = null;
_trophyIconTried = false;
_trophyIconSprite = null;
EnsureHarmonyStillPatched(forceLog: true);
}
_patchCheckTimer += Time.unscaledDeltaTime;
if (_patchCheckTimer >= 5f)
{
_patchCheckTimer = 0f;
EnsureHarmonyStillPatched(forceLog: false);
}
DetectRoutedRpcInstanceChange();
TryRegisterRpcs();
TryRegisterCommands();
if (IsServer() && !_serverConfigHooksInstalled)
{
HookServerConfigEvents();
_serverConfigHooksInstalled = true;
}
if (IsServer() && _rpcsRegistered && !_serverBroadcastedInitialConfig)
{
Runtime.LoadFromConfig();
BroadcastServerConfig();
_serverBroadcastedInitialConfig = true;
}
if (!IsServer() && _serverAuthoritativeConfig != null && _serverAuthoritativeConfig.Value && !_requestedServerConfig && flag)
{
_requestTimer += Time.unscaledDeltaTime;
if (_requestTimer >= 1.5f)
{
_requestTimer = 0f;
RequestServerConfig();
_requestedServerConfig = true;
}
}
if (IsServer() && _recordsDirty && Time.unscaledTime >= _nextRecordsSaveAt)
{
SaveRecordsToDisk();
}
if (_toastUntil > 0f && Time.unscaledTime <= _toastUntil && !string.IsNullOrEmpty(_toastText))
{
ShowHud((MessageType)2, _toastText);
_toastUntil = 0f;
_toastText = null;
}
if (EffectiveLeaderboard && flag && !IsTypingOrConsoleOpen() && ZInput.GetKeyDown(EffectiveLeaderboardHotkey, true))
{
_lbVisible = !_lbVisible;
if (_lbVisible)
{
if (string.IsNullOrEmpty(_lbText))
{
_lbText = "Loading leaderboard...";
}
RequestLeaderboardIfClient();
}
}
if (_lbVisible && (!flag || !EffectiveLeaderboard))
{
_lbVisible = false;
}
_localCleanupTimer += Time.unscaledDeltaTime;
if (_localCleanupTimer < 0.25f)
{
return;
}
_localCleanupTimer = 0f;
try
{
if (!EffectiveShowSE)
{
return;
}
Player localPlayer = Player.m_localPlayer;
if (!((Object)(object)localPlayer == (Object)null) && ((Character)localPlayer).IsOwner())
{
if (!IsOnCooldown(localPlayer, out var _))
{
RemoveCooldownStatusEffectIfPresent(localPlayer);
}
else
{
EnsureCooldownStatusEffect(localPlayer);
}
}
}
catch
{
}
}
private void OnGUI()
{
//IL_0001: Unknown result type (might be due to invalid IL or missing references)
//IL_0006: Unknown result type (might be due to invalid IL or missing references)
//IL_0007: Unknown result type (might be due to invalid IL or missing references)
//IL_000c: Unknown result type (might be due to invalid IL or missing references)
//IL_0504: Unknown result type (might be due to invalid IL or missing references)
//IL_050b: 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_00de: Unknown result type (might be due to invalid IL or missing references)
//IL_0121: Unknown result type (might be due to invalid IL or missing references)
//IL_012b: Expected O, but got Unknown
//IL_0126: Unknown result type (might be due to invalid IL or missing references)
//IL_0140: Unknown result type (might be due to invalid IL or missing references)
//IL_014a: Expected O, but got Unknown
//IL_0145: Unknown result type (might be due to invalid IL or missing references)
//IL_01e2: Unknown result type (might be due to invalid IL or missing references)
//IL_01ee: Expected O, but got Unknown
//IL_01f7: Unknown result type (might be due to invalid IL or missing references)
//IL_0203: Expected O, but got Unknown
//IL_017d: Unknown result type (might be due to invalid IL or missing references)
//IL_0187: Expected O, but got Unknown
//IL_0182: Unknown result type (might be due to invalid IL or missing references)
//IL_0233: Unknown result type (might be due to invalid IL or missing references)
//IL_023f: Expected O, but got Unknown
//IL_0334: Unknown result type (might be due to invalid IL or missing references)
//IL_0366: Unknown result type (might be due to invalid IL or missing references)
//IL_030e: Unknown result type (might be due to invalid IL or missing references)
//IL_0319: Unknown result type (might be due to invalid IL or missing references)
//IL_0320: Unknown result type (might be due to invalid IL or missing references)
//IL_032c: Unknown result type (might be due to invalid IL or missing references)
//IL_04e7: Unknown result type (might be due to invalid IL or missing references)
//IL_041e: Unknown result type (might be due to invalid IL or missing references)
//IL_042a: Expected O, but got Unknown
//IL_0489: Unknown result type (might be due to invalid IL or missing references)
//IL_0450: Unknown result type (might be due to invalid IL or missing references)
//IL_046b: Unknown result type (might be due to invalid IL or missing references)
Matrix4x4 matrix = GUI.matrix;
Color color = GUI.color;
try
{
GUI.matrix = Matrix4x4.identity;
if (!_lbVisible || !IsNetConnected() || !EffectiveLeaderboard || IsTypingOrConsoleOpen())
{
return;
}
EnsureLeaderboardGuiStyles();
EnsureValheimPanelBacking();
EnsureFirstPlaceTrophyIcon();
_lbTitleStyle.wordWrap = true;
_lbBodyStyle.wordWrap = true;
_lbFooterStyle.wordWrap = true;
string text = "BALANCED GLIDERS — TOP GLIDES";
string text2 = (string.IsNullOrEmpty(_lbText) ? "Loading leaderboard..." : _lbText);
string[] array = text2.Replace("\r", "").Split(new char[1] { '\n' });
string text3 = $"{EffectiveLeaderboardHotkey} = Toggle Leaderboard";
float num = 16f;
float num2 = 6f;
float num3 = (float)Screen.width - 40f;
float num4 = 380f;
float num5 = 0f;
num5 = Mathf.Max(num5, _lbTitleStyle.CalcSize(new GUIContent(text)).x);
num5 = Mathf.Max(num5, _lbFooterStyle.CalcSize(new GUIContent(text3)).x);
for (int i = 0; i < array.Length; i++)
{
string text4 = (string.IsNullOrEmpty(array[i]) ? " " : array[i]);
float x = _lbBodyStyle.CalcSize(new GUIContent(text4)).x;
if (x > num5)
{
num5 = x;
}
}
float num6 = Mathf.Clamp(num5 + num * 2f + 10f, num4, num3);
float num7 = num6 - num * 2f;
float num8 = _lbTitleStyle.CalcHeight(new GUIContent(text), num7);
float num9 = _lbFooterStyle.CalcHeight(new GUIContent(text3), num7);
float num10 = 0f;
for (int j = 0; j < array.Length; j++)
{
string text5 = (string.IsNullOrEmpty(array[j]) ? " " : array[j]);
float num11 = _lbBodyStyle.CalcHeight(new GUIContent(text5), num7);
num10 += num11;
if (j != array.Length - 1)
{
num10 += num2;
}
}
float num12 = num + num8 + 12f + num10 + 12f + num9 + num + 10f;
float num13 = ((float)Screen.width - num6) * 0.5f;
float num14 = Mathf.Clamp((float)Screen.height * 0.18f, 70f, (float)Screen.height - num12 - 40f);
Rect val = default(Rect);
((Rect)(ref val))..ctor(num13, num14, num6, num12);
if (_panelBackingHas && (Object)(object)_panelBackingTex != (Object)null)
{
float panelDarkenMultiplier = GetPanelDarkenMultiplier();
GUI.color = new Color(panelDarkenMultiplier, panelDarkenMultiplier, panelDarkenMultiplier, 1f);
GUI.DrawTextureWithTexCoords(val, (Texture)(object)_panelBackingTex, _panelBackingUv, true);
GUI.color = color;
}
GUI.Box(val, GUIContent.none, _lbPanelStyle);
float num15 = ((Rect)(ref val)).x + num;
float num16 = ((Rect)(ref val)).y + num;
GUI.Label(new Rect(num15, num16, num7, num8), text, _lbTitleStyle);
num16 += num8 + 12f;
float num17 = 18f;
float num18 = 6f;
for (int k = 0; k < array.Length; k++)
{
string text6 = (string.IsNullOrEmpty(array[k]) ? " " : array[k]);
bool flag = k == 0;
Sprite val2 = null;
if (flag)
{
val2 = _trophyIconSprite;
if ((Object)(object)val2 == (Object)null)
{
val2 = GetFirstPlaceFallbackSprite();
}
}
float num19 = ((flag && (Object)(object)val2 != (Object)null) ? (num7 - (num17 + num18)) : num7);
if (num19 < 60f)
{
num19 = 60f;
}
float num20 = _lbBodyStyle.CalcHeight(new GUIContent(text6), num19);
if (flag && (Object)(object)val2 != (Object)null)
{
DrawSprite(new Rect(num15, num16 + 2f, num17, num17), val2);
GUI.Label(new Rect(num15 + num17 + num18, num16, num19, num20), text6, _lbBodyStyle);
}
else
{
GUI.Label(new Rect(num15, num16, num7, num20), text6, _lbBodyStyle);
}
num16 += num20;
if (k != array.Length - 1)
{
num16 += num2;
}
}
num16 += 12f;
GUI.Label(new Rect(num15, num16, num7, num9), text3, _lbFooterStyle);
}
catch
{
}
finally
{
GUI.color = color;
GUI.matrix = matrix;
}
}
private static void Dbg(string msg)
{
try
{
if (EffectiveDebug && !string.IsNullOrEmpty(msg))
{
Debug.Log((object)("[BalancedGliders] " + msg));
}
}
catch
{
}
}
private static void EnsureFirstPlaceTrophyIcon()
{
if (_trophyIconTried)
{
return;
}
_trophyIconTried = true;
try
{
if ((Object)(object)InventoryGui.instance == (Object)null)
{
return;
}
Image[] componentsInChildren = ((Component)InventoryGui.instance).GetComponentsInChildren<Image>(true);
if (componentsInChildren == null || componentsInChildren.Length == 0)
{
return;
}
foreach (Image val in componentsInChildren)
{
if (!((Object)(object)val == (Object)null) && !((Object)(object)val.sprite == (Object)null))
{
string text = (((Object)(object)((Component)val).gameObject != (Object)null) ? ((Object)((Component)val).gameObject).name : "");
string text2 = ((Object)val.sprite).name ?? "";
string text3 = text.ToLowerInvariant();
string text4 = text2.ToLowerInvariant();
if (text3.Contains("troph") || text4.Contains("troph"))
{
_trophyIconSprite = val.sprite;
break;
}
}
}
}
catch
{
_trophyIconSprite = null;
}
}
private static void DrawSprite(Rect rect, Sprite sprite)
{
//IL_0025: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: 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_0070: Unknown result type (might be due to invalid IL or missing references)
if (!((Object)(object)sprite == (Object)null))
{
Texture2D texture = sprite.texture;
if (!((Object)(object)texture == (Object)null))
{
Rect textureRect = sprite.textureRect;
Rect val = default(Rect);
((Rect)(ref val))..ctor(((Rect)(ref textureRect)).x / (float)((Texture)texture).width, ((Rect)(ref textureRect)).y / (float)((Texture)texture).height, ((Rect)(ref textureRect)).width / (float)((Texture)texture).width, ((Rect)(ref textureRect)).height / (float)((Texture)texture).height);
GUI.DrawTextureWithTexCoords(rect, (Texture)(object)texture, val, true);
}
}
}
private static float GetPanelDarkenMultiplier()
{
return IsNightTime() ? 0.8f : 1f;
}
private static bool IsNightTime()
{
try
{
try
{
bool flag = EnvMan.IsDay();
return !flag;
}
catch
{
}
EnvMan instance = EnvMan.instance;
if ((Object)(object)instance == (Object)null)
{
return false;
}
try
{
float dayFraction = instance.GetDayFraction();
return dayFraction < 0.25f || dayFraction > 0.75f;
}
catch
{
}
}
catch
{
}
return false;
}
private static void EnsureLeaderboardGuiStyles()
{
//IL_0019: Unknown result type (might be due to invalid IL or missing references)
//IL_001e: Unknown result type (might be due to invalid IL or missing references)
//IL_0026: 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_0037: Unknown result type (might be due to invalid IL or missing references)
//IL_0044: Expected O, but got Unknown
//IL_004e: Unknown result type (might be due to invalid IL or missing references)
//IL_0053: Unknown result type (might be due to invalid IL or missing references)
//IL_005b: Unknown result type (might be due to invalid IL or missing references)
//IL_0063: Unknown result type (might be due to invalid IL or missing references)
//IL_006c: Unknown result type (might be due to invalid IL or missing references)
//IL_0079: Expected O, but got Unknown
//IL_0083: 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_0090: Unknown result type (might be due to invalid IL or missing references)
//IL_0098: Unknown result type (might be due to invalid IL or missing references)
//IL_00a1: Unknown result type (might be due to invalid IL or missing references)
//IL_00ae: Expected O, but got Unknown
//IL_00b8: Unknown result type (might be due to invalid IL or missing references)
//IL_00c2: Expected O, but got Unknown
//IL_00cf: Unknown result type (might be due to invalid IL or missing references)
//IL_00d9: Expected O, but got Unknown
//IL_00f8: Unknown result type (might be due to invalid IL or missing references)
//IL_0121: Unknown result type (might be due to invalid IL or missing references)
//IL_014a: Unknown result type (might be due to invalid IL or missing references)
if (!_guiInit)
{
_lbTitleStyle = new GUIStyle(GUI.skin.label)
{
alignment = (TextAnchor)1,
fontStyle = (FontStyle)1,
fontSize = 22,
wordWrap = true
};
_lbBodyStyle = new GUIStyle(GUI.skin.label)
{
alignment = (TextAnchor)0,
fontStyle = (FontStyle)0,
fontSize = 18,
wordWrap = true
};
_lbFooterStyle = new GUIStyle(GUI.skin.label)
{
alignment = (TextAnchor)1,
fontStyle = (FontStyle)1,
fontSize = 14,
wordWrap = true
};
_lbPanelStyle = new GUIStyle(GUI.skin.box);
_lbPanelStyle.padding = new RectOffset(16, 16, 16, 16);
_lbTitleStyle.normal.textColor = new Color(0.93f, 0.78f, 0.46f, 1f);
_lbFooterStyle.normal.textColor = new Color(0.9f, 0.83f, 0.65f, 1f);
_lbBodyStyle.normal.textColor = new Color(0.95f, 0.95f, 0.95f, 1f);
_guiInit = true;
}
}
private static void EnsureValheimPanelBacking()
{
//IL_02e9: Unknown result type (might be due to invalid IL or missing references)
//IL_02ee: Unknown result type (might be due to invalid IL or missing references)
//IL_033e: Unknown result type (might be due to invalid IL or missing references)
//IL_0340: Unknown result type (might be due to invalid IL or missing references)
//IL_00c8: 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_00bd: Unknown result type (might be due to invalid IL or missing references)
//IL_00cd: Unknown result type (might be due to invalid IL or missing references)
if (_panelBackingTried)
{
return;
}
_panelBackingTried = true;
try
{
if ((Object)(object)InventoryGui.instance == (Object)null)
{
return;
}
Image[] componentsInChildren = ((Component)InventoryGui.instance).GetComponentsInChildren<Image>(true);
if (componentsInChildren == null || componentsInChildren.Length == 0)
{
return;
}
Image val = null;
float num = -1f;
foreach (Image val2 in componentsInChildren)
{
if ((Object)(object)val2 == (Object)null)
{
continue;
}
Sprite sprite = val2.sprite;
if ((Object)(object)sprite == (Object)null || (Object)(object)sprite.texture == (Object)null)
{
continue;
}
Rect val3 = (Rect)(((Object)(object)((Graphic)val2).rectTransform != (Object)null) ? ((Graphic)val2).rectTransform.rect : default(Rect));
float num2 = Mathf.Abs(((Rect)(ref val3)).width * ((Rect)(ref val3)).height);
if (num2 < 20000f)
{
continue;
}
string text = (((Object)sprite).name ?? "").ToLowerInvariant();
if (!text.Contains("tooltip") && !text.Contains("tip") && !text.Contains("scroll") && !text.Contains("button") && !text.Contains("icon") && !text.Contains("small") && !text.Contains("border") && !text.Contains("frame_small") && !text.Contains("paper") && !text.Contains("parch") && !text.Contains("list"))
{
float num3 = num2;
bool flag = text.Contains("wood");
bool flag2 = text.Contains("panel") || text.Contains("back") || text.Contains("bg");
if (flag)
{
num3 *= 1.5f;
}
else if (flag2)
{
num3 *= 1.2f;
}
float num4 = ((Mathf.Abs(((Rect)(ref val3)).height) > 0.01f) ? Mathf.Abs(((Rect)(ref val3)).width / ((Rect)(ref val3)).height) : 1f);
if (num4 >= 1.5f && num4 <= 4f)
{
num3 *= 1.1f;
}
if (num3 > num)
{
num = num3;
val = val2;
}
}
}
if (!((Object)(object)val == (Object)null) && !((Object)(object)val.sprite == (Object)null) && !((Object)(object)val.sprite.texture == (Object)null))
{
Texture2D texture = val.sprite.texture;
Rect textureRect = val.sprite.textureRect;
Rect panelBackingUv = default(Rect);
((Rect)(ref panelBackingUv))..ctor(((Rect)(ref textureRect)).x / (float)((Texture)texture).width, ((Rect)(ref textureRect)).y / (float)((Texture)texture).height, ((Rect)(ref textureRect)).width / (float)((Texture)texture).width, ((Rect)(ref textureRect)).height / (float)((Texture)texture).height);
_panelBackingTex = texture;
_panelBackingUv = panelBackingUv;
_panelBackingHas = true;
}
}
catch
{
_panelBackingHas = false;
_panelBackingTex = null;
}
}
private static Sprite GetFirstPlaceFallbackSprite()
{
try
{
if ((Object)(object)ObjectDB.instance == (Object)null)
{
return null;
}
GameObject itemPrefab = ObjectDB.instance.GetItemPrefab("TrophyEikthyr");
if ((Object)(object)itemPrefab == (Object)null)
{
return null;
}
ItemDrop component = itemPrefab.GetComponent<ItemDrop>();
if ((Object)(object)component == (Object)null)
{
return null;
}
return component.m_itemData.GetIcon();
}
catch
{
return null;
}
}
private void EnsureHarmonyStillPatched(bool forceLog)
{
try
{
if (!AreCorePatchesPresent())
{
((BaseUnityPlugin)this).Logger.LogWarning((object)"[Balanced Gliders] Detected missing Harmony patches. Re-applying.");
ApplyAllHarmonyPatches();
}
else if (forceLog && _debugLogs != null && _debugLogs.Value)
{
((BaseUnityPlugin)this).Logger.LogInfo((object)"[Balanced Gliders] Harmony patch check OK.");
}
}
catch
{
ApplyAllHarmonyPatches();
}
}
private bool AreCorePatchesPresent()
{
MethodInfo methodInfo = AccessTools.Method(typeof(GliderSystem), "CanGlide", (Type[])null, (Type[])null);
if (methodInfo == null)
{
return false;
}
Patches patchInfo = Harmony.GetPatchInfo((MethodBase)methodInfo);
if (patchInfo == null)
{
return false;
}
bool flag = false;
if (patchInfo.Prefixes != null)
{
for (int i = 0; i < patchInfo.Prefixes.Count; i++)
{
Patch val = patchInfo.Prefixes[i];
if (val != null && val.owner == "Pix.BalancedGliders")
{
flag = true;
break;
}
}
}
if (!flag && patchInfo.Postfixes != null)
{
for (int j = 0; j < patchInfo.Postfixes.Count; j++)
{
Patch val2 = patchInfo.Postfixes[j];
if (val2 != null && val2.owner == "Pix.BalancedGliders")
{
flag = true;
break;
}
}
}
if (!flag)
{
return false;
}
MethodInfo methodInfo2 = AccessTools.Method(typeof(ObjectDB), "Awake", (Type[])null, (Type[])null);
if (methodInfo2 == null)
{
return false;
}
Patches patchInfo2 = Harmony.GetPatchInfo((MethodBase)methodInfo2);
if (patchInfo2 == null)
{
return false;
}
bool result = false;
if (patchInfo2.Postfixes != null)
{
for (int k = 0; k < patchInfo2.Postfixes.Count; k++)
{
Patch val3 = patchInfo2.Postfixes[k];
if (val3 != null && val3.owner == "Pix.BalancedGliders")
{
result = true;
break;
}
}
}
return result;
}
private static bool IsNetConnected()
{
try
{
if ((Object)(object)ZNet.instance == (Object)null)
{
return false;
}
if (IsServer())
{
return true;
}
return ZNet.instance.IsConnected(ZNet.GetUID());
}
catch
{
return false;
}
}
private static bool IsServer()
{
try
{
return (Object)(object)ZNet.instance != (Object)null && ZNet.instance.IsServer();
}
catch
{
return false;
}
}
private static void DetectRoutedRpcInstanceChange()
{
try
{
ZRoutedRpc instance = ZRoutedRpc.instance;
if (instance == null)
{
_lastRoutedRpcInstance = null;
_rpcsRegistered = false;
_serverBroadcastedInitialConfig = false;
}
else if (instance != _lastRoutedRpcInstance)
{
_lastRoutedRpcInstance = instance;
_rpcsRegistered = false;
_serverBroadcastedInitialConfig = false;
}
}
catch
{
_rpcsRegistered = false;
_serverBroadcastedInitialConfig = false;
}
}
private void HookServerConfigEvents()
{
try
{
Action broadcast = delegate
{
Runtime.LoadFromConfig();
BroadcastServerConfig();
};
if (_enabled != null)
{
_enabled.SettingChanged += delegate
{
broadcast();
};
}
if (_cooldownSeconds != null)
{
_cooldownSeconds.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicEnabled != null)
{
_dynamicEnabled.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicBaseSeconds != null)
{
_dynamicBaseSeconds.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicPower != null)
{
_dynamicPower.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicMultiplier != null)
{
_dynamicMultiplier.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicMinSeconds != null)
{
_dynamicMinSeconds.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicMaxSeconds != null)
{
_dynamicMaxSeconds.SettingChanged += delegate
{
broadcast();
};
}
if (_dynamicShortHopThresholdSeconds != null)
{
_dynamicShortHopThresholdSeconds.SettingChanged += delegate
{
broadcast();
};
}
if (_showStatusEffect != null)
{
_showStatusEffect.SettingChanged += delegate
{
broadcast();
};
}
if (_debugLogs != null)
{
_debugLogs.SettingChanged += delegate
{
broadcast();
};
}
if (_leaderboardEnabled != null)
{
_leaderboardEnabled.SettingChanged += delegate
{
broadcast();
};
}
if (_leaderboardHotkey != null)
{
_leaderboardHotkey.SettingChanged += delegate
{
broadcast();
};
}
if (_leaderboardMaxRows != null)
{
_leaderboardMaxRows.SettingChanged += delegate
{
broadcast();
};
}
}
catch
{
}
}
private static void RequestServerConfig()
{
//IL_0033: Unknown result type (might be due to invalid IL or missing references)
//IL_0039: Expected O, but got Unknown
try
{
if (ZRoutedRpc.instance != null && !((Object)(object)ZNet.instance == (Object)null))
{
ZRoutedRpc.instance.InvokeRoutedRPC("BG_RequestConfig", new object[1] { (object)new ZPackage() });
}
}
catch
{
}
}
private static void BroadcastServerConfig()
{
try
{
if (IsServer() && ZRoutedRpc.instance != null)
{
ZPackage val = BuildConfigPackageFromRuntime();
ZRoutedRpc.instance.InvokeRoutedRPC(ZRoutedRpc.Everybody, "BG_Config", new object[1] { val });
}
}
catch
{
}
}
private static ZPackage BuildConfigPackageFromRuntime()
{
//IL_0001: Unknown result type (might be due to invalid IL or missing references)
//IL_0007: Expected O, but got Unknown
//IL_0098: Unknown result type (might be due to invalid IL or missing references)
//IL_00a2: Expected I4, but got Unknown
ZPackage val = new ZPackage();
val.Write(Runtime.Enabled);
val.Write(Runtime.CooldownSeconds);
val.Write(Runtime.DynamicEnabled);
val.Write(Runtime.DynamicBaseSeconds);
val.Write(Runtime.DynamicPower);
val.Write(Runtime.DynamicMultiplier);
val.Write(Runtime.DynamicMinSeconds);
val.Write(Runtime.DynamicMaxSeconds);
val.Write(Runtime.DynamicShortHopThresholdSeconds);
val.Write(Runtime.ShowStatusEffect);
val.Write(Runtime.DebugLogs);
val.Write(Runtime.LeaderboardEnabled);
val.Write((int)Runtime.LeaderboardHotkey);
val.Write(Runtime.LeaderboardMaxRows);
return val;
}
private static void ApplyConfigPackageToRuntime(ZPackage pkg)
{
//IL_008b: Unknown result type (might be due to invalid IL or missing references)
Runtime.Enabled = pkg.ReadBool();
Runtime.CooldownSeconds = pkg.ReadSingle();
Runtime.DynamicEnabled = pkg.ReadBool();
Runtime.DynamicBaseSeconds = pkg.ReadSingle();
Runtime.DynamicPower = pkg.ReadSingle();
Runtime.DynamicMultiplier = pkg.ReadSingle();
Runtime.DynamicMinSeconds = pkg.ReadSingle();
Runtime.DynamicMaxSeconds = pkg.ReadSingle();
Runtime.DynamicShortHopThresholdSeconds = pkg.ReadSingle();
Runtime.ShowStatusEffect = pkg.ReadBool();
Runtime.DebugLogs = pkg.ReadBool();
Runtime.LeaderboardEnabled = pkg.ReadBool();
Runtime.LeaderboardHotkey = (KeyCode)pkg.ReadInt();
Runtime.LeaderboardMaxRows = pkg.ReadInt();
Runtime.HasServerConfig = true;
}
private static bool ShouldUseServerRuntime()
{
if (!IsNetConnected())
{
return false;
}
if (_serverAuthoritativeConfig == null || !_serverAuthoritativeConfig.Value)
{
return false;
}
if (IsServer())
{
return true;
}
if (_lockClientConfig != null && _lockClientConfig.Value)
{
return true;
}
return Runtime.HasServerConfig;
}
private static float ComputeCooldownSeconds(float glideSeconds)
{
bool num;
if (!ShouldUseServerRuntime())
{
if (_dynamicEnabled == null)
{
goto IL_002e;
}
num = _dynamicEnabled.Value;
}
else
{
num = Runtime.DynamicEnabled;
}
if (num)
{
float num2 = Mathf.Max(0f, ShouldUseServerRuntime() ? Runtime.DynamicMinSeconds : ((_dynamicMinSeconds != null) ? _dynamicMinSeconds.Value : 10f));
float num3 = Mathf.Max(num2, ShouldUseServerRuntime() ? Runtime.DynamicMaxSeconds : ((_dynamicMaxSeconds != null) ? _dynamicMaxSeconds.Value : 150f));
float num4 = Mathf.Max(0f, ShouldUseServerRuntime() ? Runtime.DynamicShortHopThresholdSeconds : ((_dynamicShortHopThresholdSeconds != null) ? _dynamicShortHopThresholdSeconds.Value : 1f));
if (glideSeconds <= num4)
{
return Mathf.Clamp(num2, num2, num3);
}
float num5 = Mathf.Max(0f, ShouldUseServerRuntime() ? Runtime.DynamicBaseSeconds : ((_dynamicBaseSeconds != null) ? _dynamicBaseSeconds.Value : 10f));
float num6 = Mathf.Max(0.01f, ShouldUseServerRuntime() ? Runtime.DynamicPower : ((_dynamicPower != null) ? _dynamicPower.Value : 1.2f));
float num7 = Mathf.Max(0f, ShouldUseServerRuntime() ? Runtime.DynamicMultiplier : ((_dynamicMultiplier != null) ? _dynamicMultiplier.Value : 2f));
float num8 = num5 + Mathf.Pow(glideSeconds, num6) * num7;
if (num8 < num2)
{
num8 = num2;
}
if (num8 > num3)
{
num8 = num3;
}
return num8;
}
goto IL_002e;
IL_002e:
float num9 = (ShouldUseServerRuntime() ? Runtime.CooldownSeconds : ((_cooldownSeconds != null) ? _cooldownSeconds.Value : 150f));
return Mathf.Clamp(num9, 0f, 86400f);
}
private static void TryRegisterRpcs()
{
try
{
if (ZRoutedRpc.instance != null && !_rpcsRegistered)
{
ZRoutedRpc.instance.Register<ZPackage>("BG_RequestConfig", (Action<long, ZPackage>)RPC_Server_RequestConfig);
ZRoutedRpc.instance.Register<ZPackage>("BG_GlideStart", (Action<long, ZPackage>)RPC_Server_GlideStart);
ZRoutedRpc.instance.Register<ZPackage>("BG_GlideEnd", (Action<long, ZPackage>)RPC_Server_GlideEnd);
ZRoutedRpc.instance.Register<ZPackage>("BG_Config", (Action<long, ZPackage>)RPC_Client_ReceiveConfig);
ZRoutedRpc.instance.Register<ZPackage>("BG_SetCooldown", (Action<long, ZPackage>)RPC_Client_SetCooldown);
ZRoutedRpc.instance.Register<ZPackage>("BG_LB_Req", (Action<long, ZPackage>)RPC_Server_RequestLeaderboard);
ZRoutedRpc.instance.Register<ZPackage>("BG_LB_Recv", (Action<long, ZPackage>)RPC_Client_ReceiveLeaderboard);
ZRoutedRpc.instance.Register<ZPackage>("BG_GlideResult", (Action<long, ZPackage>)RPC_Client_GlideResult);
_rpcsRegistered = true;
}
}
catch
{
_rpcsRegistered = false;
}
}
private static void TryRegisterCommands()
{
//IL_0043: 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_003a: Expected O, but got Unknown
//IL_007b: Unknown result type (might be due to invalid IL or missing references)
//IL_0067: Unknown result type (might be due to invalid IL or missing references)
//IL_006c: Unknown result type (might be due to invalid IL or missing references)
//IL_0072: Expected O, but got Unknown
if (_commandsRegistered)
{
return;
}
try
{
object obj = <>c.<>9__115_0;
if (obj == null)
{
ConsoleEvent val = delegate
{
OutputClient(BuildStatusText(), hud: false);
};
<>c.<>9__115_0 = val;
obj = (object)val;
}
new ConsoleCommand("bg_status", "Balanced Gliders: show effective status.", (ConsoleEvent)obj, false, false, false, false, false, (ConsoleOptionsFetcher)null, false, false, false);
object obj2 = <>c.<>9__115_1;
if (obj2 == null)
{
ConsoleEvent val2 = delegate
{
if (!EffectiveLeaderboard)
{
OutputClient("Balanced Gliders: leaderboard is disabled.", hud: true);
}
else
{
_lbVisible = !_lbVisible;
if (_lbVisible)
{
if (string.IsNullOrEmpty(_lbText))
{
_lbText = "Loading leaderboard...";
}
RequestLeaderboardIfClient();
}
}
};
<>c.<>9__115_1 = val2;
obj2 = (object)val2;
}
new ConsoleCommand("bg_top", "Balanced Gliders: toggle leaderboard.", (ConsoleEvent)obj2, false, false, false, false, false, (ConsoleOptionsFetcher)null, false, false, false);
_commandsRegistered = true;
}
catch
{
_commandsRegistered = true;
}
}
private static void OutputClient(string text, bool hud)
{
try
{
if (!string.IsNullOrEmpty(text))
{
if (hud && (Object)(object)MessageHud.instance != (Object)null)
{
MessageHud.instance.ShowMessage((MessageType)1, text, 0, (Sprite)null, false);
}
if ((Object)(object)Chat.instance != (Object)null)
{
Chat.instance.SendText((Type)1, text);
}
if (EffectiveDebug)
{
Debug.Log((object)("[Balanced Gliders] " + text));
}
}
}
catch
{
}
}
private static string BuildStatusText()
{
//IL_0094: Unknown result type (might be due to invalid IL or missing references)
try
{
bool flag = IsNetConnected();
bool flag2 = IsServer();
bool flag3 = ShouldUseServerRuntime();
return "[Balanced Gliders v0.8.1] status\n" + $"Connected={flag} Server={flag2}\n" + $"RPCsRegistered={_rpcsRegistered} HasServerConfig={Runtime.HasServerConfig} UseServerRuntime={flag3}\n" + $"Enabled={EffectiveEnabled} ShowSE={EffectiveShowSE}\n" + $"Leaderboard={EffectiveLeaderboard} Hotkey={EffectiveLeaderboardHotkey} MaxRows={EffectiveLeaderboardMaxRows}";
}
catch
{
return "[Balanced Gliders] status unavailable.";
}
}
private static void RPC_Server_RequestConfig(long sender, ZPackage pkg)
{
try
{
if (IsServer())
{
Runtime.LoadFromConfig();
ZPackage val = BuildConfigPackageFromRuntime();
ZRoutedRpc.instance.InvokeRoutedRPC(sender, "BG_Config", new object[1] { val });
}
}
catch
{
}
}
private static void RPC_Client_ReceiveConfig(long sender, ZPackage pkg)
{
try
{
if (!IsServer())
{
ApplyConfigPackageToRuntime(pkg);
}
}
catch
{
}
}
private static void RPC_Server_GlideStart(long sender, ZPackage pkg)
{
//IL_006a: Unknown result type (might be due to invalid IL or missing references)
//IL_006f: Unknown result type (might be due to invalid IL or missing references)
//IL_0091: Unknown result type (might be due to invalid IL or missing references)
//IL_00f3: Unknown result type (might be due to invalid IL or missing references)
//IL_00ff: Unknown result type (might be due to invalid IL or missing references)
//IL_0104: Unknown result type (might be due to invalid IL or missing references)
try
{
if (!IsServer() || !EffectiveEnabled)
{
return;
}
long num = 0L;
try
{
num = pkg.ReadLong();
}
catch
{
num = 0L;
}
ZNetPeer val = (((Object)(object)ZNet.instance != (Object)null) ? ZNet.instance.GetPeer(sender) : null);
if (val == null)
{
return;
}
ZDOID characterID = val.m_characterID;
if (((ZDOID)(ref characterID)).IsNone())
{
return;
}
ZDO val2 = ((ZDOMan.instance != null) ? ZDOMan.instance.GetZDO(characterID) : null);
if (val2 != null)
{
long networkTimeMs = GetNetworkTimeMs();
long num2 = networkTimeMs;
if (num > 0 && Math.Abs(num - networkTimeMs) <= 10000)
{
num2 = num;
}
val2.Set(ZdoKey_GlideStartMs, num2);
if (EffectiveLeaderboard)
{
_glideTrackByZdo[characterID] = new GlideTrack
{
StartPos = val2.GetPosition(),
StartMs = num2
};
}
}
}
catch
{
}
}
private static void RPC_Server_GlideEnd(long sender, ZPackage pkg)
{
//IL_01bc: Unknown result type (might be due to invalid IL or missing references)
//IL_006a: Unknown result type (might be due to invalid IL or missing references)
//IL_006f: Unknown result type (might be due to invalid IL or missing references)
//IL_0091: Unknown result type (might be due to invalid IL or missing references)
//IL_017a: Unknown result type (might be due to invalid IL or missing references)
//IL_0181: Expected O, but got Unknown
//IL_013e: Unknown result type (might be due to invalid IL or missing references)
try
{
if (!IsServer() || !EffectiveEnabled)
{
return;
}
long num = 0L;
try
{
num = pkg.ReadLong();
}
catch
{
num = 0L;
}
ZNetPeer val = (((Object)(object)ZNet.instance != (Object)null) ? ZNet.instance.GetPeer(sender) : null);
if (val == null)
{
return;
}
ZDOID characterID = val.m_characterID;
if (((ZDOID)(ref characterID)).IsNone())
{
return;
}
ZDO val2 = ((ZDOMan.instance != null) ? ZDOMan.instance.GetZDO(characterID) : null);
if (val2 == null)
{
return;
}
long networkTimeMs = GetNetworkTimeMs();
long num2 = networkTimeMs;
if (num > 0 && Math.Abs(num - networkTimeMs) <= 10000)
{
num2 = num;
}
long @long = val2.GetLong(ZdoKey_GlideStartMs, 0L);
val2.Set(ZdoKey_GlideStartMs, 0L);
float num3 = 0f;
if (@long > 0 && num2 > @long)
{
num3 = (float)(num2 - @long) / 1000f;
}
if (num3 < 0.15f)
{
if (EffectiveLeaderboard)
{
_glideTrackByZdo.Remove(characterID);
}
return;
}
float num4 = ComputeCooldownSeconds(num3);
long num5 = num2 + (long)(Mathf.Max(0f, num4) * 1000f);
val2.Set(ZdoKey_CooldownEndMs, num5);
try
{
ZPackage val3 = new ZPackage();
val3.Write(num5);
ZRoutedRpc.instance.InvokeRoutedRPC(sender, "BG_SetCooldown", new object[1] { val3 });
}
catch
{
}
if (EffectiveLeaderboard)
{
UpdateLeaderboard_Server(sender, val, characterID, val2, num3);
}
}
catch
{
}
}
private static void RPC_Client_SetCooldown(long sender, ZPackage pkg)
{
try
{
if (IsServer())
{
return;
}
long num = 0L;
try
{
num = pkg.ReadLong();
}
catch
{
num = 0L;
}
if (num <= 0)
{
return;
}
Player localPlayer = Player.m_localPlayer;
if (!((Object)(object)localPlayer == (Object)null) && ((Character)localPlayer).IsOwner())
{
ZDO zdo = GetZdo(localPlayer);
if (zdo != null)
{
zdo.Set(ZdoKey_CooldownEndMs, num);
}
}
}
catch
{
}
}
private static void RPC_Server_RequestLeaderboard(long sender, ZPackage pkg)
{
//IL_0029: Unknown result type (might be due to invalid IL or missing references)
//IL_002f: Expected O, but got Unknown
try
{
if (IsServer() && EffectiveLeaderboard)
{
string text = BuildLeaderboardText_Server(EffectiveLeaderboardMaxRows);
ZPackage val = new ZPackage();
val.Write(text ?? "");
ZRoutedRpc.instance.InvokeRoutedRPC(sender, "BG_LB_Recv", new object[1] { val });
}
}
catch
{
}
}
private static void RPC_Client_ReceiveLeaderboard(long sender, ZPackage pkg)
{
try
{
if (!IsServer())
{
string text = "";
try
{
text = pkg.ReadString();
}
catch
{
text = "";
}
if (string.IsNullOrEmpty(text))
{
text = "No leaderboard data available.";
}
_lbText = text;
_lbLastRequestAt = Time.unscaledTime;
}
}
catch
{
}
}
private static void RPC_Client_GlideResult(long sender, ZPackage pkg)
{
try
{
if (!IsServer())
{
float num = 0f;
bool flag = false;
bool flag2 = false;
try
{
num = pkg.ReadSingle();
}
catch
{
num = 0f;
}
try
{
flag = pkg.ReadBool();
}
catch
{
flag = false;
}
try
{
flag2 = pkg.ReadBool();
}
catch
{
flag2 = false;
}
_toastText = BuildToastText_Client(num, flag, flag2);
_toastUntil = Time.unscaledTime + 0.05f;
}
}
catch
{
}
}
private static void UpdateLeaderboard_Server(long senderUid, ZNetPeer peer, ZDOID zdoid, ZDO zdo, float airtimeSeconds)
{
//IL_002f: Unknown result type (might be due to invalid IL or missing references)
//IL_004a: Unknown result type (might be due to invalid IL or missing references)
//IL_0052: Unknown result type (might be due to invalid IL or missing references)
//IL_0057: Unknown result type (might be due to invalid IL or missing references)
//IL_0059: Unknown result type (might be due to invalid IL or missing references)
//IL_005e: Unknown result type (might be due to invalid IL or missing references)
//IL_005f: Unknown result type (might be due to invalid IL or missing references)
//IL_0065: Unknown result type (might be due to invalid IL or missing references)
//IL_006d: Unknown result type (might be due to invalid IL or missing references)
//IL_0073: Unknown result type (might be due to invalid IL or missing references)
//IL_0091: Unknown result type (might be due to invalid IL or missing references)
//IL_0097: Unknown result type (might be due to invalid IL or missing references)
//IL_0281: Unknown result type (might be due to invalid IL or missing references)
//IL_0288: Expected O, but got Unknown
try
{
if (!IsServer() || peer == null || zdo == null || !_glideTrackByZdo.TryGetValue(zdoid, out var value))
{
return;
}
_glideTrackByZdo.Remove(zdoid);
Vector3 position = zdo.GetPosition();
Vector3 startPos = value.StartPos;
float num = position.x - startPos.x;
float num2 = position.z - startPos.z;
float num3 = Mathf.Sqrt(num * num + num2 * num2);
float num4 = Mathf.Max(0f, startPos.y - position.y);
if (num3 < 0.5f)
{
return;
}
string name = SafePeerName(peer);
string text = NormalizeNameKey(name);
if (string.IsNullOrEmpty(text))
{
return;
}
long num5 = text.GetStableHashCode();
if (num5 == 0)
{
num5 = senderUid;
}
if (num5 == 0)
{
return;
}
long networkTimeMs = GetNetworkTimeMs();
float num6 = 0f;
foreach (RecordEntry value4 in _recordsById.Values)
{
if (value4 != null)
{
string text2 = NormalizeNameKey(value4.Name);
if (text2 == text && value4.BestDistance > num6)
{
num6 = value4.BestDistance;
}
}
}
if (!_recordsById.TryGetValue(num5, out var value2) || value2 == null)
{
value2 = new RecordEntry
{
Id = num5
};
_recordsById[num5] = value2;
}
value2.Name = name;
value2.LatestDistance = num3;
value2.LatestAirtime = airtimeSeconds;
value2.LatestDrop = num4;
value2.UpdatedAtMs = networkTimeMs;
bool flag = num3 > num6 + 0.01f;
if (flag)
{
value2.BestDistance = num3;
value2.BestAirtime = airtimeSeconds;
value2.BestDrop = num4;
}
float value3;
bool flag2 = !_dailyBestById.TryGetValue(num5, out value3) || num3 > value3 + 0.01f;
if (flag2)
{
_dailyBestById[num5] = num3;
}
_recordsDirty = true;
_nextRecordsSaveAt = Time.unscaledTime + 2f;
try
{
ZPackage val = new ZPackage();
val.Write(num3);
val.Write(flag2);
val.Write(flag);
ZRoutedRpc.instance.InvokeRoutedRPC(senderUid, "BG_GlideResult", new object[1] { val });
}
catch
{
}
}
catch
{
}
}
private static string BuildLeaderboardText_Server(int topN)
{
try
{
if (!IsServer())
{
return "Balanced Gliders: leaderboard is server-only.";
}
if (_recordsById.Count == 0)
{
return "(no records yet)";
}
int num = Mathf.Clamp(topN, 5, 100);
Dictionary<string, RecordEntry> dictionary = new Dictionary<string, RecordEntry>(StringComparer.OrdinalIgnoreCase);
foreach (RecordEntry value4 in _recordsById.Values)
{
if (value4 != null)
{
string text = (string.IsNullOrEmpty(value4.Name) ? "Someone" : value4.Name);
string text2 = NormalizeNameKey(text);
if (string.IsNullOrEmpty(text2))
{
text2 = text;
}
if (!dictionary.TryGetValue(text2, out var value) || value == null)
{
dictionary[text2] = value4;
}
else if (value4.BestDistance > value.BestDistance + 0.01f || (Mathf.Abs(value4.BestDistance - value.BestDistance) <= 0.01f && value4.UpdatedAtMs > value.UpdatedAtMs))
{
dictionary[text2] = value4;
}
}
}
List<RecordEntry> list = new List<RecordEntry>(dictionary.Values);
list.Sort((RecordEntry a, RecordEntry b) => b.BestDistance.CompareTo(a.BestDistance));
int num2 = Mathf.Min(num, list.Count);
StringBuilder stringBuilder = new StringBuilder(1024);
for (int i = 0; i < num2; i++)
{
RecordEntry recordEntry = list[i];
string value2 = (string.IsNullOrEmpty(recordEntry.Name) ? "Someone" : recordEntry.Name);
string value3 = (i + 1).ToString(CultureInfo.InvariantCulture) + ". ";
stringBuilder.Append(value3).Append(value2).Append(" — ")
.Append(recordEntry.BestDistance.ToString("0", CultureInfo.InvariantCulture))
.Append("m | ")
.Append("Drop ")
.Append(recordEntry.BestDrop.ToString("0", CultureInfo.InvariantCulture))
.Append("m | ")
.Append(recordEntry.BestAirtime.ToString("0.0", CultureInfo.InvariantCulture))
.Append("s")
.Append(" (Latest ")
.Append(recordEntry.LatestDistance.ToString("0", CultureInfo.InvariantCulture))
.Append("m | ")
.Append("Drop ")
.Append(recordEntry.LatestDrop.ToString("0", CultureInfo.InvariantCulture))
.Append("m | ")
.Append(recordEntry.LatestAirtime.ToString("0.0", CultureInfo.InvariantCulture))
.Append("s)")
.Append('\n');
}
return stringBuilder.ToString().TrimEnd(new char[1] { '\n' });
}
catch
{
return "No leaderboard data available.";
}
}
private static void LoadRecordsFromDisk()
{
try
{
if (string.IsNullOrEmpty(_recordsPath) || !File.Exists(_recordsPath))
{
return;
}
string[] array = File.ReadAllLines(_recordsPath);
if (array == null || array.Length == 0)
{
return;
}
_recordsById.Clear();
foreach (string text in array)
{
if (string.IsNullOrEmpty(text))
{
continue;
}
List<string> list = SplitPipe(text);
if (list != null && list.Count >= 9 && long.TryParse(list[0], NumberStyles.Integer, CultureInfo.InvariantCulture, out var result) && result != 0)
{
RecordEntry recordEntry = new RecordEntry();
recordEntry.Id = result;
recordEntry.Name = UnescapeField(list[1]);
recordEntry.BestDistance = ParseFloat(list[2]);
recordEntry.BestAirtime = ParseFloat(list[3]);
recordEntry.BestDrop = ParseFloat(list[4]);
recordEntry.LatestDistance = ParseFloat(list[5]);
recordEntry.LatestAirtime = ParseFloat(list[6]);
recordEntry.LatestDrop = ParseFloat(list[7]);
if (!long.TryParse(list[8], NumberStyles.Integer, CultureInfo.InvariantCulture, out var result2))
{
result2 = 0L;
}
recordEntry.UpdatedAtMs = result2;
_recordsById[result] = recordEntry;
}
}
}
catch
{
}
}
private static void SaveRecordsToDisk()
{
try
{
if (string.IsNullOrEmpty(_recordsPath))
{
return;
}
Dictionary<string, RecordEntry> dictionary = new Dictionary<string, RecordEntry>(StringComparer.OrdinalIgnoreCase);
foreach (RecordEntry value3 in _recordsById.Values)
{
if (value3 != null)
{
string text = (string.IsNullOrEmpty(value3.Name) ? "Someone" : value3.Name);
string text2 = NormalizeNameKey(text);
if (string.IsNullOrEmpty(text2))
{
text2 = text;
}
if (!dictionary.TryGetValue(text2, out var value) || value == null || value3.BestDistance > value.BestDistance + 0.01f || (Mathf.Abs(value3.BestDistance - value.BestDistance) <= 0.01f && value3.UpdatedAtMs > value.UpdatedAtMs))
{
dictionary[text2] = value3;
}
}
}
StringBuilder stringBuilder = new StringBuilder(4096);
foreach (KeyValuePair<string, RecordEntry> item in dictionary)
{
RecordEntry value2 = item.Value;
if (value2 != null)
{
stringBuilder.Append(value2.Id.ToString(CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(EscapeField(value2.Name)).Append('|');
stringBuilder.Append(value2.BestDistance.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.BestAirtime.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.BestDrop.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.LatestDistance.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.LatestAirtime.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.LatestDrop.ToString("R", CultureInfo.InvariantCulture)).Append('|');
stringBuilder.Append(value2.UpdatedAtMs.ToString(CultureInfo.InvariantCulture));
stringBuilder.Append('\n');
}
}
File.WriteAllText(_recordsPath, stringBuilder.ToString());
_recordsDirty = false;
}
catch
{
}
}
private static bool IsOnCooldown(Player p, out float remainingSeconds)
{
long cooldownEndMs = GetCooldownEndMs(p);
long networkTimeMs = GetNetworkTimeMs();
long num = cooldownEndMs - networkTimeMs;
remainingSeconds = ((num > 0) ? ((float)num / 1000f) : 0f);
return num > 0;
}
private static long GetCooldownEndMs(Player p)
{
ZDO zdo = GetZdo(p);
if (zdo == null)
{
return 0L;
}
return zdo.GetLong(ZdoKey_CooldownEndMs, 0L);
}
private static bool WasGliding(Player p)
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
if (TryGetValidZdoId(p, out var uid))
{
if (_wasGlidingByZdo.TryGetValue(uid, out var value))
{
return value;
}
return false;
}
long playerIdSafe = GetPlayerIdSafe(p);
if (playerIdSafe != 0 && _wasGlidingByPlayerId.TryGetValue(playerIdSafe, out var value2))
{
return value2;
}
return false;
}
private static void MarkGliding(Player p, bool gliding)
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
if (TryGetValidZdoId(p, out var uid))
{
_wasGlidingByZdo[uid] = gliding;
return;
}
long playerIdSafe = GetPlayerIdSafe(p);
if (playerIdSafe != 0)
{
_wasGlidingByPlayerId[playerIdSafe] = gliding;
}
}
private static long GetPlayerIdSafe(Player p)
{
try
{
return p.GetPlayerID();
}
catch
{
return 0L;
}
}
private static bool TryGetValidZdoId(Player p, out ZDOID uid)
{
//IL_0002: Unknown result type (might be due to invalid IL or missing references)
//IL_001e: Unknown result type (might be due to invalid IL or missing references)
//IL_0023: Unknown result type (might be due to invalid IL or missing references)
//IL_002b: Unknown result type (might be due to invalid IL or missing references)
//IL_0031: Unknown result type (might be due to invalid IL or missing references)
uid = default(ZDOID);
try
{
ZDO zdo = GetZdo(p);
if (zdo == null)
{
return false;
}
uid = zdo.m_uid;
if (((ZDOID)(ref uid)).Equals(default(ZDOID)))
{
return false;
}
return true;
}
catch
{
return false;
}
}
private static ZDO GetZdo(Player p)
{
try
{
ZNetView val = _frNView.Invoke((Character)(object)p);
return ((Object)(object)val != (Object)null) ? val.GetZDO() : null;
}
catch
{
return null;
}
}
private static long GetNetworkTimeMs()
{
double num = Time.realtimeSinceStartupAsDouble;
try
{
ZNet instance = ZNet.instance;
if ((Object)(object)instance != (Object)null)
{
num = instance.GetTimeSeconds();
}
}
catch
{
}
return (long)(num * 1000.0);
}
private static string FormatSeconds(float seconds)
{
if (seconds < 0f)
{
seconds = 0f;
}
int num = (int)Mathf.Ceil(seconds);
int num2 = num / 3600;
int num3 = num % 3600 / 60;
int num4 = num % 60;
if (num2 > 0)
{
return num2 + ":" + num3.ToString("00") + ":" + num4.ToString("00");
}
if (num3 > 0)
{
return num3 + ":" + num4.ToString("00");
}
return "0:" + num4.ToString("00");
}
private static bool TryForceSetCooldownIcon(StatusEffect target)
{
if ((Object)(object)target == (Object)null)
{
return false;
}
try
{
ObjectDB instance = ObjectDB.instance;
if ((Object)(object)instance == (Object)null)
{
return false;
}
StatusEffect statusEffect = instance.GetStatusEffect("SlowFall".GetStableHashCode());
if ((Object)(object)statusEffect != (Object)null && (Object)(object)statusEffect.m_icon != (Object)null)
{
target.m_icon = statusEffect.m_icon;
return true;
}
StatusEffect statusEffect2 = instance.GetStatusEffect("SE_FeatherFall".GetStableHashCode());
if ((Object)(object)statusEffect2 != (Object)null && (Object)(object)statusEffect2.m_icon != (Object)null)
{
target.m_icon = statusEffect2.m_icon;
return true;
}
StatusEffect statusEffect3 = instance.GetStatusEffect("Wet".GetStableHashCode());
if ((Object)(object)statusEffect3 != (Object)null && (Object)(object)statusEffect3.m_icon != (Object)null)
{
target.m_icon = statusEffect3.m_icon;
return true;
}
}
catch
{
}
return false;
}
private static void EnsureCooldownSEPrefab()
{
if ((Object)(object)_cooldownSEPrefab != (Object)null)
{
TryForceSetCooldownIcon(_cooldownSEPrefab);
return;
}
try
{
if ((Object)(object)ObjectDB.instance != (Object)null)
{
StatusEffect statusEffect = ObjectDB.instance.GetStatusEffect(CooldownSEHash);
if ((Object)(object)statusEffect != (Object)null)
{
_cooldownSEPrefab = statusEffect;
TryForceSetCooldownIcon(_cooldownSEPrefab);
return;
}
}
}
catch
{
}
SE_GliderCooldown sE_GliderCooldown = ScriptableObject.CreateInstance<SE_GliderCooldown>();
((Object)sE_GliderCooldown).name = "SE_BalancedGliders_Cooldown";
((StatusEffect)sE_GliderCooldown).m_name = "Glider Cooldown";
((StatusEffect)sE_GliderCooldown).m_tooltip = "Glider is recharging.";
((StatusEffect)sE_GliderCooldown).m_ttl = 999999f;
TryForceSetCooldownIcon((StatusEffect)(object)sE_GliderCooldown);
if ((Object)(object)((StatusEffect)sE_GliderCooldown).m_icon == (Object)null)
{
try
{
if ((Object)(object)ObjectDB.instance != (Object)null && ObjectDB.instance.m_StatusEffects != null)
{
foreach (StatusEffect statusEffect2 in ObjectDB.instance.m_StatusEffects)
{
if ((Object)(object)statusEffect2 != (Object)null && (Object)(object)statusEffect2.m_icon != (Object)null)
{
((StatusEffect)sE_GliderCooldown).m_icon = statusEffect2.m_icon;
break;
}
}
}
}
catch
{
}
}
_cooldownSEPrefab = (StatusEffect)(object)sE_GliderCooldown;
}
private static void EnsureCooldownStatusEffect(Player p)
{
if ((Object)(object)p == (Object)null || !EffectiveShowSE)
{
return;
}
SEMan sEMan = ((Character)p).GetSEMan();
if (sEMan == null)
{
return;
}
try
{
EnsureCooldownSEPrefab();
if ((Object)(object)ObjectDB.instance != (Object)null && (Object)(object)ObjectDB.instance.GetStatusEffect(CooldownSEHash) == (Object)null)
{
EnsureSEInObjectDB(ObjectDB.instance);
}
if (!sEMan.HaveStatusEffect(CooldownSEHash))
{
sEMan.AddStatusEffect(CooldownSEHash, true, 0, 0f);
}
}
catch
{
}
}
private static void RemoveCooldownStatusEffectIfPresent(Player p)
{
if ((Object)(object)p == (Object)null)
{
return;
}
SEMan sEMan = ((Character)p).GetSEMan();
if (sEMan == null)
{
return;
}
try
{
if (sEMan.HaveStatusEffect(CooldownSEHash))
{
sEMan.RemoveStatusEffect(CooldownSEHash, true);
}
}
catch
{
}
}
private static void EnsureSEInObjectDB(ObjectDB db)
{
try
{
if ((Object)(object)db == (Object)null)
{
return;
}
StatusEffect statusEffect = db.GetStatusEffect(CooldownSEHash);
if ((Object)(object)statusEffect != (Object)null)
{
_cooldownSEPrefab = statusEffect;
TryForceSetCooldownIcon(statusEffect);
return;
}
EnsureCooldownSEPrefab();
TryForceSetCooldownIcon(_cooldownSEPrefab);
if ((Object)(object)_cooldownSEPrefab != (Object)null && db.m_StatusEffects != null && !db.m_StatusEffects.Contains(_cooldownSEPrefab))
{
db.m_StatusEffects.Add(_cooldownSEPrefab);
}
}
catch
{
}
}
private static bool IsTypingOrConsoleOpen()
{
try
{
if ((Object)(object)Chat.instance != (Object)null && Chat.instance.HasFocus())
{
return true;
}
if (Console.IsVisible())
{
return true;
}
}
catch
{
}
return false;
}
private static void ShowHud(MessageType type, string text)
{
//IL_0024: Unknown result type (might be due to invalid IL or missing references)
try
{
if (!((Object)(object)MessageHud.instance == (Object)null) && !string.IsNullOrEmpty(text))
{
MessageHud.instance.ShowMessage(type, text, 0, (Sprite)null, false);
}
}
catch
{
}
}
private static void RequestLeaderboardIfClient()
{
//IL_006d: Unknown result type (might be due to invalid IL or missing references)
//IL_0073: Expected O, but got Unknown
try
{
if (!EffectiveLeaderboard)
{
return;
}
if (IsServer())
{
_lbText = BuildLeaderboardText_Server(EffectiveLeaderboardMaxRows);
}
else if (!(Time.unscaledTime - _lbLastRequestAt < 0.35f))
{
_lbLastRequestAt = Time.unscaledTime;
if (ZRoutedRpc.instance != null)
{
ZRoutedRpc.instance.InvokeRoutedRPC("BG_LB_Req", new object[1] { (object)new ZPackage() });
}
}
}
catch
{
}
}
private static string BuildToastText_Client(float dist, bool newDaily, bool newAllTime)
{
string pipeSeparated;
string fallback;
string newValue;
if (newAllTime)
{
pipeSeparated = ((_toastVariantsAllTimePB != null) ? _toastVariantsAllTimePB.Value : "");
fallback = $"ALL-TIME PB! {dist:0}m";
newValue = "All-Time PB";
}
else if (newDaily)
{
pipeSeparated = ((_toastVariantsDailyPB != null) ? _toastVariantsDailyPB.Value : "");
fallback = $"Daily PB! {dist:0}m";
newValue = "Daily PB";
}
else
{
pipeSeparated = ((_toastVariantsNormal != null) ? _toastVariantsNormal.Value : "");
fallback = $"You traveled {dist:0}m";
newValue = "Glide Complete";
}
string text = ChooseVariant(pipeSeparated, fallback);
string newValue2 = "Viking";
try
{
Player localPlayer = Player.m_localPlayer;
if ((Object)(object)localPlayer != (Object)null && !string.IsNullOrEmpty(localPlayer.GetPlayerName()))
{
newValue2 = localPlayer.GetPlayerName();
}
}
catch
{
}
return text.Replace("{dist}", dist.ToString("0", CultureInfo.InvariantCulture)).Replace("{dist1}", dist.ToString("0.0", CultureInfo.InvariantCulture)).Replace("{name}", newValue2)
.Replace("{when}", newValue);
}
private static string ChooseVariant(string pipeSeparated, string fallback)
{
if (string.IsNullOrEmpty(pipeSeparated))
{
return fallback;
}
string[] array = pipeSeparated.Split(new char[1] { '|' }, StringSplitOptions.RemoveEmptyEntries);
if (array == null || array.Length == 0)
{
return fallback;
}
int num = Random.Range(0, array.Length);
string text = ((array[num] != null) ? array[num].Trim() : "");
return string.IsNullOrEmpty(text) ? fallback : text;
}
private static string StripRichText(string s)
{
if (string.IsNullOrEmpty(s))
{
return "";
}
StringBuilder stringBuilder = new StringBuilder(s.Length);
bool flag = false;
foreach (char c in s)
{
switch (c)
{
case '<':
flag = true;
continue;
case '>':
flag = false;
continue;
}
if (!flag)
{
stringBuilder.Append(c);
}
}
return stringBuilder.ToString();
}
private static string NormalizeNameKey(string name)
{
if (string.IsNullOrEmpty(name))
{
return "";
}
name = StripRichText(name);
name = name.Trim();
name = name.Replace("\t", " ");
name = name.Replace("|", " ");
while (name.Contains(" "))
{
name = name.Replace(" ", " ");
}
return name.ToLowerInvariant();
}
private static string SafePeerName(ZNetPeer peer)
{
try
{
if (peer == null)
{
return "Someone";
}
string playerName = peer.m_playerName;
if (!string.IsNullOrEmpty(playerName))
{
return playerName;
}
}
catch
{
}
return "Someone";
}
private static string EscapeField(string s)
{
if (s == null)
{
return "";
}
return s.Replace("\\", "\\\\").Replace("|", "\\|").Replace("\n", " ")
.Replace("\r", " ");
}
private static string UnescapeField(string s)
{
if (s == null)
{
return "";
}
StringBuilder stringBuilder = new StringBuilder(s.Length);
bool flag = false;
foreach (char c in s)
{
if (!flag)
{
if (c == '\\')
{
flag = true;
}
else
{
stringBuilder.Append(c);
}
}
else
{
stringBuilder.Append(c);
flag = false;
}
}
return stringBuilder.ToString();
}
private static List<string> SplitPipe(string line)
{
if (line == null)
{
return null;
}
List<string> list = new List<string>(12);
StringBuilder stringBuilder = new StringBuilder(line.Length);
bool flag = false;
foreach (char c in line)
{
if (!flag)
{
switch (c)
{
case '\\':
flag = true;
break;
case '|':
list.Add(stringBuilder.ToString());
stringBuilder.Length = 0;
break;
default:
stringBuilder.Append(c);
break;
}
}
else
{
stringBuilder.Append(c);
flag = false;
}
}
list.Add(stringBuilder.ToString());
return list;
}
private static float ParseFloat(string s)
{
if (float.TryParse(s, NumberStyles.Float, CultureInfo.InvariantCulture, out var result))
{
return result;
}
return 0f;
}
}