using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using BepInEx;
using BepInEx.Bootstrap;
using BepInEx.Configuration;
using BepInEx.Core.Logging.Interpolation;
using BepInEx.Logging;
using BepInEx.Unity.IL2CPP;
using HarmonyLib;
using I2.Loc;
using Il2CppInterop.Runtime;
using Il2CppInterop.Runtime.InteropTypes;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppSystem.Collections.Generic;
using Microsoft.CodeAnalysis;
using ModSettings.Core;
using TMPro;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Controls;
using UnityEngine.UI;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")]
[assembly: AssemblyCompany("ModSettings.Plugin")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("0.2.0.0")]
[assembly: AssemblyInformationalVersion("0.2.0+6baae216dc75e3d6f6ceb0a73f81536dbb0fb0e6")]
[assembly: AssemblyProduct("ModSettings.Plugin")]
[assembly: AssemblyTitle("ModSettings.Plugin")]
[assembly: AssemblyVersion("0.2.0.0")]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
[CompilerGenerated]
[Embedded]
internal sealed class EmbeddedAttribute : Attribute
{
}
}
namespace System.Runtime.CompilerServices
{
[CompilerGenerated]
[Embedded]
[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
internal sealed class RefSafetyRulesAttribute : Attribute
{
public readonly int Version;
public RefSafetyRulesAttribute(int P_0)
{
Version = P_0;
}
}
}
namespace ModSettings.Plugin
{
internal sealed class ConfigStore
{
private sealed class Live
{
public ConfigFile File { get; }
public BepInPlugin Owner { get; }
public Live(ConfigFile file, BepInPlugin owner)
{
File = file;
Owner = owner;
}
}
private readonly ManualLogSource _log;
private Dictionary<string, Live> _live = new Dictionary<string, Live>(StringComparer.OrdinalIgnoreCase);
public IReadOnlyList<ModEntry> Mods { get; private set; } = Array.Empty<ModEntry>();
public ConfigStore(ManualLogSource log)
{
_log = log;
}
public void Refresh()
{
_live = LiveConfigFiles();
List<ConfigSource> list = (from path in Directory.EnumerateFiles(Paths.ConfigPath, "*.cfg", SearchOption.AllDirectories)
where path.EndsWith(".cfg", StringComparison.OrdinalIgnoreCase)
select path).Select(Source).ToList();
Mods = ModList.Build((IEnumerable<ConfigSource>)list);
}
public string Apply(ModEntry mod, SettingView view, string input)
{
//IL_0009: 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_00ae: Unknown result type (might be due to invalid IL or missing references)
//IL_00b5: Expected O, but got Unknown
CfgSetting setting = view.Setting;
ValueCheck val = ValueRules.Check(setting, input);
if (!((ValueCheck)(ref val)).Ok)
{
return ((ValueCheck)(ref val)).Error;
}
string fullPath = Path.GetFullPath(Path.Combine(Paths.ConfigPath, mod.Source.RelativePath));
try
{
_live.TryGetValue(fullPath, out var value);
ConfigEntryBase val2 = ((value == null) ? null : Entry(value.File, setting));
if (val2 != null)
{
return ApplyToEntry(value.File, val2, ((ValueCheck)(ref val)).Raw);
}
WriteFile(fullPath, setting, ((ValueCheck)(ref val)).Raw);
if (value != null)
{
value.File.Reload();
}
return null;
}
catch (Exception ex)
{
ManualLogSource log = _log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val3 = new BepInExErrorLogInterpolatedStringHandler(22, 4, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("Could not save ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(setting.Section);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(".");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(setting.Key);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(" in ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(mod.Source.RelativePath);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(": ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<Exception>(ex);
}
log.LogError(val3);
return "Could not save: " + ex.Message;
}
finally
{
Refresh();
}
}
private ConfigSource Source(string path)
{
//IL_0044: Unknown result type (might be due to invalid IL or missing references)
//IL_004b: Expected O, but got Unknown
//IL_006e: Unknown result type (might be due to invalid IL or missing references)
//IL_0074: Expected O, but got Unknown
//IL_013f: Unknown result type (might be due to invalid IL or missing references)
//IL_0145: Expected O, but got Unknown
string fullPath = Path.GetFullPath(path);
string relativePath = Path.GetRelativePath(Paths.ConfigPath, fullPath);
bool flag = string.Equals(fullPath, Path.GetFullPath(Paths.BepInExConfigPath), StringComparison.OrdinalIgnoreCase);
string text;
try
{
text = ReadShared(fullPath);
}
catch (Exception ex)
{
return new ConfigSource(relativePath, (string)null, ex.Message, (SourceKind)((!flag) ? 1 : 2), (string)null, (string)null, (IReadOnlySet<string>)null, (IReadOnlyDictionary<string, SettingTags>)null);
}
if (_live.TryGetValue(fullPath, out var value))
{
ReloadIfChangedOnDisk(value.File, text, relativePath);
HashSet<string> hashSet = new HashSet<string>();
Dictionary<string, SettingTags> dictionary = new Dictionary<string, SettingTags>();
foreach (ConfigEntryBase value2 in value.File.Values)
{
string text2 = ConfigSource.KeyOf(value2.Definition.Section, value2.Definition.Key);
hashSet.Add(text2);
dictionary[text2] = Tags.Of(value2);
}
int num = (flag ? 2 : 0);
BepInPlugin owner = value.Owner;
string obj = ((owner != null) ? owner.Name : null);
BepInPlugin owner2 = value.Owner;
return new ConfigSource(relativePath, text, (string)null, (SourceKind)num, obj, (owner2 == null) ? null : ((object)owner2.Version)?.ToString(), (IReadOnlySet<string>)hashSet, (IReadOnlyDictionary<string, SettingTags>)dictionary);
}
return new ConfigSource(relativePath, text, (string)null, (SourceKind)((!flag) ? 1 : 2), (string)null, (string)null, (IReadOnlySet<string>)null, (IReadOnlyDictionary<string, SettingTags>)null);
}
private void ReloadIfChangedOnDisk(ConfigFile file, string text, string relative)
{
//IL_0090: Unknown result type (might be due to invalid IL or missing references)
//IL_0097: Expected O, but got Unknown
//IL_0049: Unknown result type (might be due to invalid IL or missing references)
//IL_004f: Expected O, but got Unknown
bool flag = default(bool);
try
{
foreach (CfgSetting setting in CfgDocument.Parse(text).Settings)
{
ConfigEntryBase val = Entry(file, setting);
if (val != null && !(val.GetSerializedValue() == setting.RawValue))
{
file.Reload();
ManualLogSource log = _log;
BepInExInfoLogInterpolatedStringHandler val2 = new BepInExInfoLogInterpolatedStringHandler(43, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<string>(relative);
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(" was changed outside the game; reloaded it.");
}
log.LogInfo(val2);
break;
}
}
}
catch (Exception ex)
{
ManualLogSource log2 = _log;
BepInExWarningLogInterpolatedStringHandler val3 = new BepInExWarningLogInterpolatedStringHandler(45, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("Could not compare ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(relative);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(" with its loaded settings: ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(ex.Message);
}
log2.LogWarning(val3);
}
}
private static ConfigEntryBase Entry(ConfigFile file, CfgSetting setting)
{
//IL_000c: Unknown result type (might be due to invalid IL or missing references)
//IL_0012: Expected O, but got Unknown
try
{
ConfigDefinition val = new ConfigDefinition(setting.Section, setting.Key);
return file.ContainsKey(val) ? file[val] : null;
}
catch (ArgumentException)
{
return null;
}
}
private static string ApplyToEntry(ConfigFile file, ConfigEntryBase entry, string raw)
{
object obj;
try
{
obj = TomlTypeConverter.ConvertToValue(raw, entry.SettingType);
}
catch (Exception ex)
{
return "Not a valid value: " + ex.Message;
}
entry.BoxedValue = obj;
if (!file.SaveOnConfigSet)
{
file.Save();
}
if (!object.Equals(entry.BoxedValue, obj))
{
return "The mod changed that value to " + entry.GetSerializedValue() + ".";
}
return null;
}
private static void WriteFile(string path, CfgSetting setting, string raw)
{
CfgDocument val = CfgDocument.Parse(ReadShared(path));
CfgSetting val2 = ((IEnumerable<CfgSetting>)val.Settings).FirstOrDefault((Func<CfgSetting, bool>)((CfgSetting s) => s.Section == setting.Section && s.Key == setting.Key)) ?? throw new InvalidOperationException(setting.Key + " is no longer in the file.");
string text = path + ".modsettings.tmp";
File.WriteAllText(text, val.WithValue(val2, raw), new UTF8Encoding(encoderShouldEmitUTF8Identifier: false));
File.Move(text, path, overwrite: true);
}
private static string ReadShared(string path)
{
using FileStream stream = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.ReadWrite | FileShare.Delete);
using StreamReader streamReader = new StreamReader(stream);
return streamReader.ReadToEnd();
}
private static Dictionary<string, Live> LiveConfigFiles()
{
Dictionary<string, Live> live = new Dictionary<string, Live>(StringComparer.OrdinalIgnoreCase);
foreach (PluginInfo value in ((BaseChainloader<BasePlugin>)(object)IL2CPPChainloader.Instance).Plugins.Values)
{
object instance = value.Instance;
BasePlugin val = (BasePlugin)((instance is BasePlugin) ? instance : null);
if (val != null)
{
Add(val.Config, value.Metadata);
}
}
Add(ConfigFile.CoreConfig, null);
return live;
void Add(ConfigFile file, BepInPlugin owner)
{
if (file != null && file.ConfigFilePath != null)
{
live.TryAdd(Path.GetFullPath(file.ConfigFilePath), new Live(file, owner));
}
}
}
}
internal sealed class FrameWatcher : MonoBehaviour
{
public FrameWatcher(IntPtr pointer)
: base(pointer)
{
}
private void Update()
{
Plugin.Instance?.OnFrame();
}
}
internal static class GameKeys
{
public static IReadOnlyList<KeyBinding> Read(Action<string, Exception> report)
{
List<string> list = new List<string>();
try
{
foreach (InputActionAsset item in Assets())
{
list.Add(item.ToJson());
}
}
catch (Exception arg)
{
report("reading the game's controls", arg);
}
string text = null;
try
{
text = KeyRebinder.CurrentOverridesJson();
}
catch (Exception arg2)
{
report("reading the game's rebinds", arg2);
}
return GameBindings.FromJson((IEnumerable<string>)list, text);
}
private static List<InputActionAsset> Assets()
{
List<InputActionAsset> assets = new List<InputActionAsset>();
Add(KeyRebinder.mainAsset);
Add(KeyRebinder.uiAsset);
List<InputActionAsset> runtimeAssets = KeyRebinder.RuntimeAssets;
if (runtimeAssets != null)
{
for (int i = 0; i < runtimeAssets.Count; i++)
{
Add(runtimeAssets[i]);
}
}
if (assets.Count == 0)
{
foreach (InputActionAsset item in Resources.FindObjectsOfTypeAll<InputActionAsset>())
{
Add(item);
}
}
return assets;
void Add(InputActionAsset asset)
{
if ((Object)(object)asset != (Object)null && assets.All((InputActionAsset a) => ((Il2CppObjectBase)a).Pointer != ((Il2CppObjectBase)asset).Pointer))
{
assets.Add(asset);
}
}
}
}
[HarmonyPatch]
internal static class Hooks
{
[HarmonyPostfix]
[HarmonyPatch(typeof(MainMenuUI), "Start")]
private static void AfterMainMenuStart(MainMenuUI __instance)
{
AddButton((Component)(object)__instance, "main menu");
}
[HarmonyPostfix]
[HarmonyPatch(typeof(EscapeMenuUI), "Start")]
private static void AfterEscapeMenuStart(EscapeMenuUI __instance)
{
PauseMenu.Remember(__instance);
AddButton((Component)(object)__instance, "pause menu");
}
[HarmonyPostfix]
[HarmonyPatch(typeof(EscapeMenuUI), "Show")]
private static void AfterEscapeMenuShow(EscapeMenuUI __instance)
{
AddButton((Component)(object)__instance, "pause menu");
}
[HarmonyPrefix]
[HarmonyPatch(typeof(UIManager), "CloseTopWindow")]
private static bool BeforeCloseTopWindow()
{
return !ClosePanel();
}
private static void AddButton(Component menu, string where)
{
try
{
Plugin instance = Plugin.Instance;
MenuButtons.Add(menu, where, ((BasePlugin)instance).Log, instance.HotkeyName, instance.Panel.Open);
}
catch (Exception e)
{
Plugin.Instance.ReportOnce("Mods button on the " + where, e);
}
}
private static bool ClosePanel()
{
try
{
return Plugin.Instance.Panel.HandleEscapeFromGame();
}
catch (Exception e)
{
Plugin.Instance.ReportOnce("closing the mod settings", e);
return false;
}
}
}
internal static class MenuButtons
{
private const string CloneName = "ModSettings Mods Button";
public static void Add(Component menu, string where, ManualLogSource log, string hotkeyName, Action onClick)
{
//IL_00f3: Unknown result type (might be due to invalid IL or missing references)
//IL_00fa: Expected O, but got Unknown
//IL_0210: Unknown result type (might be due to invalid IL or missing references)
//IL_021a: Expected O, but got Unknown
if ((Object)(object)menu == (Object)null)
{
return;
}
Button[] source = ((IEnumerable<Button>)menu.GetComponentsInChildren<Button>(true)).ToArray();
if (source.Any((Button b) => ((Object)b).name == "ModSettings Mods Button"))
{
return;
}
List<Button> list = (from b in source
where (Object)(object)((Component)b).transform.parent != (Object)null && ((Component)b).gameObject.activeSelf
group b by ((Il2CppObjectBase)((Component)b).transform.parent).Pointer into g
orderby g.Count() descending
select g).FirstOrDefault()?.OrderBy((Button b) => ((Component)b).transform.GetSiblingIndex()).ToList();
if (list == null || list.Count == 0)
{
bool flag = default(bool);
BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(58, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("No buttons found on the ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(where);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("; press ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(hotkeyName);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" to open the mod settings.");
}
log.LogWarning(val);
return;
}
Button val2 = list[list.Count - 1];
Button obj;
if (list.Count < 2)
{
obj = val2;
}
else
{
obj = list[list.Count - 2];
}
Button val3 = obj;
Transform parent = ((Component)val2).transform.parent;
float heightBefore = ColumnHeight(parent);
GameObject val4 = Object.Instantiate<GameObject>(((Component)val3).gameObject, parent);
((Object)val4).name = "ModSettings Mods Button";
val4.transform.SetSiblingIndex(((Component)val2).transform.GetSiblingIndex());
foreach (Localize componentsInChild in val4.GetComponentsInChildren<Localize>(true))
{
((Behaviour)componentsInChild).enabled = false;
}
TMP_Text componentInChildren = val4.GetComponentInChildren<TMP_Text>(true);
if ((Object)(object)componentInChildren != (Object)null)
{
componentInChildren.text = "Mods";
Ui.UseFont(componentInChildren);
}
Button component = val4.GetComponent<Button>();
component.onClick = new ButtonClickedEvent();
Ui.OnClick(component, onClick);
bool flag2 = (Object)(object)((Component)parent).GetComponent<LayoutGroup>() != (Object)null;
log.LogInfo((object)($"Added a Mods button to the {where}, copied from '{((Object)val3).name}' under '{PathOf(parent)}'" + (flag2 ? "." : "; that column has no layout group, so the button may overlap another.")));
KeepHeight(parent, heightBefore, where, log);
}
private static void KeepHeight(Transform parent, float heightBefore, string where, ManualLogSource log)
{
//IL_0155: Unknown result type (might be due to invalid IL or missing references)
//IL_015c: Expected O, but got Unknown
//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_010d: Unknown result type (might be due to invalid IL or missing references)
//IL_0119: Unknown result type (might be due to invalid IL or missing references)
//IL_0126: Unknown result type (might be due to invalid IL or missing references)
VerticalLayoutGroup component = ((Component)parent).GetComponent<VerticalLayoutGroup>();
RectTransform val = ((Il2CppObjectBase)parent).TryCast<RectTransform>();
if ((Object)(object)component == (Object)null || (Object)(object)val == (Object)null || heightBefore <= 0f)
{
return;
}
LayoutRebuilder.ForceRebuildLayoutImmediate(val);
float num = ColumnHeight(parent) - heightBefore;
if (num <= 0.5f)
{
return;
}
List<RectTransform> list = ActiveChildren(parent);
int num2 = Math.Max(1, list.Count - 1);
float spacing = ((HorizontalOrVerticalLayoutGroup)component).spacing;
float num3 = (((HorizontalOrVerticalLayoutGroup)component).spacing = Math.Max(0f, spacing - num / (float)num2));
float num5 = num - (spacing - num3) * (float)num2;
float num6 = ((num5 > 0.5f) ? (num5 / (float)list.Count) : 0f);
if (num6 > 0f)
{
foreach (RectTransform item in list)
{
Rect rect = item.rect;
float num7 = ((Rect)(ref rect)).height - num6;
if (((HorizontalOrVerticalLayoutGroup)component).childControlHeight)
{
LayoutElement obj = ((Component)item).GetComponent<LayoutElement>() ?? ((Component)item).gameObject.AddComponent<LayoutElement>();
obj.minHeight = num7;
obj.preferredHeight = num7;
}
else
{
item.sizeDelta = new Vector2(item.sizeDelta.x, item.sizeDelta.y - num6);
}
}
}
LayoutRebuilder.ForceRebuildLayoutImmediate(val);
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val2 = new BepInExInfoLogInterpolatedStringHandler(74, 6, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Kept the ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<string>(where);
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(" column ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<float>(heightBefore, "0");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(" tall: spacing ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<float>(spacing, "0.#");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(" -> ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<float>(num3, "0.#");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(", ");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("buttons ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<float>(num6, "0.#");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(" shorter (it had grown by ");
((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<float>(num, "0.#");
((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(").");
}
log.LogInfo(val2);
}
private static float ColumnHeight(Transform parent)
{
//IL_004f: Unknown result type (might be due to invalid IL or missing references)
//IL_0054: Unknown result type (might be due to invalid IL or missing references)
RectTransform val = ((Il2CppObjectBase)parent).TryCast<RectTransform>();
if ((Object)(object)val != (Object)null)
{
LayoutRebuilder.ForceRebuildLayoutImmediate(val);
}
float num = float.MinValue;
float num2 = float.MaxValue;
Il2CppStructArray<Vector3> val2 = new Il2CppStructArray<Vector3>(4L);
foreach (RectTransform item in ActiveChildren(parent))
{
item.GetWorldCorners(val2);
for (int i = 0; i < 4; i++)
{
float y = parent.InverseTransformPoint(((Il2CppArrayBase<Vector3>)(object)val2)[i]).y;
num = Math.Max(num, y);
num2 = Math.Min(num2, y);
}
}
if (!(num > num2))
{
return 0f;
}
return num - num2;
}
private static List<RectTransform> ActiveChildren(Transform parent)
{
List<RectTransform> list = new List<RectTransform>();
for (int i = 0; i < parent.childCount; i++)
{
RectTransform val = ((Il2CppObjectBase)parent.GetChild(i)).TryCast<RectTransform>();
if ((Object)(object)val != (Object)null && ((Component)val).gameObject.activeSelf)
{
list.Add(val);
}
}
return list;
}
private static string PathOf(Transform transform)
{
List<string> list = new List<string>();
Transform val = transform;
while ((Object)(object)val != (Object)null)
{
list.Add(((Object)val).name);
val = val.parent;
}
list.Reverse();
return string.Join("/", list);
}
}
internal static class PauseMenu
{
private static EscapeMenuUI _menu;
public static void Remember(EscapeMenuUI menu)
{
_menu = menu;
}
public static bool Open()
{
EscapeMenuUI menu = _menu;
if ((Object)(object)menu == (Object)null || ((UIWindow)menu).IsOpen)
{
return false;
}
UIManager instance = UIManager.Instance;
if ((Object)(object)instance != (Object)null && instance.IsAnyWindowOpen())
{
return false;
}
((UIWindow)menu).TryOpen();
return true;
}
public static void Close()
{
EscapeMenuUI menu = _menu;
if ((Object)(object)menu != (Object)null && ((UIWindow)menu).IsOpen)
{
((UIWindow)menu).TryClose();
}
}
}
[BepInPlugin("com.github.kirby1997.modsettings", "ModSettings", "0.2.0")]
public sealed class Plugin : BasePlugin
{
public const string Id = "com.github.kirby1997.modsettings";
public const string Name = "ModSettings";
public const string Version = "0.2.0";
private readonly HashSet<string> _reported = new HashSet<string>();
private ConfigEntry<Key> _hotkey;
private List<(Key Key, KeyControl Control)> _keyControls;
private IntPtr _keyboardPointer;
private bool _pausedForPanel;
internal static Plugin Instance { get; private set; }
internal SettingsPanel Panel { get; private set; }
internal string HotkeyName => ((object)_hotkey.Value/*cast due to .constrained prefix*/).ToString();
public override void Load()
{
//IL_005c: Unknown result type (might be due to invalid IL or missing references)
//IL_007a: Unknown result type (might be due to invalid IL or missing references)
//IL_0080: Expected O, but got Unknown
Instance = this;
_hotkey = ((BasePlugin)this).Config.Bind<Key>("General", "Hotkey", (Key)103, "Key that opens and closes the mod settings anywhere in the game. None turns it off.");
Panel = new SettingsPanel(((BasePlugin)this).Log, new ConfigStore(((BasePlugin)this).Log), () => GameKeys.Read(ReportOnce));
((BasePlugin)this).AddComponent<FrameWatcher>();
new Harmony("com.github.kirby1997.modsettings").PatchAll(typeof(Hooks));
ManualLogSource log = ((BasePlugin)this).Log;
bool flag = default(bool);
BepInExInfoLogInterpolatedStringHandler val = new BepInExInfoLogInterpolatedStringHandler(8, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("ModSettings");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>("0.2.0");
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" loaded");
}
log.LogInfo(val);
}
internal void OnFrame()
{
//IL_004e: Unknown result type (might be due to invalid IL or missing references)
//IL_005c: Unknown result type (might be due to invalid IL or missing references)
try
{
Keyboard current = Keyboard.current;
bool escapePressed = current != null && ((ButtonControl)current.escapeKey).wasPressedThisFrame;
if (!Panel.IsOpen)
{
_pausedForPanel = false;
}
if (current != null && Panel.IsCapturing)
{
Capture(current);
}
else if (current != null && (int)_hotkey.Value != 0 && ((ButtonControl)current[_hotkey.Value]).wasPressedThisFrame)
{
ToggleFromHotkey();
}
Panel.Tick(escapePressed);
}
catch (Exception e)
{
ReportOnce("frame update", e);
}
}
private void ToggleFromHotkey()
{
if (Panel.IsOpen)
{
Panel.Close();
if (_pausedForPanel)
{
PauseMenu.Close();
}
_pausedForPanel = false;
}
else
{
_pausedForPanel = PauseMenu.Open();
Panel.Open();
}
}
private unsafe void Capture(Keyboard keyboard)
{
//IL_001a: Unknown result type (might be due to invalid IL or missing references)
//IL_001f: Unknown result type (might be due to invalid IL or missing references)
foreach (var item in KeyControls(keyboard))
{
var (val, _) = item;
if (!((ButtonControl)item.Control).wasPressedThisFrame)
{
continue;
}
string text = ((object)(*(Key*)(&val))/*cast due to .constrained prefix*/).ToString();
if (!Panel.CapturingShortcut || !KeyNames.IsModifier(text))
{
List<string> heldModifiers = (from k in KeyControls(keyboard)
where KeyNames.IsModifier(((object)(*(Key*)(&k.Key))/*cast due to .constrained prefix*/).ToString()) && ((ButtonControl)k.Control).isPressed
select ((object)(*(Key*)(&k.Key))/*cast due to .constrained prefix*/).ToString()).ToList();
Panel.FinishCapture(text, heldModifiers);
break;
}
}
}
private List<(Key Key, KeyControl Control)> KeyControls(Keyboard keyboard)
{
//IL_004c: Unknown result type (might be due to invalid IL or missing references)
//IL_0051: 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_0055: Unknown result type (might be due to invalid IL or missing references)
//IL_0058: Invalid comparison between Unknown and I4
//IL_005c: 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)
if (_keyControls != null && _keyboardPointer == ((Il2CppObjectBase)keyboard).Pointer)
{
return _keyControls;
}
_keyboardPointer = ((Il2CppObjectBase)keyboard).Pointer;
_keyControls = new List<(Key, KeyControl)>();
foreach (Key item in Enum.GetValues<Key>().Distinct())
{
if ((int)item == 0 || (int)item == 60)
{
continue;
}
try
{
KeyControl val = keyboard[item];
if (val != null)
{
_keyControls.Add((item, val));
}
}
catch (ArgumentException)
{
}
}
return _keyControls;
}
internal void ReportOnce(string what, Exception e)
{
//IL_0019: Unknown result type (might be due to invalid IL or missing references)
//IL_001f: Expected O, but got Unknown
if (_reported.Add(what))
{
ManualLogSource log = ((BasePlugin)this).Log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(9, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(what);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" failed: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<Exception>(e);
}
log.LogError(val);
}
}
}
internal sealed class SettingsPanel
{
private const float SliderDelay = 0.4f;
private const string Note = "Changes save straight away. Some mods only read their settings when the game starts.";
private readonly ManualLogSource _log;
private readonly ConfigStore _store;
private readonly Func<IReadOnlyList<KeyBinding>> _gameKeys;
private GameObject _root;
private RectTransform _modList;
private RectTransform _settings;
private ScrollRect _settingsScroll;
private TextMeshProUGUI _status;
private Image _statusBar;
private string _selectedPath;
private CursorLockMode _cursorLock;
private bool _cursorVisible;
private int _escapeFrame = -1;
private int _escapeHandledFrame = -1;
private IReadOnlyList<KeyBinding> _gameBindings = Array.Empty<KeyBinding>();
private IReadOnlyDictionary<string, IReadOnlyList<string>> _clashes = new Dictionary<string, IReadOnlyList<string>>();
private (ModEntry Mod, SettingView View, TextMeshProUGUI Label)? _capture;
private (ModEntry Mod, SettingView View, string Text)? _pendingSlider;
private float _pendingSince;
public bool IsOpen
{
get
{
if ((Object)(object)_root != (Object)null)
{
return _root.activeSelf;
}
return false;
}
}
public bool IsCapturing
{
get
{
if (IsOpen)
{
return _capture.HasValue;
}
return false;
}
}
public bool CapturingShortcut
{
get
{
if (IsCapturing)
{
return _capture.Value.View.Setting.TypeName == "KeyboardShortcut";
}
return false;
}
}
public SettingsPanel(ManualLogSource log, ConfigStore store, Func<IReadOnlyList<KeyBinding>> gameKeys)
{
_log = log;
_store = store;
_gameKeys = gameKeys;
}
public void Toggle()
{
if (IsOpen)
{
Close();
}
else
{
Open();
}
}
public void Open()
{
//IL_007e: Unknown result type (might be due to invalid IL or missing references)
//IL_0084: Expected O, but got Unknown
//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)
try
{
if ((Object)(object)_root == (Object)null)
{
Build();
}
_store.Refresh();
_gameBindings = _gameKeys();
_capture = null;
_cursorLock = Cursor.lockState;
_cursorVisible = Cursor.visible;
_root.SetActive(true);
ShowStatus("Changes save straight away. Some mods only read their settings when the game starts.", error: false);
ShowMods();
}
catch (Exception ex)
{
ManualLogSource log = _log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(33, 1, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Could not open the mod settings: ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<Exception>(ex);
}
log.LogError(val);
}
}
public void Close()
{
//IL_0028: Unknown result type (might be due to invalid IL or missing references)
if (IsOpen)
{
FlushSlider();
_capture = null;
_root.SetActive(false);
Cursor.lockState = _cursorLock;
Cursor.visible = _cursorVisible;
}
}
public void Tick(bool escapePressed)
{
if (!IsOpen)
{
return;
}
Cursor.lockState = (CursorLockMode)0;
Cursor.visible = true;
if (_pendingSlider.HasValue && Time.unscaledTime - _pendingSince >= 0.4f)
{
FlushSlider();
}
int frameCount = Time.frameCount;
if (escapePressed && _escapeHandledFrame != frameCount)
{
if (IsCapturing)
{
_escapeHandledFrame = frameCount;
CancelCapture();
}
else
{
_escapeFrame = frameCount;
}
}
else if (_escapeFrame == frameCount - 1 && _escapeHandledFrame != _escapeFrame)
{
Close();
}
}
public bool HandleEscapeFromGame()
{
if (!IsOpen)
{
return false;
}
int frameCount = Time.frameCount;
if (_escapeHandledFrame == frameCount)
{
return true;
}
_escapeHandledFrame = frameCount;
if (IsCapturing)
{
CancelCapture();
}
else
{
Close();
}
return true;
}
public void FinishCapture(string key, IReadOnlyList<string> heldModifiers)
{
//IL_0034: Unknown result type (might be due to invalid IL or missing references)
//IL_0039: Unknown result type (might be due to invalid IL or missing references)
(ModEntry, SettingView, TextMeshProUGUI)? capture = _capture;
if (capture.HasValue)
{
(ModEntry, SettingView, TextMeshProUGUI) valueOrDefault = capture.GetValueOrDefault();
_capture = null;
ValueCheck val = KeyNames.Capture(valueOrDefault.Item2.Setting, key, heldModifiers);
if (!((ValueCheck)(ref val)).Ok)
{
((TMP_Text)valueOrDefault.Item3).text = KeyText(valueOrDefault.Item2);
ShowStatus(valueOrDefault.Item2.Label + " not saved: " + ((ValueCheck)(ref val)).Error, error: true);
}
else
{
Apply(valueOrDefault.Item1, valueOrDefault.Item2, ((ValueCheck)(ref val)).Raw, rebuild: true);
}
}
}
private void StartCapture(ModEntry mod, SettingView view, TextMeshProUGUI label)
{
CancelCapture();
_capture = (mod, view, label);
((TMP_Text)label).text = "Press a key...";
string value = ((view.Setting.TypeName == "KeyboardShortcut") ? " Hold Ctrl, Shift or Alt with it for a combination." : "");
ShowStatus($"Press the key to use for {view.Label}.{value} Esc cancels.", error: false);
}
private void CancelCapture()
{
(ModEntry, SettingView, TextMeshProUGUI)? capture = _capture;
if (capture.HasValue)
{
(ModEntry, SettingView, TextMeshProUGUI) valueOrDefault = capture.GetValueOrDefault();
_capture = null;
((TMP_Text)valueOrDefault.Item3).text = KeyText(valueOrDefault.Item2);
ShowStatus("Changes save straight away. Some mods only read their settings when the game starts.", error: false);
}
}
private static string KeyText(SettingView view)
{
if (KeyNames.Parse(view.Setting.TypeName, view.Setting.RawValue) != null)
{
return ValueRules.Display(view.Setting);
}
return "(none)";
}
private void Build()
{
//IL_0006: Unknown result type (might be due to invalid IL or missing references)
//IL_000b: Unknown result type (might be due to invalid IL or missing references)
//IL_0017: Expected O, but got Unknown
//IL_005b: Unknown result type (might be due to invalid IL or missing references)
//IL_00b1: Unknown result type (might be due to invalid IL or missing references)
//IL_00db: Unknown result type (might be due to invalid IL or missing references)
//IL_00e1: Unknown result type (might be due to invalid IL or missing references)
//IL_00f2: Unknown result type (might be due to invalid IL or missing references)
//IL_00fd: Unknown result type (might be due to invalid IL or missing references)
//IL_015b: Unknown result type (might be due to invalid IL or missing references)
//IL_0271: Unknown result type (might be due to invalid IL or missing references)
_root = new GameObject("ModSettings Settings")
{
layer = 5
};
Object.DontDestroyOnLoad((Object)(object)_root);
Canvas obj = _root.AddComponent<Canvas>();
obj.renderMode = (RenderMode)0;
obj.sortingOrder = 32000;
CanvasScaler obj2 = _root.AddComponent<CanvasScaler>();
obj2.uiScaleMode = (ScaleMode)1;
obj2.referenceResolution = new Vector2(1920f, 1080f);
obj2.matchWidthOrHeight = 0.5f;
_root.AddComponent<GraphicRaycaster>();
RectTransform component = _root.GetComponent<RectTransform>();
RectTransform obj3 = Ui.Rect("Blocker", (Transform)(object)component);
Ui.Stretch(obj3);
Ui.NewImage((Component)(object)obj3, new Color(0f, 0f, 0f, 0.65f));
RectTransform val = Ui.Rect("Window", (Transform)(object)component);
Vector2 val2 = default(Vector2);
((Vector2)(ref val2))..ctor(0.5f, 0.5f);
val.anchorMax = val2;
val.anchorMin = val2;
val.sizeDelta = new Vector2(1500f, 900f);
Ui.NewImage((Component)(object)val, Ui.PanelColor);
Ui.Place(((TMP_Text)Ui.NewText((Transform)(object)val, "Mod settings", 44f, (TextAlignmentOptions)4097)).rectTransform, 0f, 1f, 0.6f, 1f, 32f, -84f, 0f, 20f);
Ui.Place(((Component)Ui.NewButton((Transform)(object)val, "Close", 30f, Ui.ButtonColor, Close)).GetComponent<RectTransform>(), 1f, 1f, 1f, 1f, -196f, -80f, 28f, 24f);
Ui.Place(((Component)Ui.NewScroll((Transform)(object)val, 6f, out _modList)).GetComponent<RectTransform>(), 0f, 0f, 0f, 1f, 24f, 104f, -444f, 100f);
_settingsScroll = Ui.NewScroll((Transform)(object)val, 4f, out _settings);
Ui.Place(((Component)_settingsScroll).GetComponent<RectTransform>(), 0f, 0f, 1f, 1f, 468f, 104f, 24f, 100f);
RectTransform val3 = Ui.Rect("Status", (Transform)(object)val);
Ui.Place(val3, 0f, 0f, 1f, 0f, 24f, 24f, 24f, -84f);
_statusBar = Ui.NewImage((Component)(object)val3, Ui.FieldColor);
_status = Ui.NewText((Transform)(object)val3, "", 24f, (TextAlignmentOptions)4097);
Ui.Stretch(((TMP_Text)_status).rectTransform, 12f);
_root.SetActive(false);
}
private void ShowMods()
{
//IL_0171: Unknown result type (might be due to invalid IL or missing references)
//IL_016a: Unknown result type (might be due to invalid IL or missing references)
IReadOnlyList<ModEntry> mods = _store.Mods;
_clashes = KeyClashes.Find(KeyClashes.FromMods((IEnumerable<ModEntry>)mods).Concat(_gameBindings));
ModEntry val = ((IEnumerable<ModEntry>)mods).FirstOrDefault((Func<ModEntry, bool>)((ModEntry m) => m.Source.RelativePath == _selectedPath)) ?? mods.FirstOrDefault();
_selectedPath = ((val != null) ? val.Source.RelativePath : null);
Ui.Clear((Transform)(object)_modList);
foreach (ModEntry mod in mods)
{
string value = ((mod.Version.Length > 0) ? ("v" + mod.Version + " · ") : "");
bool flag = mod == val;
string value2 = (_clashes.Keys.Any((string id) => id.StartsWith(mod.Source.RelativePath + "\n", StringComparison.Ordinal)) ? " · key clash" : "");
Ui.Height((Component)(object)Ui.NewButton((Transform)(object)_modList, $"{mod.Title}\n<size=70%>{value}{mod.Status}{value2}</size>", 28f, flag ? Ui.SelectedColor : Ui.ButtonColor, delegate
{
Select(mod);
}), 76f);
}
ShowSettings(val);
}
private void Select(ModEntry mod)
{
//IL_003b: Unknown result type (might be due to invalid IL or missing references)
//IL_0041: Expected O, but got Unknown
try
{
FlushSlider();
_selectedPath = mod.Source.RelativePath;
ShowMods();
_settingsScroll.verticalNormalizedPosition = 1f;
}
catch (Exception ex)
{
ManualLogSource log = _log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(17, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Could not show ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(mod.Title);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<Exception>(ex);
}
log.LogError(val);
}
}
private void ShowSettings(ModEntry mod)
{
Ui.Clear((Transform)(object)_settings);
if (mod == (ModEntry)null)
{
AddLine("No config files found in BepInEx\\config.", 28f);
return;
}
AddLine(mod.Source.RelativePath, 22f);
if (mod.Error != null)
{
AddLine("Could not read this file: " + mod.Error, 28f);
return;
}
if (mod.Sections.Count == 0)
{
AddLine("No settings.", 28f);
}
foreach (SectionView section in mod.Sections)
{
((TMP_Text)AddLine((section.Name.Length > 0) ? section.Name : "(no section)", 34f)).fontStyle = (FontStyles)1;
foreach (SettingView setting in section.Settings)
{
AddSetting(mod, setting);
}
}
}
private TextMeshProUGUI AddLine(string text, float size)
{
//IL_0029: Unknown result type (might be due to invalid IL or missing references)
//IL_002e: Unknown result type (might be due to invalid IL or missing references)
//IL_003a: Expected O, but got Unknown
RectTransform obj = Ui.Rect("Line", (Transform)(object)_settings);
VerticalLayoutGroup obj2 = ((Component)obj).gameObject.AddComponent<VerticalLayoutGroup>();
((HorizontalOrVerticalLayoutGroup)obj2).childControlHeight = true;
((HorizontalOrVerticalLayoutGroup)obj2).childControlWidth = true;
((LayoutGroup)obj2).padding = new RectOffset
{
top = 6
};
return Ui.NewText((Transform)(object)obj, text, size, (TextAlignmentOptions)4097);
}
private void AddWarning(string text)
{
//IL_0011: Unknown result type (might be due to invalid IL or missing references)
//IL_0035: Unknown result type (might be due to invalid IL or missing references)
//IL_003a: 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_004a: Unknown result type (might be due to invalid IL or missing references)
//IL_0051: Unknown result type (might be due to invalid IL or missing references)
//IL_005d: Expected O, but got Unknown
RectTransform obj = Ui.Rect("Warning", (Transform)(object)_settings);
Ui.NewImage((Component)(object)obj, Ui.ErrorColor);
VerticalLayoutGroup obj2 = ((Component)obj).gameObject.AddComponent<VerticalLayoutGroup>();
((HorizontalOrVerticalLayoutGroup)obj2).childControlHeight = true;
((HorizontalOrVerticalLayoutGroup)obj2).childControlWidth = true;
((LayoutGroup)obj2).padding = new RectOffset
{
left = 10,
right = 10,
top = 4,
bottom = 4
};
Ui.NewText((Transform)(object)obj, text, 22f, (TextAlignmentOptions)4097);
}
private void AddSetting(ModEntry mod, SettingView view)
{
//IL_00e0: Unknown result type (might be due to invalid IL or missing references)
//IL_00e7: Expected O, but got Unknown
bool flag = !view.AppliesLive;
RectTransform val = Ui.Rect(view.Label, (Transform)(object)_settings);
Ui.Height((Component)(object)val, flag ? 76f : 60f);
Ui.Place(((TMP_Text)Ui.NewText((Transform)(object)val, view.Label + (flag ? "\n<size=70%>applies next launch</size>" : ""), 28f, (TextAlignmentOptions)4097, rich: true)).rectTransform, 0f, 0f, 0.42f, 1f);
RectTransform val2 = Ui.Rect("Control", (Transform)(object)val);
Ui.Place(val2, 0.44f, 0f, 1f, 1f, 0f, 4f, 0f, 4f);
try
{
AddControl(mod, view, val2);
}
catch (Exception ex)
{
ManualLogSource log = _log;
bool flag2 = default(bool);
BepInExErrorLogInterpolatedStringHandler val3 = new BepInExErrorLogInterpolatedStringHandler(17, 2, ref flag2);
if (flag2)
{
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("Could not draw ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(view.Setting.Key);
((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(": ");
((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<Exception>(ex);
}
log.LogError(val3);
Ui.Stretch(((TMP_Text)Ui.NewText((Transform)(object)val2, ValueRules.Display(view.Setting), 28f, (TextAlignmentOptions)4097)).rectTransform);
}
if (_clashes.TryGetValue(KeyClashes.IdOf(mod, view), out var value))
{
AddWarning("Also bound to: " + string.Join(", ", value));
}
string text = ValueRules.Details(view.Setting);
if (text.Length > 0)
{
AddLine(text, 22f);
}
}
private void AddControl(ModEntry mod, SettingView view, RectTransform area)
{
//IL_0081: Unknown result type (might be due to invalid IL or missing references)
//IL_0086: Unknown result type (might be due to invalid IL or missing references)
//IL_0087: Unknown result type (might be due to invalid IL or missing references)
//IL_00a1: Expected I4, but got Unknown
//IL_022c: Unknown result type (might be due to invalid IL or missing references)
//IL_02c8: Unknown result type (might be due to invalid IL or missing references)
//IL_0335: Unknown result type (might be due to invalid IL or missing references)
//IL_033a: 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_0131: Unknown result type (might be due to invalid IL or missing references)
//IL_01d7: Unknown result type (might be due to invalid IL or missing references)
//IL_01d0: Unknown result type (might be due to invalid IL or missing references)
CfgSetting setting = view.Setting;
string shown = ValueRules.Display(setting);
if (view.ReadOnly)
{
Ui.Stretch(((TMP_Text)Ui.NewText((Transform)(object)area, shown + " (read-only)", 28f, (TextAlignmentOptions)4097)).rectTransform);
return;
}
ControlKind control = view.Control;
switch ((int)control)
{
case 4:
{
TextMeshProUGUI keyLabel = null;
Button val = Ui.NewButton((Transform)(object)area, KeyText(view), 28f, Ui.ButtonColor, delegate
{
StartCapture(mod, view, keyLabel);
});
keyLabel = ((Component)val).GetComponentInChildren<TextMeshProUGUI>();
Ui.Place(((Component)val).GetComponent<RectTransform>(), 0f, 0f, 0.7f, 1f);
Ui.Place(((Component)Ui.NewButton((Transform)(object)area, "Clear", 26f, Ui.OffColor, delegate
{
Apply(mod, view, "None", rebuild: true);
})).GetComponent<RectTransform>(), 0.72f, 0f, 1f, 1f);
return;
}
case 0:
{
bool on = string.Equals(shown, "true", StringComparison.OrdinalIgnoreCase);
Ui.Place(((Component)Ui.NewButton((Transform)(object)area, on ? "On" : "Off", 28f, on ? Ui.ButtonColor : Ui.OffColor, delegate
{
Apply(mod, view, on ? "false" : "true", rebuild: true);
})).GetComponent<RectTransform>(), 0f, 0f, 0.3f, 1f);
return;
}
case 1:
Ui.Place(((Component)Ui.NewButton((Transform)(object)area, "<", 30f, Ui.ButtonColor, delegate
{
Apply(mod, view, ValueRules.Cycle(setting, -1), rebuild: true);
})).GetComponent<RectTransform>(), 0f, 0f, 0.12f, 1f);
Ui.Place(((TMP_Text)Ui.NewText((Transform)(object)area, shown, 28f, (TextAlignmentOptions)514)).rectTransform, 0.13f, 0f, 0.87f, 1f);
Ui.Place(((Component)Ui.NewButton((Transform)(object)area, ">", 30f, Ui.ButtonColor, delegate
{
Apply(mod, view, ValueRules.Cycle(setting, 1), rebuild: true);
})).GetComponent<RectTransform>(), 0.88f, 0f, 1f, 1f);
return;
case 2:
{
NumberRange value = setting.Range.Value;
double num = ValueRules.ParseNumber(setting) ?? ((NumberRange)(ref value)).Min;
TextMeshProUGUI valueText = Ui.NewText((Transform)(object)area, shown, 28f, (TextAlignmentOptions)4100);
Ui.Place(((TMP_Text)valueText).rectTransform, 0.76f, 0f, 1f, 1f);
Ui.Place(((Component)Ui.NewSlider((Transform)(object)area, (float)((NumberRange)(ref value)).Min, (float)((NumberRange)(ref value)).Max, ValueRules.IsInteger(setting.TypeName), (float)num, delegate(float position)
{
string text = ValueRules.SliderText(setting, (double)position);
((TMP_Text)valueText).text = text;
_pendingSlider = (mod, view, text);
_pendingSince = Time.unscaledTime;
})).GetComponent<RectTransform>(), 0f, 0f, 0.74f, 1f);
return;
}
}
Ui.Stretch(((Component)Ui.NewInput((Transform)(object)area, shown, 26f, delegate(string text)
{
if (text != shown)
{
Apply(mod, view, text, rebuild: true);
}
})).GetComponent<RectTransform>());
}
private void FlushSlider()
{
(ModEntry, SettingView, string)? pendingSlider = _pendingSlider;
if (pendingSlider.HasValue)
{
(ModEntry, SettingView, string) valueOrDefault = pendingSlider.GetValueOrDefault();
_pendingSlider = null;
Apply(valueOrDefault.Item1, valueOrDefault.Item2, valueOrDefault.Item3, rebuild: false);
}
}
private void Apply(ModEntry mod, SettingView view, string text, bool rebuild)
{
//IL_00b6: Unknown result type (might be due to invalid IL or missing references)
//IL_00bd: Expected O, but got Unknown
try
{
string text2 = _store.Apply(mod, view, text);
if (text2 == null)
{
ShowStatus($"Saved {view.Label} = {text}.", error: false);
}
else
{
ShowStatus(view.Label + " not saved: " + text2, error: true);
}
if (rebuild || text2 != null)
{
float verticalNormalizedPosition = _settingsScroll.verticalNormalizedPosition;
ShowMods();
Canvas.ForceUpdateCanvases();
_settingsScroll.verticalNormalizedPosition = verticalNormalizedPosition;
}
}
catch (Exception ex)
{
ManualLogSource log = _log;
bool flag = default(bool);
BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(18, 2, ref flag);
if (flag)
{
((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Could not apply ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(view.Setting.Key);
((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": ");
((BepInExLogInterpolatedStringHandler)val).AppendFormatted<Exception>(ex);
}
log.LogError(val);
}
}
private void ShowStatus(string text, bool error)
{
//IL_001c: Unknown result type (might be due to invalid IL or missing references)
//IL_0015: Unknown result type (might be due to invalid IL or missing references)
((TMP_Text)_status).text = text;
((Graphic)_statusBar).color = (error ? Ui.ErrorColor : Ui.FieldColor);
}
}
internal static class Tags
{
public static SettingTags Of(ConfigEntryBase entry)
{
//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
//IL_00b4: Expected O, but got Unknown
ConfigDescription description = entry.Description;
object[] array = ((description != null) ? description.Tags : null);
if (array == null)
{
return SettingTags.None;
}
object[] array2 = array;
foreach (object obj in array2)
{
if (obj != null && !(obj.GetType().Name != "ConfigurationManagerAttributes"))
{
object obj2 = Member(obj, "Browsable");
bool num = obj2 is bool && !(bool)obj2;
obj2 = Member(obj, "ReadOnly");
return new SettingTags(num, obj2 is bool && (bool)obj2, Member(obj, "Order") as int?, Member(obj, "DispName") as string);
}
}
return SettingTags.None;
}
private static object Member(object target, string name)
{
Type type = target.GetType();
object obj = type.GetField(name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(target);
if (obj == null)
{
PropertyInfo? property = type.GetProperty(name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
if ((object)property == null)
{
return null;
}
obj = property.GetValue(target);
}
return obj;
}
}
internal static class Ui
{
public static readonly Color PanelColor = new Color(0.04f, 0.17f, 0.32f, 1f);
public static readonly Color ButtonColor = new Color(0.02f, 0.55f, 0.72f, 1f);
public static readonly Color SelectedColor = new Color(0.96f, 0.78f, 0.08f, 1f);
public static readonly Color FieldColor = new Color(0.01f, 0.09f, 0.18f, 1f);
public static readonly Color OffColor = new Color(0.2f, 0.27f, 0.35f, 1f);
public static readonly Color ErrorColor = new Color(0.62f, 0.12f, 0.12f, 1f);
private const int UiLayer = 5;
private static TMP_FontAsset _font;
private static Material _fontMaterial;
public static void UseFont(TMP_Text template)
{
if (!((Object)(object)((template != null) ? template.font : null) == (Object)null))
{
_font = template.font;
_fontMaterial = template.fontSharedMaterial;
}
}
public static RectTransform Rect(string name, Transform parent)
{
//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)
RectTransform obj = new GameObject(name)
{
layer = 5
}.AddComponent<RectTransform>();
((Transform)obj).SetParent(parent, false);
return obj;
}
public static void Place(RectTransform rect, float xMin, float yMin, float xMax, float yMax, float left = 0f, float bottom = 0f, float right = 0f, float top = 0f)
{
//IL_0003: Unknown result type (might be due to invalid IL or missing references)
//IL_0011: Unknown result type (might be due to invalid IL or missing references)
//IL_0020: 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)
rect.anchorMin = new Vector2(xMin, yMin);
rect.anchorMax = new Vector2(xMax, yMax);
rect.offsetMin = new Vector2(left, bottom);
rect.offsetMax = new Vector2(0f - right, 0f - top);
}
public static void Stretch(RectTransform rect, float inset = 0f)
{
Place(rect, 0f, 0f, 1f, 1f, inset, inset, inset, inset);
}
public static Image NewImage(Component owner, Color color)
{
//IL_000c: Unknown result type (might be due to invalid IL or missing references)
Image obj = owner.gameObject.AddComponent<Image>();
((Graphic)obj).color = color;
return obj;
}
public static TextMeshProUGUI NewText(Transform parent, string text, float size, TextAlignmentOptions alignment = (TextAlignmentOptions)4097, bool rich = false)
{
//IL_005e: 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)
TextMeshProUGUI val = ((Component)Rect("Text", parent)).gameObject.AddComponent<TextMeshProUGUI>();
if ((Object)(object)_font == (Object)null)
{
_font = FallbackFont();
}
if ((Object)(object)_font != (Object)null)
{
((TMP_Text)val).font = _font;
}
if ((Object)(object)_fontMaterial != (Object)null)
{
((TMP_Text)val).fontSharedMaterial = _fontMaterial;
}
((Graphic)val).color = Color.white;
((TMP_Text)val).fontSize = size;
((TMP_Text)val).alignment = alignment;
((TMP_Text)val).richText = rich;
((TMP_Text)val).enableWordWrapping = true;
((Graphic)val).raycastTarget = false;
((TMP_Text)val).text = text;
return val;
}
public static Button NewButton(Transform parent, string label, float size, Color color, Action onClick)
{
//IL_000c: Unknown result type (might be due to invalid IL or missing references)
RectTransform obj = Rect("Button", parent);
Image targetGraphic = NewImage((Component)(object)obj, color);
Button val = ((Component)obj).gameObject.AddComponent<Button>();
((Selectable)val).targetGraphic = (Graphic)(object)targetGraphic;
OnClick(val, onClick);
Stretch(((TMP_Text)NewText((Transform)(object)obj, label, size, (TextAlignmentOptions)514, rich: true)).rectTransform, 6f);
return val;
}
public static void OnClick(Button button, Action onClick)
{
((UnityEvent)button.onClick).AddListener(DelegateSupport.ConvertDelegate<UnityAction>((Delegate)onClick));
}
public static Slider NewSlider(Transform parent, float min, float max, bool whole, float value, Action<float> changed)
{
//IL_0045: 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_00a2: Unknown result type (might be due to invalid IL or missing references)
//IL_0100: Unknown result type (might be due to invalid IL or missing references)
//IL_010c: Unknown result type (might be due to invalid IL or missing references)
RectTransform val = Rect("Slider", parent);
RectTransform obj = Rect("Background", (Transform)(object)val);
Place(obj, 0f, 0.35f, 1f, 0.65f);
NewImage((Component)(object)obj, FieldColor);
RectTransform val2 = Rect("Fill Area", (Transform)(object)val);
Place(val2, 0f, 0.35f, 1f, 0.65f, 12f, 0f, 12f);
RectTransform val3 = Rect("Fill", (Transform)(object)val2);
val3.sizeDelta = Vector2.zero;
NewImage((Component)(object)val3, ButtonColor);
RectTransform val4 = Rect("Handle Slide Area", (Transform)(object)val);
Place(val4, 0f, 0f, 1f, 1f, 12f, 0f, 12f);
RectTransform val5 = Rect("Handle", (Transform)(object)val4);
val5.sizeDelta = new Vector2(24f, 0f);
Image targetGraphic = NewImage((Component)(object)val5, SelectedColor);
Slider obj2 = ((Component)val).gameObject.AddComponent<Slider>();
obj2.fillRect = val3;
obj2.handleRect = val5;
((Selectable)obj2).targetGraphic = (Graphic)(object)targetGraphic;
obj2.direction = (Direction)0;
obj2.minValue = min;
obj2.maxValue = max;
obj2.wholeNumbers = whole;
obj2.SetValueWithoutNotify(value);
((UnityEvent<float>)(object)obj2.onValueChanged).AddListener(DelegateSupport.ConvertDelegate<UnityAction<float>>((Delegate)changed));
return obj2;
}
public static TMP_InputField NewInput(Transform parent, string value, float size, Action<string> endEdit)
{
//IL_0019: Unknown result type (might be due to invalid IL or missing references)
//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
RectTransform val = Rect("Input", parent);
((Component)val).gameObject.SetActive(false);
Image targetGraphic = NewImage((Component)(object)val, FieldColor);
RectTransform val2 = Rect("Text Area", (Transform)(object)val);
Place(val2, 0f, 0f, 1f, 1f, 10f, 4f, 10f, 4f);
((Component)val2).gameObject.AddComponent<RectMask2D>();
TextMeshProUGUI val3 = NewText((Transform)(object)val2, "", size, (TextAlignmentOptions)4097);
Stretch(((TMP_Text)val3).rectTransform);
((TMP_Text)val3).enableWordWrapping = false;
TMP_InputField obj = ((Component)val).gameObject.AddComponent<TMP_InputField>();
obj.textViewport = val2;
obj.textComponent = (TMP_Text)(object)val3;
((Selectable)obj).targetGraphic = (Graphic)(object)targetGraphic;
obj.lineType = (LineType)0;
obj.richText = false;
obj.customCaretColor = true;
obj.caretColor = Color.white;
obj.SetTextWithoutNotify(value);
((UnityEvent<string>)(object)obj.onEndEdit).AddListener(DelegateSupport.ConvertDelegate<UnityAction<string>>((Delegate)endEdit));
((Component)val).gameObject.SetActive(true);
return obj;
}
public static ScrollRect NewScroll(Transform parent, float spacing, out RectTransform content)
{
//IL_0044: Unknown result type (might be due to invalid IL or missing references)
//IL_0068: Unknown result type (might be due to invalid IL or missing references)
//IL_007e: Unknown result type (might be due to invalid IL or missing references)
//IL_0094: Unknown result type (might be due to invalid IL or missing references)
//IL_00a0: Unknown result type (might be due to invalid IL or missing references)
//IL_00be: Unknown result type (might be due to invalid IL or missing references)
//IL_00c3: Unknown result type (might be due to invalid IL or missing references)
//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
//IL_00d2: Unknown result type (might be due to invalid IL or missing references)
//IL_00d9: Unknown result type (might be due to invalid IL or missing references)
//IL_00e5: Expected O, but got Unknown
RectTransform val = Rect("Scroll", parent);
RectTransform val2 = Rect("Viewport", (Transform)(object)val);
Stretch(val2);
((Component)val2).gameObject.AddComponent<RectMask2D>();
NewImage((Component)(object)val2, new Color(0f, 0f, 0f, 0f));
content = Rect("Content", (Transform)(object)val2);
content.anchorMin = new Vector2(0f, 1f);
content.anchorMax = new Vector2(1f, 1f);
content.pivot = new Vector2(0.5f, 1f);
content.sizeDelta = Vector2.zero;
VerticalLayoutGroup obj = ((Component)content).gameObject.AddComponent<VerticalLayoutGroup>();
((HorizontalOrVerticalLayoutGroup)obj).spacing = spacing;
((LayoutGroup)obj).padding = new RectOffset
{
left = 4,
right = 16,
top = 4,
bottom = 4
};
((HorizontalOrVerticalLayoutGroup)obj).childControlWidth = true;
((HorizontalOrVerticalLayoutGroup)obj).childControlHeight = true;
((HorizontalOrVerticalLayoutGroup)obj).childForceExpandWidth = true;
((HorizontalOrVerticalLayoutGroup)obj).childForceExpandHeight = false;
((Component)content).gameObject.AddComponent<ContentSizeFitter>().verticalFit = (FitMode)2;
ScrollRect obj2 = ((Component)val).gameObject.AddComponent<ScrollRect>();
obj2.viewport = val2;
obj2.content = content;
obj2.horizontal = false;
obj2.vertical = true;
obj2.movementType = (MovementType)2;
obj2.scrollSensitivity = 40f;
return obj2;
}
public static void Height(Component row, float height)
{
LayoutElement obj = row.gameObject.AddComponent<LayoutElement>();
obj.minHeight = height;
obj.preferredHeight = height;
}
public static void Clear(Transform parent)
{
for (int num = parent.childCount - 1; num >= 0; num--)
{
GameObject gameObject = ((Component)parent.GetChild(num)).gameObject;
gameObject.SetActive(false);
Object.Destroy((Object)(object)gameObject);
}
}
private static TMP_FontAsset FallbackFont()
{
Il2CppArrayBase<TMP_FontAsset> val = Resources.FindObjectsOfTypeAll<TMP_FontAsset>();
if (val.Length <= 0)
{
return null;
}
return val[0];
}
}
}