using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using UnityEngine;
using UnityEngine.Events;
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: AssemblyTitle("GlobalVoiceVolume")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("GlobalVoiceVolume")]
[assembly: AssemblyCopyright("Copyright © 2026")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("6b1fd74a-5005-4ea7-a0c9-189d17020192")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyVersion("1.0.0.0")]
namespace HoppinHauler.GlobalVoiceVolume;
[BepInPlugin("HoppinHauler.GlobalVoiceVolume", "Global Voice Volume", "1.0.1")]
public sealed class Plugin : BaseUnityPlugin
{
public const string PluginGuid = "HoppinHauler.GlobalVoiceVolume";
public const string PluginName = "Global Voice Volume";
public const string PluginVersion = "1.0.1";
internal static ConfigEntry<bool> Enabled;
internal static ConfigEntry<bool> ApplyDefaultOnStart;
internal static ConfigEntry<float> DefaultVolumeRaw;
private void Awake()
{
//IL_006a: Unknown result type (might be due to invalid IL or missing references)
Enabled = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "Enabled", true, "Enable the global voice volume slider.");
ApplyDefaultOnStart = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "ApplyDefaultOnStart", true, "Automatically apply DefaultVolumeRaw when QuickMenu initializes (e.g., when joining a lobby).");
DefaultVolumeRaw = ((BaseUnityPlugin)this).Config.Bind<float>("General", "DefaultVolumeRaw", 9999f, "Default value in the game's slider units (example: your slider is -20..20). Set to 9999 to always use slider.maxValue (max volume).");
new Harmony("HoppinHauler.GlobalVoiceVolume").PatchAll();
}
}
internal static class GlobalVoiceOverlay
{
[CompilerGenerated]
private sealed class <ReapplyNextFrame>d__9 : IEnumerator<object>, IDisposable, IEnumerator
{
private int <>1__state;
private object <>2__current;
public QuickMenuManager qm;
object IEnumerator<object>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <ReapplyNextFrame>d__9(int <>1__state)
{
this.<>1__state = <>1__state;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
<>1__state = -2;
}
private bool MoveNext()
{
//IL_004f: Unknown result type (might be due to invalid IL or missing references)
//IL_005a: Expected O, but got Unknown
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<>2__current = null;
<>1__state = 1;
return true;
case 1:
<>1__state = -1;
if (!Plugin.Enabled.Value)
{
return false;
}
if ((Object)GlobalSlider == (Object)null)
{
return false;
}
ApplyVolumeToAll(qm, GlobalSlider.value);
return false;
}
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
}
internal static Slider GlobalSlider;
internal static float LastAppliedValue;
internal static float LastMin;
internal static float LastMax;
internal static void Reset()
{
GlobalSlider = null;
LastAppliedValue = 0f;
LastMin = 0f;
LastMax = 0f;
}
private static float ClampToRange(float v, float min, float max)
{
if (min > max)
{
float num = min;
min = max;
max = num;
}
if (v < min)
{
return min;
}
if (v > max)
{
return max;
}
return v;
}
private static float ResolveDefaultValue(Slider referenceSlider)
{
if ((Object)(object)referenceSlider == (Object)null)
{
return 0f;
}
float minValue = referenceSlider.minValue;
float maxValue = referenceSlider.maxValue;
LastMin = minValue;
LastMax = maxValue;
float value = Plugin.DefaultVolumeRaw.Value;
if (value >= 9999f)
{
return maxValue;
}
return ClampToRange(value, minValue, maxValue);
}
internal static void AddGlobalSlider(QuickMenuManager qm)
{
//IL_0039: Unknown result type (might be due to invalid IL or missing references)
//IL_0044: Expected O, but got Unknown
//IL_01bc: Unknown result type (might be due to invalid IL or missing references)
//IL_01cb: Unknown result type (might be due to invalid IL or missing references)
//IL_01da: Unknown result type (might be due to invalid IL or missing references)
//IL_01e9: Unknown result type (might be due to invalid IL or missing references)
//IL_01f8: Unknown result type (might be due to invalid IL or missing references)
//IL_0207: Unknown result type (might be due to invalid IL or missing references)
//IL_0216: Unknown result type (might be due to invalid IL or missing references)
//IL_021b: Unknown result type (might be due to invalid IL or missing references)
//IL_0250: Unknown result type (might be due to invalid IL or missing references)
//IL_0255: Unknown result type (might be due to invalid IL or missing references)
//IL_0259: Unknown result type (might be due to invalid IL or missing references)
//IL_0260: Unknown result type (might be due to invalid IL or missing references)
//IL_0267: Unknown result type (might be due to invalid IL or missing references)
//IL_0273: Unknown result type (might be due to invalid IL or missing references)
if (!Plugin.Enabled.Value || (Object)(object)qm == (Object)null || (Object)GlobalSlider != (Object)null || qm.playerListSlots == null || qm.playerListSlots.Length == 0)
{
return;
}
PlayerListSlot val = qm.playerListSlots[0];
if (val == null || (Object)(object)val.volumeSlider == (Object)null)
{
return;
}
Slider volumeSlider = val.volumeSlider;
Transform parent = ((Component)volumeSlider).transform.parent;
if ((Object)(object)parent == (Object)null)
{
return;
}
Transform val2 = parent.Find("GlobalVoiceVolume");
if ((Object)(object)val2 != (Object)null)
{
Object.Destroy((Object)(object)((Component)val2).gameObject);
}
GameObject val3 = Object.Instantiate<GameObject>(((Component)volumeSlider).gameObject, parent);
((Object)val3).name = "GlobalVoiceVolume";
Slider component = val3.GetComponent<Slider>();
if ((Object)(object)component == (Object)null)
{
Object.Destroy((Object)(object)val3);
return;
}
GlobalSlider = component;
component.minValue = volumeSlider.minValue;
component.maxValue = volumeSlider.maxValue;
component.wholeNumbers = volumeSlider.wholeNumbers;
LayoutElement val4 = val3.GetComponent<LayoutElement>();
if ((Object)(object)val4 == (Object)null)
{
val4 = val3.AddComponent<LayoutElement>();
}
val4.ignoreLayout = true;
RectTransform component2 = ((Component)volumeSlider).GetComponent<RectTransform>();
RectTransform component3 = val3.GetComponent<RectTransform>();
if ((Object)(object)component2 != (Object)null && (Object)(object)component3 != (Object)null)
{
component3.anchorMin = component2.anchorMin;
component3.anchorMax = component2.anchorMax;
component3.pivot = component2.pivot;
component3.sizeDelta = component2.sizeDelta;
((Transform)component3).localScale = ((Transform)component2).localScale;
component3.anchoredPosition = component2.anchoredPosition + new Vector2(0f, 28f);
}
Image[] componentsInChildren = val3.GetComponentsInChildren<Image>(true);
foreach (Image val5 in componentsInChildren)
{
if (!((Object)(object)val5 == (Object)null))
{
Color color = ((Graphic)val5).color;
((Graphic)val5).color = new Color(color.r, color.g, color.b, 1f);
}
}
((UnityEventBase)component.onValueChanged).RemoveAllListeners();
((UnityEvent<float>)(object)component.onValueChanged).AddListener((UnityAction<float>)delegate(float value)
{
ApplyVolumeToAll(qm, value);
});
float value2 = volumeSlider.value;
if (Plugin.ApplyDefaultOnStart.Value)
{
value2 = ResolveDefaultValue(volumeSlider);
}
component.value = value2;
ApplyVolumeToAll(qm, value2);
}
internal static void ApplyVolumeToAll(QuickMenuManager qm, float value)
{
//IL_0040: Unknown result type (might be due to invalid IL or missing references)
//IL_004b: Expected O, but got Unknown
if ((Object)(object)qm == (Object)null || qm.playerListSlots == null)
{
return;
}
float num = LastMin;
float num2 = LastMax;
if (num == 0f && num2 == 0f && (Object)GlobalSlider != (Object)null)
{
num = GlobalSlider.minValue;
num2 = GlobalSlider.maxValue;
}
float value2 = (LastAppliedValue = ClampToRange(value, num, num2));
for (int i = 0; i < qm.playerListSlots.Length; i++)
{
PlayerListSlot val = qm.playerListSlots[i];
if (val != null && !((Object)(object)val.volumeSlider == (Object)null))
{
val.volumeSlider.value = value2;
}
}
}
[IteratorStateMachine(typeof(<ReapplyNextFrame>d__9))]
internal static IEnumerator ReapplyNextFrame(QuickMenuManager qm)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <ReapplyNextFrame>d__9(0)
{
qm = qm
};
}
}
[HarmonyPatch(typeof(QuickMenuManager), "Start")]
internal static class QuickMenuManager_Start_Patch
{
[HarmonyPostfix]
private static void Postfix(QuickMenuManager __instance)
{
GlobalVoiceOverlay.Reset();
GlobalVoiceOverlay.AddGlobalSlider(__instance);
}
}
[HarmonyPatch(typeof(QuickMenuManager), "AddUserToPlayerList")]
internal static class QuickMenuManager_AddUserToPlayerList_Patch
{
[HarmonyPostfix]
private static void Postfix(QuickMenuManager __instance)
{
//IL_0019: Unknown result type (might be due to invalid IL or missing references)
//IL_0024: Expected O, but got Unknown
if (Plugin.Enabled.Value && !((Object)GlobalVoiceOverlay.GlobalSlider == (Object)null))
{
((MonoBehaviour)__instance).StartCoroutine(GlobalVoiceOverlay.ReapplyNextFrame(__instance));
}
}
}