using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Text;
using Il2CppInterop.Runtime.InteropTypes;
using Il2CppInterop.Runtime.InteropTypes.Arrays;
using Il2CppSystem;
using Il2CppSystem.Reflection;
using MelonLoader;
using MelonLoader.Preferences;
using Microsoft.CodeAnalysis;
using Poop;
using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Controls;
using UnityEngine.Rendering;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: MelonInfo(typeof(PoopMod), "Poop", "1.0.0", "Zooks", null)]
[assembly: MelonGame("Boneloaf", "Gang Beasts")]
[assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")]
[assembly: AssemblyCompany("Poop")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("Poop")]
[assembly: AssemblyTitle("Poop")]
[assembly: AssemblyVersion("1.0.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 Poop
{
internal static class LocalFlags
{
private const BindingFlags Flags = (BindingFlags)52;
public static bool SaysLocal(Transform root)
{
foreach (Component componentsInChild in ((Component)root).GetComponentsInChildren<Component>(true))
{
if ((Object)(object)componentsInChild == (Object)null)
{
continue;
}
try
{
if (Check(componentsInChild))
{
return true;
}
}
catch
{
}
}
return false;
}
private static bool Check(Component c)
{
Type il2CppType = ((Object)c).GetIl2CppType();
foreach (PropertyInfo item in (Il2CppArrayBase<PropertyInfo>)(object)il2CppType.GetProperties((BindingFlags)52))
{
if (!(item.PropertyType.FullName != "System.Boolean") && Interesting(((MemberInfo)item).Name))
{
Object value = item.GetValue((Object)(object)c, (Il2CppReferenceArray<Object>)null);
if (value != null && ((Il2CppObjectBase)value).Unbox<bool>())
{
return true;
}
}
}
foreach (FieldInfo item2 in (Il2CppArrayBase<FieldInfo>)(object)il2CppType.GetFields((BindingFlags)52))
{
if (!(item2.FieldType.FullName != "System.Boolean") && Interesting(((MemberInfo)item2).Name))
{
Object value2 = item2.GetValue((Object)(object)c);
if (value2 != null && ((Il2CppObjectBase)value2).Unbox<bool>())
{
return true;
}
}
}
return false;
}
private static bool Interesting(string name)
{
string text = name.ToLowerInvariant().Replace("_", "").Replace("<", "")
.Replace(">k__backingfield", "");
if (text.StartsWith("m"))
{
text = text.Substring(1);
}
if (!text.Contains("islocal"))
{
switch (text)
{
default:
return text == "isowned";
case "isowner":
case "ismine":
case "hasauthority":
break;
}
}
return true;
}
}
internal static class PoopAudio
{
public static float Volume = 1f;
private static AudioSource _normal;
private static AudioSource _slow;
private static bool _checkedListener;
private static bool _moaned;
private static void Ensure()
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
//IL_0018: Unknown result type (might be due to invalid IL or missing references)
//IL_0020: Unknown result type (might be due to invalid IL or missing references)
//IL_0026: Expected O, but got Unknown
//IL_0026: Unknown result type (might be due to invalid IL or missing references)
//IL_002c: Expected O, but got Unknown
//IL_0036: Expected O, but got Unknown
if (!((Object)(object)_normal != (Object)null))
{
GameObject val = new GameObject("PoopSfx")
{
hideFlags = (HideFlags)61
};
Object.DontDestroyOnLoad((Object)val);
_normal = MakeSource(val);
_slow = MakeSource(val);
}
}
private static AudioSource MakeSource(GameObject go)
{
AudioSource obj = go.AddComponent<AudioSource>();
obj.playOnAwake = false;
obj.loop = false;
obj.spatialBlend = 0f;
obj.priority = 0;
obj.ignoreListenerPause = true;
obj.bypassEffects = true;
obj.bypassListenerEffects = true;
obj.bypassReverbZones = true;
return obj;
}
public static void Play(AudioClip clip, float pitch, float vol)
{
if ((Object)(object)clip == (Object)null)
{
if (!_moaned)
{
_moaned = true;
MelonLogger.Warning("no clip to play, poop.wav didnt load (check the startup log for where it looked)");
}
return;
}
Ensure();
if (!_checkedListener)
{
_checkedListener = true;
if ((Object)(object)Object.FindObjectOfType<AudioListener>() == (Object)null)
{
MelonLogger.Warning("scene has no AudioListener, you wont hear anything");
}
if (AudioListener.volume <= 0.001f)
{
MelonLogger.Warning("AudioListener.volume is 0");
}
}
AudioSource obj = ((pitch > 0.98f) ? _normal : _slow);
obj.clip = clip;
obj.pitch = pitch;
obj.volume = Mathf.Clamp01(vol * Volume);
obj.Play();
}
public static AudioClip LoadWav(string path)
{
byte[] array = File.ReadAllBytes(path);
if (array.Length < 12 || Tag(array, 0) != "RIFF" || Tag(array, 8) != "WAVE")
{
throw new Exception("not a wav file");
}
int num = 0;
int num2 = 0;
int num3 = 0;
int num4 = 0;
int num5 = -1;
int num6 = 0;
int num7 = 12;
while (num7 + 8 <= array.Length)
{
string text = Tag(array, num7);
int num8 = BitConverter.ToInt32(array, num7 + 4);
num7 += 8;
if (text == "fmt ")
{
num = BitConverter.ToInt16(array, num7);
num2 = BitConverter.ToInt16(array, num7 + 2);
num3 = BitConverter.ToInt32(array, num7 + 4);
num4 = BitConverter.ToInt16(array, num7 + 14);
if (num == -2 && num8 >= 26)
{
num = BitConverter.ToInt16(array, num7 + 24);
}
}
else if (text == "data")
{
num5 = num7;
num6 = Math.Min(num8, array.Length - num7);
}
num7 += num8 + (num8 & 1);
}
if (num5 < 0)
{
throw new Exception("no data chunk");
}
if (num2 < 1 || num3 < 1)
{
throw new Exception("bad fmt chunk");
}
int num9 = num4 / 8;
int num10 = num6 / num9 / num2;
float[] array2 = new float[num10 * num2];
for (int i = 0; i < array2.Length; i++)
{
int num11 = num5 + i * num9;
float num12 = ((num == 3 && num4 == 32) ? BitConverter.ToSingle(array, num11) : (num4 switch
{
16 => (float)BitConverter.ToInt16(array, num11) / 32768f,
8 => (float)(array[num11] - 128) / 128f,
24 => (float)(((array[num11] << 8) | (array[num11 + 1] << 16) | (array[num11 + 2] << 24)) >> 8) / 8388608f,
32 => (float)BitConverter.ToInt32(array, num11) / 2.1474836E+09f,
_ => throw new Exception($"unsupported wav: fmt {num} {num4}bit"),
}));
array2[i] = num12;
}
AudioClip obj = AudioClip.Create(Path.GetFileNameWithoutExtension(path), num10, num2, num3, false);
obj.SetData(Il2CppStructArray<float>.op_Implicit(array2), 0);
return obj;
}
private static string Tag(byte[] b, int at)
{
return Encoding.ASCII.GetString(b, at, 4);
}
}
internal static class PoopLook
{
private const string UrpLit = "Universal Render Pipeline/Lit";
private const string UrpSimple = "Universal Render Pipeline/Simple Lit";
private static readonly Color Dark = new Color(0.2f, 0.1f, 0.04f);
private static readonly Color Brown = new Color(0.36f, 0.2f, 0.08f);
private static readonly Color Light = new Color(0.46f, 0.28f, 0.12f);
public static string ShaderOverride = "";
public static string Mode = "Auto";
public static int DonorLayer = 0;
private static bool? _urp;
private static List<(Material mat, int layer, string from, int score)> _scan;
public static string PipelineName
{
get
{
RenderPipelineAsset renderPipelineAsset = GraphicsSettings.renderPipelineAsset;
if (!((Object)(object)renderPipelineAsset == (Object)null))
{
return ((MemberInfo)((Object)renderPipelineAsset).GetIl2CppType()).Name;
}
return "Built-in";
}
}
public static bool IsUrp
{
get
{
if (!_urp.HasValue)
{
_urp = PipelineName.Contains("Universal");
}
return _urp.Value;
}
}
public static void Forget()
{
_urp = null;
_scan = null;
}
public static Material PoopMaterial()
{
//IL_000a: Unknown result type (might be due to invalid IL or missing references)
return Setup(Base("poop"), Color.white, 0.62f);
}
public static Material SplatMaterial()
{
//IL_0019: Unknown result type (might be due to invalid IL or missing references)
return Setup(Base("splat"), new Color(0.7f, 0.6f, 0.55f), 0.75f);
}
private static Material Base(string name)
{
Material val = null;
string how = "";
if (!string.IsNullOrEmpty(ShaderOverride))
{
val = Fresh(ShaderOverride);
how = "ShaderOverride";
if ((Object)(object)val == (Object)null)
{
MelonLogger.Warning("ShaderOverride '" + ShaderOverride + "' isnt in the build");
}
}
if ((Object)(object)val == (Object)null && IsUrp)
{
switch (Mode)
{
case "Lit":
val = Fresh("Universal Render Pipeline/Lit");
how = "fresh URP Lit";
break;
case "SimpleLit":
val = Fresh("Universal Render Pipeline/Simple Lit");
how = "fresh URP Simple Lit";
break;
case "Clone":
val = Clone(null, out how);
break;
default:
val = Clone("Universal Render Pipeline/Lit", out how);
if ((Object)(object)val == (Object)null)
{
val = Fresh("Universal Render Pipeline/Lit");
how = "fresh URP Lit";
}
if ((Object)(object)val == (Object)null)
{
val = Fresh("Universal Render Pipeline/Simple Lit");
how = "fresh URP Simple Lit";
}
if ((Object)(object)val == (Object)null)
{
val = Clone(null, out how);
}
break;
}
}
if ((Object)(object)val == (Object)null && !IsUrp)
{
val = Clone(null, out how);
if ((Object)(object)val == (Object)null)
{
val = Fresh("Standard");
how = "fresh Standard";
}
if ((Object)(object)val == (Object)null)
{
val = Fresh("Legacy Shaders/Diffuse");
how = "fresh Legacy Diffuse";
}
}
if ((Object)(object)val == (Object)null)
{
val = Clone(null, out how);
if ((Object)(object)val == (Object)null)
{
throw new Exception("could not build any material at all");
}
}
((Object)val).name = name;
MelonLogger.Msg($"{name} material: {how} -> shader '{((Object)val.shader).name}' (pipeline {PipelineName})");
return val;
}
private static Material Fresh(string shaderName)
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
//IL_0019: Expected O, but got Unknown
Shader val = Shader.Find(shaderName);
if ((Object)(object)val == (Object)null)
{
return null;
}
Material val2 = new Material(val);
Scan();
foreach (var item in _scan)
{
if (!(((Object)item.mat.shader).name != shaderName))
{
val2.shaderKeywords = item.mat.shaderKeywords;
break;
}
}
return val2;
}
private static Material Clone(string wantShader, out string how)
{
//IL_00df: Unknown result type (might be due to invalid IL or missing references)
//IL_00e5: Expected O, but got Unknown
Scan();
foreach (var item in _scan)
{
if ((wantShader == null || !(((Object)item.mat.shader).name != wantShader)) && item.score >= 0)
{
DonorLayer = item.layer;
how = $"clone of '{((Object)item.mat).name}' off '{item.from}' (layer {item.layer}, score {item.score})";
return new Material(item.mat);
}
}
how = "";
return null;
}
private static void Scan()
{
if (_scan != null)
{
return;
}
_scan = new List<(Material, int, string, int)>();
HashSet<int> hashSet = new HashSet<int>();
Dictionary<string, int> dictionary = new Dictionary<string, int>();
foreach (Renderer item in Object.FindObjectsOfType<Renderer>())
{
if ((Object)(object)item == (Object)null || !item.enabled || !item.isVisible)
{
continue;
}
string name = ((MemberInfo)((Object)item).GetIl2CppType()).Name;
int num = 0;
if (name == "MeshRenderer")
{
num += 10;
}
else if (name == "SkinnedMeshRenderer")
{
num += 2;
}
else if (name.Contains("Particle") || name.Contains("Line") || name.Contains("Trail"))
{
num -= 100;
}
foreach (Material item2 in (Il2CppArrayBase<Material>)(object)item.sharedMaterials)
{
if ((Object)(object)item2 == (Object)null || (Object)(object)item2.shader == (Object)null)
{
continue;
}
string name2 = ((Object)item2.shader).name;
dictionary[name2] = ((!dictionary.TryGetValue(name2, out var value)) ? 1 : (value + 1));
if (!hashSet.Add(((Object)item2).GetInstanceID()) || item2.renderQueue > 2500)
{
continue;
}
int num2 = num;
if (IsUrp)
{
if (name2 == "Universal Render Pipeline/Lit")
{
num2 += 50;
}
else if (name2 == "Universal Render Pipeline/Simple Lit")
{
num2 += 40;
}
else if (name2.StartsWith("Universal Render Pipeline/"))
{
num2 += 25;
}
else if (name2.Contains("Shader Graphs/"))
{
num2 += 10;
}
else if (name2 == "Standard" || name2.StartsWith("Legacy") || name2.Contains("Mobile/"))
{
num2 -= 100;
}
}
else if (name2 == "Standard")
{
num2 += 30;
}
else if (name2.Contains("Standard"))
{
num2 += 15;
}
else if (name2.Contains("Diffuse"))
{
num2 += 5;
}
if (item2.HasProperty("_BaseMap") || item2.HasProperty("_MainTex"))
{
num2 += 5;
}
if (item2.HasProperty("_BaseColor") || item2.HasProperty("_Color"))
{
num2 += 3;
}
if (!item2.IsKeywordEnabled("_ALPHATEST_ON") && !item2.IsKeywordEnabled("_SURFACE_TYPE_TRANSPARENT") && !item2.IsKeywordEnabled("_ALPHABLEND_ON"))
{
num2 += 4;
}
if (name2.Contains("Skybox") || name2.Contains("Particle") || name2.Contains("UI") || name2.Contains("Sprite") || name2.Contains("Hidden") || name2.Contains("Terrain"))
{
num2 -= 100;
}
_scan.Add((item2, ((Component)item).gameObject.layer, ((Object)item).name, num2));
}
}
_scan.Sort(((Material mat, int layer, string from, int score) a, (Material mat, int layer, string from, int score) b) => b.score.CompareTo(a.score));
List<KeyValuePair<string, int>> list = new List<KeyValuePair<string, int>>(dictionary);
list.Sort((KeyValuePair<string, int> a, KeyValuePair<string, int> b) => b.Value.CompareTo(a.Value));
StringBuilder stringBuilder = new StringBuilder("shaders in scene:");
for (int num3 = 0; num3 < list.Count && num3 < 12; num3++)
{
StringBuilder stringBuilder2 = stringBuilder;
StringBuilder.AppendInterpolatedStringHandler handler = new StringBuilder.AppendInterpolatedStringHandler(5, 2, stringBuilder2);
handler.AppendLiteral(" [");
handler.AppendFormatted(list[num3].Value);
handler.AppendLiteral("] ");
handler.AppendFormatted(list[num3].Key);
stringBuilder2.Append(ref handler);
}
MelonLogger.Msg(stringBuilder.ToString());
}
private static Material Setup(Material m, Color tint, float gloss)
{
//IL_0057: 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)
//IL_00a4: Unknown result type (might be due to invalid IL or missing references)
//IL_00af: Unknown result type (might be due to invalid IL or missing references)
//IL_0089: Unknown result type (might be due to invalid IL or missing references)
//IL_0099: Unknown result type (might be due to invalid IL or missing references)
//IL_012a: Unknown result type (might be due to invalid IL or missing references)
//IL_02b8: Unknown result type (might be due to invalid IL or missing references)
//IL_034b: Unknown result type (might be due to invalid IL or missing references)
//IL_038a: Unknown result type (might be due to invalid IL or missing references)
//IL_03b9: Unknown result type (might be due to invalid IL or missing references)
//IL_040a: Unknown result type (might be due to invalid IL or missing references)
//IL_03e8: Unknown result type (might be due to invalid IL or missing references)
//IL_0445: Unknown result type (might be due to invalid IL or missing references)
Texture2D val = (Texture2D)(object)(m.mainTexture = (Texture)(object)PoopTexture(128));
if (m.HasProperty("_BaseMap"))
{
m.SetTexture("_BaseMap", (Texture)(object)val);
}
if (m.HasProperty("_MainTex"))
{
m.SetTexture("_MainTex", (Texture)(object)val);
}
if (m.HasProperty("_BaseColor"))
{
m.SetColor("_BaseColor", tint);
}
if (m.HasProperty("_Color"))
{
m.SetColor("_Color", tint);
}
if (m.HasProperty("_BaseMap"))
{
m.SetTextureScale("_BaseMap", Vector2.one);
m.SetTextureOffset("_BaseMap", Vector2.zero);
}
m.mainTextureScale = Vector2.one;
m.mainTextureOffset = Vector2.zero;
if (m.HasProperty("_Smoothness"))
{
m.SetFloat("_Smoothness", gloss);
}
if (m.HasProperty("_Glossiness"))
{
m.SetFloat("_Glossiness", gloss);
}
if (m.HasProperty("_Metallic"))
{
m.SetFloat("_Metallic", 0.05f);
}
if (m.HasProperty("_SpecColor"))
{
m.SetColor("_SpecColor", new Color(0.3f, 0.3f, 0.3f));
}
if (m.HasProperty("_Surface"))
{
m.SetFloat("_Surface", 0f);
}
if (m.HasProperty("_Blend"))
{
m.SetFloat("_Blend", 0f);
}
if (m.HasProperty("_AlphaClip"))
{
m.SetFloat("_AlphaClip", 0f);
}
if (m.HasProperty("_Mode"))
{
m.SetFloat("_Mode", 0f);
}
if (m.HasProperty("_SrcBlend"))
{
m.SetInt("_SrcBlend", 1);
}
if (m.HasProperty("_DstBlend"))
{
m.SetInt("_DstBlend", 0);
}
if (m.HasProperty("_ZWrite"))
{
m.SetInt("_ZWrite", 1);
}
if (m.HasProperty("_Cull"))
{
m.SetInt("_Cull", 2);
}
if (m.HasProperty("_Cutoff"))
{
m.SetFloat("_Cutoff", 0f);
}
if (m.HasProperty("_QueueOffset"))
{
m.SetFloat("_QueueOffset", 0f);
}
m.DisableKeyword("_SURFACE_TYPE_TRANSPARENT");
m.DisableKeyword("_ALPHATEST_ON");
m.DisableKeyword("_ALPHABLEND_ON");
m.DisableKeyword("_ALPHAPREMULTIPLY_ON");
m.DisableKeyword("_ALPHAMODULATE_ON");
m.SetOverrideTag("RenderType", "Opaque");
m.renderQueue = 2000;
if (m.IsKeywordEnabled("_EMISSION") && m.HasProperty("_EmissionColor"))
{
m.SetColor("_EmissionColor", Color.black);
}
if (m.IsKeywordEnabled("_NORMALMAP") && m.HasProperty("_BumpMap"))
{
m.SetTexture("_BumpMap", (Texture)(object)BumpTexture(128));
if (m.HasProperty("_BumpScale"))
{
m.SetFloat("_BumpScale", 1f);
}
}
if ((m.IsKeywordEnabled("_METALLICSPECGLOSSMAP") || m.IsKeywordEnabled("_METALLICGLOSSMAP")) && m.HasProperty("_MetallicGlossMap"))
{
m.SetTexture("_MetallicGlossMap", (Texture)(object)Flat(new Color(0.05f, 0f, 0f, gloss)));
}
if (m.IsKeywordEnabled("_SPECGLOSSMAP") && m.HasProperty("_SpecGlossMap"))
{
m.SetTexture("_SpecGlossMap", (Texture)(object)Flat(new Color(0.3f, 0.3f, 0.3f, gloss)));
}
if (m.IsKeywordEnabled("_OCCLUSIONMAP") && m.HasProperty("_OcclusionMap"))
{
m.SetTexture("_OcclusionMap", (Texture)(object)Flat(Color.white));
}
if (m.IsKeywordEnabled("_PARALLAXMAP") && m.HasProperty("_ParallaxMap"))
{
m.SetTexture("_ParallaxMap", (Texture)(object)Flat(Color.black));
}
if (m.HasProperty("_DetailAlbedoMap"))
{
m.SetTexture("_DetailAlbedoMap", (Texture)(object)Flat(Color.gray));
}
if (m.HasProperty("_DetailNormalMap"))
{
m.SetTexture("_DetailNormalMap", (Texture)null);
}
if (m.HasProperty("_DetailMask"))
{
m.SetTexture("_DetailMask", (Texture)(object)Flat(Color.white));
}
return m;
}
public static string Keywords(Material m)
{
StringBuilder stringBuilder = new StringBuilder();
foreach (string item in (Il2CppArrayBase<string>)(object)m.shaderKeywords)
{
if (stringBuilder.Length > 0)
{
stringBuilder.Append(' ');
}
stringBuilder.Append(item);
}
return stringBuilder.ToString();
}
private static Texture2D Flat(Color c)
{
//IL_0004: Unknown result type (might be due to invalid IL or missing references)
//IL_000a: Expected O, but got Unknown
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
//IL_0014: Unknown result type (might be due to invalid IL or missing references)
//IL_001b: Unknown result type (might be due to invalid IL or missing references)
//IL_001c: Unknown result type (might be due to invalid IL or missing references)
//IL_0023: Unknown result type (might be due to invalid IL or missing references)
//IL_0024: 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_002c: Unknown result type (might be due to invalid IL or missing references)
Texture2D val = new Texture2D(2, 2, (TextureFormat)4, false);
val.SetPixels(Il2CppStructArray<Color>.op_Implicit((Color[])(object)new Color[4] { c, c, c, c }));
val.Apply();
return val;
}
private static Texture2D PoopTexture(int size)
{
//IL_0004: Unknown result type (might be due to invalid IL or missing references)
//IL_000a: Expected O, but got Unknown
//IL_0085: Unknown result type (might be due to invalid IL or missing references)
//IL_008a: 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_0096: 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_009a: Unknown result type (might be due to invalid IL or missing references)
//IL_00a7: Unknown result type (might be due to invalid IL or missing references)
//IL_00ac: Unknown result type (might be due to invalid IL or missing references)
//IL_00ec: Unknown result type (might be due to invalid IL or missing references)
//IL_00ee: 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_00d1: Unknown result type (might be due to invalid IL or missing references)
//IL_00d6: Unknown result type (might be due to invalid IL or missing references)
Texture2D val = new Texture2D(size, size, (TextureFormat)4, true);
Color[] array = (Color[])(object)new Color[size * size];
float num = Random.Range(0f, 100f);
float num2 = Random.Range(0f, 100f);
for (int i = 0; i < size; i++)
{
for (int j = 0; j < size; j++)
{
float num3 = (float)j / (float)size;
float num4 = (float)i / (float)size;
float num5 = Mathf.PerlinNoise(num3 * 6f + num, num4 * 6f + num2);
float num6 = Mathf.PerlinNoise(num3 * 22f + num2, num4 * 22f + num);
Color val2 = Color.Lerp(Dark, Light, num5);
val2 = Color.Lerp(val2, Brown, num6 * 0.5f);
if (Mathf.PerlinNoise(num3 * 60f + num, num4 * 60f) > 0.72f)
{
val2 *= 0.7f;
}
val2.a = 1f;
array[i * size + j] = val2;
}
}
val.SetPixels(Il2CppStructArray<Color>.op_Implicit(array));
((Texture)val).wrapMode = (TextureWrapMode)0;
val.Apply();
return val;
}
private static Texture2D BumpTexture(int size)
{
//IL_0091: Unknown result type (might be due to invalid IL or missing references)
//IL_0097: Expected O, but got Unknown
//IL_010b: Unknown result type (might be due to invalid IL or missing references)
//IL_0110: Unknown result type (might be due to invalid IL or missing references)
//IL_0114: 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_0128: 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_0153: Unknown result type (might be due to invalid IL or missing references)
//IL_0158: Unknown result type (might be due to invalid IL or missing references)
float[] array = new float[size * size];
float num = Random.Range(0f, 100f);
for (int i = 0; i < size; i++)
{
for (int j = 0; j < size; j++)
{
array[i * size + j] = Mathf.PerlinNoise((float)j / (float)size * 10f + num, (float)i / (float)size * 10f) * 0.6f + Mathf.PerlinNoise((float)j / (float)size * 40f, (float)i / (float)size * 40f + num) * 0.4f;
}
}
Texture2D val = new Texture2D(size, size, (TextureFormat)4, true);
Color[] array2 = (Color[])(object)new Color[size * size];
for (int k = 0; k < size; k++)
{
for (int l = 0; l < size; l++)
{
float num2 = array[k * size + (l + size - 1) % size];
float num3 = array[k * size + (l + 1) % size];
float num4 = array[(k + size - 1) % size * size + l];
float num5 = array[(k + 1) % size * size + l];
Vector3 val2 = new Vector3((num2 - num3) * 3f, (num4 - num5) * 3f, 1f);
Vector3 normalized = ((Vector3)(ref val2)).normalized;
array2[k * size + l] = new Color(1f, normalized.y * 0.5f + 0.5f, 1f, normalized.x * 0.5f + 0.5f);
}
}
val.SetPixels(Il2CppStructArray<Color>.op_Implicit(array2));
((Texture)val).wrapMode = (TextureWrapMode)0;
val.Apply();
return val;
}
}
internal static class PoopMesh
{
public static Mesh BuildSwirl()
{
//IL_0074: Unknown result type (might be due to invalid IL or missing references)
//IL_0079: Unknown result type (might be due to invalid IL or missing references)
//IL_00eb: Unknown result type (might be due to invalid IL or missing references)
//IL_00f0: Unknown result type (might be due to invalid IL or missing references)
//IL_0105: Unknown result type (might be due to invalid IL or missing references)
//IL_010a: Unknown result type (might be due to invalid IL or missing references)
//IL_0118: Unknown result type (might be due to invalid IL or missing references)
//IL_011d: Unknown result type (might be due to invalid IL or missing references)
//IL_011f: Unknown result type (might be due to invalid IL or missing references)
//IL_0124: Unknown result type (might be due to invalid IL or missing references)
//IL_0128: Unknown result type (might be due to invalid IL or missing references)
//IL_012d: Unknown result type (might be due to invalid IL or missing references)
//IL_012f: Unknown result type (might be due to invalid IL or missing references)
//IL_0131: Unknown result type (might be due to invalid IL or missing references)
//IL_0136: Unknown result type (might be due to invalid IL or missing references)
//IL_013b: Unknown result type (might be due to invalid IL or missing references)
//IL_0154: Unknown result type (might be due to invalid IL or missing references)
//IL_0156: Unknown result type (might be due to invalid IL or missing references)
//IL_0158: Unknown result type (might be due to invalid IL or missing references)
//IL_015d: 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)
//IL_0166: Unknown result type (might be due to invalid IL or missing references)
//IL_014d: Unknown result type (might be due to invalid IL or missing references)
//IL_0152: Unknown result type (might be due to invalid IL or missing references)
//IL_02ab: Unknown result type (might be due to invalid IL or missing references)
//IL_02b2: Expected O, but got Unknown
//IL_0306: 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_0313: Unknown result type (might be due to invalid IL or missing references)
//IL_0318: Unknown result type (might be due to invalid IL or missing references)
//IL_0323: Unknown result type (might be due to invalid IL or missing references)
//IL_0328: Unknown result type (might be due to invalid IL or missing references)
//IL_01b6: Unknown result type (might be due to invalid IL or missing references)
//IL_01bf: Unknown result type (might be due to invalid IL or missing references)
//IL_01c4: Unknown result type (might be due to invalid IL or missing references)
//IL_01cd: Unknown result type (might be due to invalid IL or missing references)
//IL_01d2: Unknown result type (might be due to invalid IL or missing references)
//IL_01db: 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_01e7: Unknown result type (might be due to invalid IL or missing references)
//IL_01ed: Unknown result type (might be due to invalid IL or missing references)
//IL_01f2: Unknown result type (might be due to invalid IL or missing references)
//IL_01f4: Unknown result type (might be due to invalid IL or missing references)
//IL_0210: Unknown result type (might be due to invalid IL or missing references)
Vector3[] array = (Vector3[])(object)new Vector3[120];
float[] array2 = new float[120];
for (int i = 0; i < 120; i++)
{
float num = (float)i / 119f;
float num2 = num * 2.6f * (float)Math.PI * 2f;
float num3 = Mathf.Lerp(0.13f, 0f, num * num);
array[i] = new Vector3(Mathf.Cos(num2) * num3, num * 0.3f + 0.06f, Mathf.Sin(num2) * num3);
float num4 = Mathf.Sin(Mathf.Clamp01(Mathf.Min(num * 10f, (1f - num) * 5f)) * (float)Math.PI * 0.5f);
array2[i] = Mathf.Lerp(0.075f, 0.03f, num) * num4;
}
List<Vector3> list = new List<Vector3>();
List<Vector2> list2 = new List<Vector2>();
List<int> list3 = new List<int>();
Vector3 val = Vector3.right;
for (int j = 0; j < 120; j++)
{
Vector3 val2 = array[Mathf.Max(j - 1, 0)];
Vector3 val3 = array[Mathf.Min(j + 1, 119)] - val2;
Vector3 normalized = ((Vector3)(ref val3)).normalized;
Vector3 val4 = Vector3.Cross(normalized, Vector3.up);
if (((Vector3)(ref val4)).sqrMagnitude > 0.0001f)
{
val = ((Vector3)(ref val4)).normalized;
}
val3 = Vector3.Cross(val, normalized);
Vector3 normalized2 = ((Vector3)(ref val3)).normalized;
float num5 = (float)j / 119f;
for (int k = 0; k <= 12; k++)
{
float num6 = (float)k / 12f * (float)Math.PI * 2f;
float num7 = 1f + Mathf.PerlinNoise(num5 * 9f, (float)k * 0.4f) * 0.18f;
Vector3 val5 = (val * Mathf.Cos(num6) + normalized2 * Mathf.Sin(num6)) * array2[j] * num7;
list.Add(array[j] + val5);
list2.Add(new Vector2((float)k / 12f, num5 * 5f));
}
}
int num8 = 13;
for (int l = 0; l < 119; l++)
{
for (int m = 0; m < 12; m++)
{
int num9 = l * num8 + m;
int num10 = num9 + num8;
list3.Add(num9);
list3.Add(num10);
list3.Add(num9 + 1);
list3.Add(num9 + 1);
list3.Add(num10);
list3.Add(num10 + 1);
}
}
Mesh val6 = new Mesh();
((Object)val6).name = "poop";
val6.vertices = Il2CppStructArray<Vector3>.op_Implicit(list.ToArray());
val6.uv = Il2CppStructArray<Vector2>.op_Implicit(list2.ToArray());
val6.triangles = Il2CppStructArray<int>.op_Implicit(list3.ToArray());
val6.RecalculateNormals();
int num11 = 60 * num8;
Vector3 val7 = list[num11] - array[60];
if (Vector3.Dot(((Il2CppArrayBase<Vector3>)(object)val6.normals)[num11], val7) < 0f)
{
Il2CppStructArray<int> triangles = val6.triangles;
for (int n = 0; n < ((Il2CppArrayBase<int>)(object)triangles).Length; n += 3)
{
int num12 = ((Il2CppArrayBase<int>)(object)triangles)[n + 1];
((Il2CppArrayBase<int>)(object)triangles)[n + 1] = ((Il2CppArrayBase<int>)(object)triangles)[n + 2];
((Il2CppArrayBase<int>)(object)triangles)[n + 2] = num12;
}
val6.triangles = triangles;
val6.RecalculateNormals();
}
val6.RecalculateBounds();
val6.RecalculateTangents();
return val6;
}
public static Mesh BuildBlob(int seed)
{
//IL_0030: 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_003c: Unknown result type (might be due to invalid IL or missing references)
//IL_0060: 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_0074: Unknown result type (might be due to invalid IL or missing references)
//IL_0078: Unknown result type (might be due to invalid IL or missing references)
//IL_0082: Unknown result type (might be due to invalid IL or missing references)
//IL_0087: 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_00b7: Unknown result type (might be due to invalid IL or missing references)
//IL_00bc: Unknown result type (might be due to invalid IL or missing references)
//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
//IL_00e9: 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_0115: Unknown result type (might be due to invalid IL or missing references)
//IL_012b: Unknown result type (might be due to invalid IL or missing references)
//IL_0132: Expected O, but got Unknown
List<Vector3> verts = new List<Vector3>();
List<Vector3> norms = new List<Vector3>();
List<Vector2> uvs = new List<Vector2>();
List<int> tris = new List<int>();
State state = Random.state;
Random.InitState(seed);
Disc(Vector2.zero, 0.45f, 0.3f, 28);
int num = Random.Range(3, 7);
for (int i = 0; i < num; i++)
{
Vector2 val = Random.insideUnitCircle * 0.5f;
Vector2 insideUnitCircle = Random.insideUnitCircle;
Disc(val + ((Vector2)(ref insideUnitCircle)).normalized * 0.25f, Random.Range(0.04f, 0.11f), 0.25f, 10);
}
Random.state = state;
Mesh val2 = new Mesh
{
name = "splat" + seed,
vertices = Il2CppStructArray<Vector3>.op_Implicit(verts.ToArray()),
normals = Il2CppStructArray<Vector3>.op_Implicit(norms.ToArray()),
uv = Il2CppStructArray<Vector2>.op_Implicit(uvs.ToArray()),
triangles = Il2CppStructArray<int>.op_Implicit(tris.ToArray())
};
val2.RecalculateBounds();
return val2;
void Disc(Vector2 centre, float radius, float wobble, int segs)
{
//IL_0014: Unknown result type (might be due to invalid IL or missing references)
//IL_001a: Unknown result type (might be due to invalid IL or missing references)
//IL_0025: Unknown result type (might be due to invalid IL or missing references)
//IL_0036: 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_0056: 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_00c3: 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_00d7: Unknown result type (might be due to invalid IL or missing references)
//IL_00dc: 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_00ea: Unknown result type (might be due to invalid IL or missing references)
//IL_00f1: 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_010e: Unknown result type (might be due to invalid IL or missing references)
//IL_0129: Unknown result type (might be due to invalid IL or missing references)
//IL_012e: Unknown result type (might be due to invalid IL or missing references)
//IL_0130: Unknown result type (might be due to invalid IL or missing references)
int count = verts.Count;
verts.Add(new Vector3(centre.x, centre.y, 0f));
norms.Add(Vector3.forward);
uvs.Add(new Vector2(0.5f, 0.5f) + centre);
float num2 = Random.Range(0f, 100f);
for (int j = 0; j <= segs; j++)
{
float num3 = (float)j / (float)segs * (float)Math.PI * 2f;
float num4 = Mathf.PerlinNoise(Mathf.Cos(num3) * 1.5f + num2, Mathf.Sin(num3) * 1.5f + num2);
float num5 = radius * (1f - wobble + num4 * wobble * 2f);
Vector2 val3 = centre + new Vector2(Mathf.Cos(num3), Mathf.Sin(num3)) * num5;
verts.Add(new Vector3(val3.x, val3.y, 0f));
norms.Add(Vector3.forward);
uvs.Add(new Vector2(0.5f, 0.5f) + val3);
}
for (int k = 0; k < segs; k++)
{
tris.Add(count);
tris.Add(count + 1 + k);
tris.Add(count + 2 + k);
}
}
}
}
public class PoopMod : MelonMod
{
private class Turd
{
public GameObject go;
public Rigidbody rb;
public Collider col;
public Renderer mr;
public float born;
public float lastSplat = -99f;
public Vector3 lastSplatPos;
public Vector3 lastVel;
public float lastThud = -99f;
}
private class Stain
{
public GameObject go;
public float dies;
}
private MelonPreferences_Entry<string> _keyPref;
private MelonPreferences_Entry<string> _bonePref;
private MelonPreferences_Entry<int> _actorIndex;
private MelonPreferences_Entry<float> _splatSecs;
private MelonPreferences_Entry<float> _poopSecs;
private MelonPreferences_Entry<float> _scale;
private MelonPreferences_Entry<float> _launch;
private MelonPreferences_Entry<float> _thudPitch;
private MelonPreferences_Entry<float> _thudJolt;
private MelonPreferences_Entry<float> _volume;
private MelonPreferences_Entry<string> _shaderOverride;
private MelonPreferences_Entry<string> _matMode;
private MelonPreferences_Entry<int> _layerOverride;
private MelonPreferences_Entry<bool> _debugCube;
private Key _key = (Key)30;
private readonly List<Turd> _turds = new List<Turd>();
private readonly List<Stain> _stains = new List<Stain>();
private Mesh _poopMesh;
private Mesh[] _blobs;
private Material _poopMat;
private Material _splatMat;
private AudioClip _sfx;
private bool _built;
private bool _sfxTried;
private bool _diagDone;
private int _layer;
private Transform _butt;
private Rigidbody[] _body = (Rigidbody[])(object)new Rigidbody[0];
private float _nextButtSearch;
private static readonly Vector3[] Feelers = (Vector3[])(object)new Vector3[6]
{
Vector3.down,
Vector3.up,
Vector3.left,
Vector3.right,
Vector3.forward,
Vector3.back
};
public override void OnInitializeMelon()
{
//IL_01c9: Unknown result type (might be due to invalid IL or missing references)
//IL_01ca: Unknown result type (might be due to invalid IL or missing references)
//IL_0225: Unknown result type (might be due to invalid IL or missing references)
MelonPreferences_Category val = MelonPreferences.CreateCategory("Poop");
_keyPref = val.CreateEntry<string>("Key", "P", (string)null, "Key name from UnityEngine.InputSystem.Key. Fn doesnt exist to the OS, pick something else.", false, false, (ValueValidator)null, (string)null);
_bonePref = val.CreateEntry<string>("ButtBone", "hips", (string)null, "substring of the rigidbody name we poop out of", false, false, (ValueValidator)null, (string)null);
_actorIndex = val.CreateEntry<int>("ActorIndex", -1, (string)null, "-1 = auto detect local player, otherwise force the nth character found", false, false, (ValueValidator)null, (string)null);
_splatSecs = val.CreateEntry<float>("SplatSeconds", 20f, (string)null, (string)null, false, false, (ValueValidator)null, (string)null);
_poopSecs = val.CreateEntry<float>("PoopSeconds", 30f, (string)null, (string)null, false, false, (ValueValidator)null, (string)null);
_scale = val.CreateEntry<float>("Scale", 1f, (string)null, "poop size multiplier", false, false, (ValueValidator)null, (string)null);
_launch = val.CreateEntry<float>("LaunchForce", 5f, (string)null, "how hard the player gets shoved upwards, 0 to disable", false, false, (ValueValidator)null, (string)null);
_thudPitch = val.CreateEntry<float>("ImpactPitch", 0.55f, (string)null, "pitch of poop.wav when the poop hits something", false, false, (ValueValidator)null, (string)null);
_thudJolt = val.CreateEntry<float>("ImpactJolt", 2.5f, (string)null, "how big a velocity change counts as a hit", false, false, (ValueValidator)null, (string)null);
_volume = val.CreateEntry<float>("Volume", 1f, (string)null, (string)null, false, false, (ValueValidator)null, (string)null);
_shaderOverride = val.CreateEntry<string>("ShaderOverride", "", (string)null, "leave empty. otherwise a shader name eg 'Universal Render Pipeline/Simple Lit'", false, false, (ValueValidator)null, (string)null);
_matMode = val.CreateEntry<string>("MaterialMode", "Auto", (string)null, "Auto, Lit, SimpleLit or Clone. Auto = clone a URP/Lit material from the level, else fresh Lit, else Simple Lit", false, false, (ValueValidator)null, (string)null);
_layerOverride = val.CreateEntry<int>("LayerOverride", -1, (string)null, "-1 = auto pick a layer the camera renders. otherwise force a layer 0-31", false, false, (ValueValidator)null, (string)null);
_debugCube = val.CreateEntry<bool>("DebugCube", false, (string)null, "also spawn two test cubes above every poop, for figuring out why its invisible", false, false, (ValueValidator)null, (string)null);
if (Enum.TryParse<Key>(_keyPref.Value, ignoreCase: true, out Key result))
{
_key = result;
}
else
{
((MelonBase)this).LoggerInstance.Warning("'" + _keyPref.Value + "' isnt a key i know, using P");
}
PoopAudio.Volume = _volume.Value;
((MelonBase)this).LoggerInstance.Msg($"loaded. press {_key} to poop");
}
public override void OnSceneWasLoaded(int buildIndex, string sceneName)
{
_built = false;
_diagDone = false;
_butt = null;
_body = (Rigidbody[])(object)new Rigidbody[0];
_turds.Clear();
_stains.Clear();
PoopLook.Forget();
}
public override void OnUpdate()
{
//IL_0047: Unknown result type (might be due to invalid IL or missing references)
if (!_sfxTried)
{
_sfxTried = true;
try
{
LoadSfx();
}
catch (Exception ex)
{
((MelonBase)this).LoggerInstance.Error("wav search blew up: " + ex);
}
}
Keyboard current = Keyboard.current;
if (current != null && ((ButtonControl)current[_key]).wasPressedThisFrame)
{
try
{
Squeeze();
}
catch (Exception ex2)
{
((MelonBase)this).LoggerInstance.Error("poop failed: " + ex2);
}
}
TickTurds();
TickStains();
}
public override void OnFixedUpdate()
{
//IL_0042: Unknown result type (might be due to invalid IL or missing references)
//IL_0047: Unknown result type (might be due to invalid IL or missing references)
//IL_0049: Unknown result type (might be due to invalid IL or missing references)
//IL_004e: Unknown result type (might be due to invalid IL or missing references)
//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)
//IL_0060: Unknown result type (might be due to invalid IL or missing references)
//IL_0061: Unknown result type (might be due to invalid IL or missing references)
float time = Time.time;
for (int i = 0; i < _turds.Count; i++)
{
Turd turd = _turds[i];
if (!((Object)(object)turd.go == (Object)null) && !((Object)(object)turd.rb == (Object)null))
{
Vector3 velocity = turd.rb.velocity;
Vector3 val = turd.lastVel - velocity;
float magnitude = ((Vector3)(ref val)).magnitude;
turd.lastVel = velocity;
if (!(magnitude < _thudJolt.Value) && !(time - turd.lastThud < 0.25f) && !(time - turd.born < 0.1f))
{
turd.lastThud = time;
PoopAudio.Play(_sfx, _thudPitch.Value, Mathf.Clamp(magnitude / 8f, 0.4f, 1f));
}
}
}
}
private void LoadSfx()
{
List<string> list = new List<string>();
try
{
list.Add(Path.GetDirectoryName(((MelonBase)this).MelonAssembly.Location));
}
catch
{
}
try
{
string directoryName = Path.GetDirectoryName(Application.dataPath);
list.Add(Path.Combine(directoryName, "Mods"));
list.Add(Path.Combine(directoryName, "Mods", "Poop"));
list.Add(Path.Combine(directoryName, "UserData"));
list.Add(Path.Combine(directoryName, "UserData", "Poop"));
list.Add(directoryName);
}
catch
{
}
List<string> list2 = new List<string>();
HashSet<string> hashSet = new HashSet<string>();
foreach (string item in list)
{
if (string.IsNullOrEmpty(item))
{
continue;
}
string fullPath;
try
{
fullPath = Path.GetFullPath(item);
}
catch
{
continue;
}
if (!hashSet.Add(fullPath) || !Directory.Exists(fullPath))
{
continue;
}
string[] files = Directory.GetFiles(fullPath, "*.wav");
foreach (string text in files)
{
list2.Add(text);
if (string.Equals(Path.GetFileName(text), "poop.wav", StringComparison.OrdinalIgnoreCase))
{
try
{
_sfx = PoopAudio.LoadWav(text);
((MelonBase)this).LoggerInstance.Msg($"loaded {text} ({_sfx.length:0.00}s, {_sfx.channels}ch, {_sfx.frequency}hz)");
return;
}
catch (Exception ex)
{
((MelonBase)this).LoggerInstance.Error("found " + text + " but couldnt read it: " + ex.Message);
}
}
}
}
((MelonBase)this).LoggerInstance.Warning("no poop.wav. folders checked:");
foreach (string item2 in hashSet)
{
((MelonBase)this).LoggerInstance.Warning(" " + item2);
}
if (list2.Count <= 0)
{
return;
}
((MelonBase)this).LoggerInstance.Warning("wavs i did see (rename one to poop.wav):");
foreach (string item3 in list2)
{
((MelonBase)this).LoggerInstance.Warning(" " + item3);
}
}
private void Squeeze()
{
//IL_0028: Unknown result type (might be due to invalid IL or missing references)
//IL_002d: Unknown result type (might be due to invalid IL or missing references)
//IL_0037: Unknown result type (might be due to invalid IL or missing references)
//IL_003c: Unknown result type (might be due to invalid IL or missing references)
//IL_0041: 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_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_005b: Unknown result type (might be due to invalid IL or missing references)
//IL_0060: 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_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_00aa: Unknown result type (might be due to invalid IL or missing references)
//IL_00af: Unknown result type (might be due to invalid IL or missing references)
//IL_00b4: Unknown result type (might be due to invalid IL or missing references)
//IL_00bc: Unknown result type (might be due to invalid IL or missing references)
//IL_00c6: Unknown result type (might be due to invalid IL or missing references)
//IL_00cb: Unknown result type (might be due to invalid IL or missing references)
//IL_00f6: Unknown result type (might be due to invalid IL or missing references)
//IL_00fc: Expected O, but got Unknown
//IL_010e: Unknown result type (might be due to invalid IL or missing references)
//IL_0133: Unknown result type (might be due to invalid IL or missing references)
//IL_0143: Unknown result type (might be due to invalid IL or missing references)
//IL_0153: Unknown result type (might be due to invalid IL or missing references)
//IL_01c8: Unknown result type (might be due to invalid IL or missing references)
//IL_01fc: Unknown result type (might be due to invalid IL or missing references)
//IL_0204: Unknown result type (might be due to invalid IL or missing references)
//IL_020e: Unknown result type (might be due to invalid IL or missing references)
//IL_0307: Unknown result type (might be due to invalid IL or missing references)
//IL_0308: 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_0294: Unknown result type (might be due to invalid IL or missing references)
//IL_02a4: Unknown result type (might be due to invalid IL or missing references)
FindButt();
if (!_built)
{
BuildStuff();
}
Vector3 val;
Vector3 val2;
if ((Object)(object)_butt != (Object)null)
{
val = _butt.position + Vector3.down * 0.15f;
val2 = Vector3.down * 3f + Random.insideUnitSphere * 0.4f;
}
else
{
Camera val3 = MainCam();
if ((Object)(object)val3 == (Object)null)
{
((MelonBase)this).LoggerInstance.Msg("no hip and no camera, nowhere to poop from");
return;
}
val = ((Component)val3).transform.position + ((Component)val3).transform.forward * 1.5f;
val2 = ((Component)val3).transform.forward * 4f;
((MelonBase)this).LoggerInstance.Msg("no rigidbody with '" + _bonePref.Value + "' in the name, pooping out of the camera instead");
}
GameObject val4 = new GameObject("Poop");
val4.layer = _layer;
val4.transform.position = val;
val4.transform.rotation = Quaternion.Euler(0f, Random.Range(0f, 360f), 0f);
val4.transform.localScale = Vector3.one * _scale.Value;
val4.AddComponent<MeshFilter>().sharedMesh = _poopMesh;
MeshRenderer val5 = val4.AddComponent<MeshRenderer>();
((Renderer)val5).sharedMaterial = _poopMat;
((Renderer)val5).shadowCastingMode = (ShadowCastingMode)1;
((Renderer)val5).receiveShadows = true;
CapsuleCollider val6 = val4.AddComponent<CapsuleCollider>();
val6.direction = 1;
val6.radius = 0.12f;
val6.height = 0.3f;
val6.center = new Vector3(0f, 0.15f, 0f);
Rigidbody val7 = val4.AddComponent<Rigidbody>();
val7.mass = 0.5f;
val7.drag = 0.1f;
val7.collisionDetectionMode = (CollisionDetectionMode)1;
val7.velocity = val2;
val7.angularVelocity = Random.insideUnitSphere * 6f;
Rigidbody[] body = _body;
for (int i = 0; i < body.Length; i++)
{
foreach (Collider componentsInChild in ((Component)body[i]).GetComponentsInChildren<Collider>())
{
Physics.IgnoreCollision((Collider)(object)val6, componentsInChild, true);
}
}
if (_launch.Value > 0f)
{
body = _body;
for (int i = 0; i < body.Length; i++)
{
body[i].AddForce(Vector3.up * _launch.Value, (ForceMode)2);
}
}
PoopAudio.Play(_sfx, 1f, 1f);
_turds.Add(new Turd
{
go = val4,
rb = val7,
col = (Collider)(object)val6,
mr = (Renderer)(object)val5,
born = Time.time,
lastVel = val2
});
if (_debugCube.Value)
{
SpawnTestCubes(val);
}
}
private void SpawnTestCubes(Vector3 at)
{
//IL_0023: Unknown result type (might be due to invalid IL or missing references)
//IL_0024: 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_0033: Unknown result type (might be due to invalid IL or missing references)
//IL_0038: Unknown result type (might be due to invalid IL or missing references)
//IL_0042: Unknown result type (might be due to invalid IL or missing references)
//IL_0047: Unknown result type (might be due to invalid IL or missing references)
//IL_0057: Unknown result type (might be due to invalid IL or missing references)
//IL_0061: Unknown result type (might be due to invalid IL or missing references)
//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
//IL_00b4: Unknown result type (might be due to invalid IL or missing references)
//IL_00b9: 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_00c8: 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)
//IL_00dd: Unknown result type (might be due to invalid IL or missing references)
//IL_00e7: Unknown result type (might be due to invalid IL or missing references)
GameObject obj = GameObject.CreatePrimitive((PrimitiveType)3);
((Object)obj).name = "PoopTestCube_MyMaterial";
obj.layer = _layer;
obj.transform.position = at + Vector3.up * 1.2f + Vector3.left * 0.4f;
obj.transform.localScale = Vector3.one * 0.35f;
obj.GetComponent<Renderer>().sharedMaterial = _poopMat;
Object.Destroy((Object)(object)obj, 6f);
GameObject obj2 = GameObject.CreatePrimitive((PrimitiveType)3);
((Object)obj2).name = "PoopTestCube_UnityMaterial";
obj2.layer = _layer;
obj2.transform.position = at + Vector3.up * 1.2f + Vector3.right * 0.4f;
obj2.transform.localScale = Vector3.one * 0.35f;
Object.Destroy((Object)(object)obj2, 6f);
Material sharedMaterial = obj2.GetComponent<Renderer>().sharedMaterial;
((MelonBase)this).LoggerInstance.Msg("test cubes up. unity's default material = " + (((Object)(object)sharedMaterial == (Object)null) ? "NULL" : (((Object)sharedMaterial).name + " / " + ((Object)sharedMaterial.shader).name)));
}
private void FindButt()
{
if ((Object)(object)_butt != (Object)null || Time.time < _nextButtSearch)
{
return;
}
_nextButtSearch = Time.time + 2f;
string value = _bonePref.Value.ToLowerInvariant();
List<Rigidbody> list = new List<Rigidbody>();
foreach (Rigidbody item in Object.FindObjectsOfType<Rigidbody>())
{
if (((Object)item).name.ToLowerInvariant().Contains(value))
{
list.Add(item);
}
}
if (list.Count != 0)
{
Rigidbody val = PickMine(list);
_butt = ((Component)val).transform;
_body = Ragdoll(val);
((MelonBase)this).LoggerInstance.Msg($"{list.Count} characters, using '{((Object)((Component)val).transform.root).name}' as me ({_body.Length} bodies)");
}
}
private Rigidbody PickMine(List<Rigidbody> hips)
{
int value = _actorIndex.Value;
if (value >= 0 && value < hips.Count)
{
((MelonBase)this).LoggerInstance.Msg($"ActorIndex forced to {value}");
return hips[value];
}
foreach (Rigidbody hip in hips)
{
if (LocalFlags.SaysLocal(((Component)hip).transform.root))
{
return hip;
}
}
Rigidbody val = null;
int num = int.MaxValue;
foreach (Rigidbody hip2 in hips)
{
PlayerInput val2 = null;
try
{
val2 = ((Component)hip2).GetComponentInParent<PlayerInput>();
}
catch
{
}
if (!((Object)(object)val2 == (Object)null) && val2.playerIndex < num)
{
num = val2.playerIndex;
val = hip2;
}
}
if ((Object)(object)val != (Object)null)
{
return val;
}
((MelonBase)this).LoggerInstance.Warning("couldnt tell which character is you, using the first one. set ActorIndex in the cfg to force it");
return hips[0];
}
private static Rigidbody[] Ragdoll(Rigidbody start)
{
Dictionary<int, Rigidbody> byId = new Dictionary<int, Rigidbody>();
Dictionary<int, List<int>> links = new Dictionary<int, List<int>>();
foreach (Joint item in Object.FindObjectsOfType<Joint>())
{
Rigidbody component = ((Component)item).GetComponent<Rigidbody>();
Rigidbody connectedBody = item.connectedBody;
if (!((Object)(object)component == (Object)null) && !((Object)(object)connectedBody == (Object)null))
{
Link(component, connectedBody);
Link(connectedBody, component);
}
}
HashSet<int> hashSet = new HashSet<int>();
Queue<int> queue = new Queue<int>();
List<Rigidbody> list = new List<Rigidbody>();
int instanceID = ((Object)start).GetInstanceID();
byId[instanceID] = start;
queue.Enqueue(instanceID);
hashSet.Add(instanceID);
while (queue.Count > 0)
{
int key = queue.Dequeue();
list.Add(byId[key]);
if (!links.TryGetValue(key, out var value))
{
continue;
}
foreach (int item2 in value)
{
if (hashSet.Add(item2))
{
queue.Enqueue(item2);
}
}
}
return list.ToArray();
void Link(Rigidbody a, Rigidbody b)
{
int instanceID2 = ((Object)a).GetInstanceID();
int instanceID3 = ((Object)b).GetInstanceID();
byId[instanceID2] = a;
byId[instanceID3] = b;
if (!links.TryGetValue(instanceID2, out var value2))
{
value2 = (links[instanceID2] = new List<int>());
}
value2.Add(instanceID3);
}
}
private static Camera MainCam()
{
Camera main = Camera.main;
if ((Object)(object)main != (Object)null && ((Behaviour)main).enabled)
{
return main;
}
Camera val = null;
foreach (Camera item in (Il2CppArrayBase<Camera>)(object)Camera.allCameras)
{
if (!((Object)(object)item == (Object)null) && ((Behaviour)item).enabled && !((Object)(object)item.targetTexture != (Object)null) && ((Object)(object)val == (Object)null || item.depth > val.depth))
{
val = item;
}
}
return val;
}
private int PickLayer()
{
//IL_00e1: Unknown result type (might be due to invalid IL or missing references)
//IL_00e6: Unknown result type (might be due to invalid IL or missing references)
//IL_00f0: Unknown result type (might be due to invalid IL or missing references)
//IL_00f5: Unknown result type (might be due to invalid IL or missing references)
//IL_00fa: Unknown result type (might be due to invalid IL or missing references)
//IL_00d4: Unknown result type (might be due to invalid IL or missing references)
//IL_00c7: Unknown result type (might be due to invalid IL or missing references)
if (_layerOverride.Value >= 0 && _layerOverride.Value < 32)
{
((MelonBase)this).LoggerInstance.Msg($"LayerOverride = {_layerOverride.Value} ({LayerMask.LayerToName(_layerOverride.Value)})");
return _layerOverride.Value;
}
Camera val = MainCam();
int num = (((Object)(object)val != (Object)null) ? val.cullingMask : (-1));
int num2 = -1;
RaycastHit val2 = default(RaycastHit);
if (Physics.Raycast((((Object)(object)_butt != (Object)null) ? _butt.position : (((Object)(object)val != (Object)null) ? ((Component)val).transform.position : Vector3.zero)) + Vector3.up * 0.5f, Vector3.down, ref val2, 30f, -1, (QueryTriggerInteraction)1))
{
num2 = ((Component)((RaycastHit)(ref val2)).collider).gameObject.layer;
}
int num3 = ((_body.Length != 0) ? ((Component)_body[0]).gameObject.layer : (-1));
int donorLayer = PoopLook.DonorLayer;
List<int> list = new List<int> { donorLayer, 0 };
for (int i = 1; i < 32; i++)
{
if (!list.Contains(i))
{
list.Add(i);
}
}
int num4 = 0;
int num5 = int.MinValue;
foreach (int item in list)
{
if ((num & (1 << item)) != 0)
{
int num6 = 0;
if (num2 >= 0 && !Physics.GetIgnoreLayerCollision(item, num2))
{
num6 += 2;
}
if (num3 >= 0 && !Physics.GetIgnoreLayerCollision(item, num3))
{
num6++;
}
if (num6 > num5)
{
num5 = num6;
num4 = item;
}
if (num6 == 3)
{
break;
}
}
}
((MelonBase)this).LoggerInstance.Msg($"camera '{(Object.op_Implicit((Object)(object)val) ? ((Object)val).name : "none")}' mask 0x{num:X8}, ground layer {num2}, actor layer {num3}, donor layer {donorLayer}");
((MelonBase)this).LoggerInstance.Msg($"poop goes on layer {num4} ({LayerMask.LayerToName(num4)}), camera draws it = {(num & (1 << num4)) != 0}");
if (num5 < 0)
{
((MelonBase)this).LoggerInstance.Warning("no layer is in the camera mask at all?! set LayerOverride manually");
}
return num4;
}
private void Diagnose(Turd t)
{
//IL_000c: 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_0028: 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_010f: Unknown result type (might be due to invalid IL or missing references)
//IL_0129: Unknown result type (might be due to invalid IL or missing references)
Camera val = MainCam();
Bounds bounds = t.mr.bounds;
float value = (((Object)(object)val != (Object)null) ? Vector3.Distance(((Component)val).transform.position, ((Bounds)(ref bounds)).center) : (-1f));
((MelonBase)this).LoggerInstance.Msg("---- visibility check ----");
((MelonBase)this).LoggerInstance.Msg($"renderer.isVisible = {t.mr.isVisible} enabled = {t.mr.enabled} layer = {t.go.layer} ({LayerMask.LayerToName(t.go.layer)})");
((MelonBase)this).LoggerInstance.Msg($"bounds centre {((Bounds)(ref bounds)).center} size {((Bounds)(ref bounds)).size} {value:0.0}m from camera '{(Object.op_Implicit((Object)(object)val) ? ((Object)val).name : "none")}'");
if ((Object)(object)val != (Object)null)
{
((MelonBase)this).LoggerInstance.Msg($"camera near/far {val.nearClipPlane}/{val.farClipPlane}, mask bit set = {(val.cullingMask & (1 << t.go.layer)) != 0}");
}
((MelonBase)this).LoggerInstance.Msg($"material '{((Object)t.mr.sharedMaterial).name}' shader '{((Object)t.mr.sharedMaterial.shader).name}' queue {t.mr.sharedMaterial.renderQueue} keywords [{PoopLook.Keywords(t.mr.sharedMaterial)}]");
((MelonBase)this).LoggerInstance.Msg("pipeline " + PoopLook.PipelineName + ". on URP the shader must start with 'Universal Render Pipeline/' or it only casts a shadow");
}
private void TickTurds()
{
//IL_00da: Unknown result type (might be due to invalid IL or missing references)
//IL_00df: Unknown result type (might be due to invalid IL or missing references)
//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
//IL_00f9: Unknown result type (might be due to invalid IL or missing references)
//IL_00fe: Unknown result type (might be due to invalid IL or missing references)
//IL_0103: 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)
//IL_0106: Unknown result type (might be due to invalid IL or missing references)
//IL_010b: Unknown result type (might be due to invalid IL or missing references)
//IL_0110: Unknown result type (might be due to invalid IL or missing references)
//IL_0122: Unknown result type (might be due to invalid IL or missing references)
//IL_0129: Unknown result type (might be due to invalid IL or missing references)
//IL_012e: Unknown result type (might be due to invalid IL or missing references)
//IL_0132: Unknown result type (might be due to invalid IL or missing references)
//IL_0145: Unknown result type (might be due to invalid IL or missing references)
//IL_014d: Unknown result type (might be due to invalid IL or missing references)
float time = Time.time;
for (int num = _turds.Count - 1; num >= 0; num--)
{
Turd turd = _turds[num];
if ((Object)(object)turd.go == (Object)null)
{
_turds.RemoveAt(num);
}
else
{
if (!_diagDone && time - turd.born > 0.5f)
{
_diagDone = true;
try
{
Diagnose(turd);
}
catch (Exception ex)
{
((MelonBase)this).LoggerInstance.Error("diag failed: " + ex.Message);
}
}
if (time - turd.born > _poopSecs.Value)
{
Object.Destroy((Object)(object)turd.go);
_turds.RemoveAt(num);
}
else if (!(time - turd.lastSplat < 0.2f))
{
Vector3 val = turd.go.transform.position + Vector3.up * 0.15f * _scale.Value;
Vector3 val2 = val - turd.lastSplatPos;
if (!(((Vector3)(ref val2)).sqrMagnitude < 0.0009f))
{
val2 = turd.rb.velocity;
if (!Poke(turd, val, ((Vector3)(ref val2)).normalized))
{
for (int i = 0; i < Feelers.Length && !Poke(turd, val, Feelers[i]); i++)
{
}
}
}
}
}
}
}
private bool Poke(Turd t, Vector3 from, Vector3 dir)
{
//IL_0022: 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_0068: Unknown result type (might be due to invalid IL or missing references)
//IL_007a: Unknown result type (might be due to invalid IL or missing references)
//IL_007b: Unknown result type (might be due to invalid IL or missing references)
if (((Vector3)(ref dir)).sqrMagnitude < 0.01f)
{
return false;
}
float num = 0.2f * _scale.Value;
RaycastHit hit = default(RaycastHit);
if (!Physics.Raycast(from, dir, ref hit, num, -1, (QueryTriggerInteraction)1))
{
return false;
}
if ((Object)(object)((RaycastHit)(ref hit)).collider == (Object)(object)t.col)
{
return false;
}
if (((Object)((Component)((RaycastHit)(ref hit)).collider).gameObject).name == "Poop")
{
return false;
}
Splat(hit);
t.lastSplat = Time.time;
t.lastSplatPos = from;
return true;
}
private void Splat(RaycastHit hit)
{
//IL_0005: Unknown result type (might be due to invalid IL or missing references)
//IL_000b: Expected O, but got Unknown
//IL_0058: Unknown result type (might be due to invalid IL or missing references)
//IL_005d: 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_007c: Unknown result type (might be due to invalid IL or missing references)
//IL_0075: Unknown result type (might be due to invalid IL or missing references)
//IL_0081: Unknown result type (might be due to invalid IL or missing references)
//IL_008a: Unknown result type (might be due to invalid IL or missing references)
//IL_008f: Unknown result type (might be due to invalid IL or missing references)
//IL_0095: Unknown result type (might be due to invalid IL or missing references)
//IL_009a: Unknown result type (might be due to invalid IL or missing references)
//IL_00aa: Unknown result type (might be due to invalid IL or missing references)
//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
//IL_00ac: 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_00cf: Unknown result type (might be due to invalid IL or missing references)
//IL_00fe: Unknown result type (might be due to invalid IL or missing references)
GameObject val = new GameObject("PoopSplat");
val.layer = _layer;
val.AddComponent<MeshFilter>().sharedMesh = _blobs[Random.Range(0, _blobs.Length)];
MeshRenderer obj = val.AddComponent<MeshRenderer>();
((Renderer)obj).sharedMaterial = _splatMat;
((Renderer)obj).shadowCastingMode = (ShadowCastingMode)0;
((Renderer)obj).receiveShadows = true;
Vector3 normal = ((RaycastHit)(ref hit)).normal;
Vector3 val2 = ((Mathf.Abs(Vector3.Dot(normal, Vector3.up)) > 0.95f) ? Vector3.forward : Vector3.up);
val.transform.position = ((RaycastHit)(ref hit)).point + normal * 0.008f;
val.transform.rotation = Quaternion.LookRotation(normal, val2) * Quaternion.Euler(0f, 0f, Random.Range(0f, 360f));
float num = Random.Range(0.35f, 0.6f) * _scale.Value;
val.transform.localScale = new Vector3(num, num, num);
val.transform.SetParent(((RaycastHit)(ref hit)).transform, true);
_stains.Add(new Stain
{
go = val,
dies = Time.time + _splatSecs.Value
});
}
private void TickStains()
{
//IL_008a: 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)
float time = Time.time;
for (int num = _stains.Count - 1; num >= 0; num--)
{
Stain stain = _stains[num];
if ((Object)(object)stain.go == (Object)null)
{
_stains.RemoveAt(num);
}
else
{
float num2 = stain.dies - time;
if (num2 <= 0f)
{
Object.Destroy((Object)(object)stain.go);
_stains.RemoveAt(num);
}
else if (num2 < 2f)
{
stain.go.transform.localScale = stain.go.transform.localScale * (1f - Time.deltaTime * 0.6f);
}
}
}
}
private void BuildStuff()
{
//IL_00bf: Unknown result type (might be due to invalid IL or missing references)
//IL_00c4: Unknown result type (might be due to invalid IL or missing references)
//IL_00c7: Unknown result type (might be due to invalid IL or missing references)
string value = "mesh";
try
{
if ((Object)(object)_poopMesh == (Object)null)
{
_poopMesh = PoopMesh.BuildSwirl();
}
if (_blobs == null)
{
_blobs = (Mesh[])(object)new Mesh[6];
for (int i = 0; i < _blobs.Length; i++)
{
_blobs[i] = PoopMesh.BuildBlob(i * 17 + 3);
}
}
Instance loggerInstance = ((MelonBase)this).LoggerInstance;
DefaultInterpolatedStringHandler defaultInterpolatedStringHandler = new DefaultInterpolatedStringHandler(28, 3);
defaultInterpolatedStringHandler.AppendLiteral("mesh ");
defaultInterpolatedStringHandler.AppendFormatted(_poopMesh.vertexCount);
defaultInterpolatedStringHandler.AppendLiteral(" verts / ");
defaultInterpolatedStringHandler.AppendFormatted(((Il2CppArrayBase<int>)(object)_poopMesh.triangles).Length / 3);
defaultInterpolatedStringHandler.AppendLiteral(" tris, bounds ");
Bounds bounds = _poopMesh.bounds;
defaultInterpolatedStringHandler.AppendFormatted<Vector3>(((Bounds)(ref bounds)).size);
loggerInstance.Msg(defaultInterpolatedStringHandler.ToStringAndClear());
value = "prefs";
PoopLook.ShaderOverride = ((_shaderOverride != null) ? (_shaderOverride.Value ?? "") : "");
PoopLook.Mode = ((_matMode != null) ? (_matMode.Value ?? "Auto") : "Auto");
((MelonBase)this).LoggerInstance.Msg($"render pipeline: {PoopLook.PipelineName} (urp = {PoopLook.IsUrp}), material mode {PoopLook.Mode}");
value = "poop material";
_poopMat = PoopLook.PoopMaterial();
if ((Object)(object)_poopMat == (Object)null)
{
throw new Exception("PoopMaterial returned null");
}
value = "splat material";
_splatMat = PoopLook.SplatMaterial();
if ((Object)(object)_splatMat == (Object)null)
{
throw new Exception("SplatMaterial returned null");
}
value = "layer";
_layer = PickLayer();
_built = true;
((MelonBase)this).LoggerInstance.Msg($"material shader '{((Object)_poopMat.shader).name}', {_poopMat.passCount} passes, keywords [{PoopLook.Keywords(_poopMat)}]");
}
catch (Exception ex)
{
((MelonBase)this).LoggerInstance.Error($"BuildStuff died at stage '{value}': {ex.GetType().Name}: {ex.Message}");
throw;
}
}
}
}