using System;
using System.CodeDom.Compiler;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Resources;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using System.Text;
using BepInEx;
using ChromaFlayer.Resources;
using HarmonyLib;
using KaimiraGames;
using Microsoft.CodeAnalysis;
using UnityEngine;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: AssemblyCompany("ChromaFlayer")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("Gives Mindflayers random colors")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("ChromaFlayer")]
[assembly: AssemblyTitle("ChromaFlayer")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
internal sealed class EmbeddedAttribute : Attribute
{
}
}
namespace System.Runtime.CompilerServices
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)]
internal sealed class NullableAttribute : Attribute
{
public readonly byte[] NullableFlags;
public NullableAttribute(byte P_0)
{
NullableFlags = new byte[1] { P_0 };
}
public NullableAttribute(byte[] P_0)
{
NullableFlags = P_0;
}
}
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)]
internal sealed class NullableContextAttribute : Attribute
{
public readonly byte Flag;
public NullableContextAttribute(byte P_0)
{
Flag = P_0;
}
}
[CompilerGenerated]
[Microsoft.CodeAnalysis.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 KaimiraGames
{
public class WeightedList<T> : IEnumerable<T>, IEnumerable
{
private readonly List<T> _list = new List<T>();
private readonly List<int> _weights = new List<int>();
private readonly List<int> _probabilities = new List<int>();
private readonly List<int> _alias = new List<int>();
private readonly Random _rand;
private int _totalWeight;
private bool _areAllProbabilitiesIdentical;
private int _minWeight;
private int _maxWeight;
public WeightErrorHandlingType BadWeightErrorHandling { get; set; }
public int TotalWeight => _totalWeight;
public int MinWeight => _minWeight;
public int MaxWeight => _maxWeight;
public IReadOnlyList<T> Items => _list.AsReadOnly();
public T this[int index] => _list[index];
public int Count => _list.Count;
public WeightedList(Random? rand = null)
{
_rand = rand ?? new Random();
}
public WeightedList(ICollection<WeightedListItem<T>> listItems, Random? rand = null)
{
_rand = rand ?? new Random();
foreach (WeightedListItem<T> listItem in listItems)
{
_list.Add(listItem._item);
_weights.Add(listItem._weight);
}
Recalculate();
}
public T? Next()
{
if (Count == 0)
{
return default(T);
}
int index = _rand.Next(Count);
if (_areAllProbabilitiesIdentical)
{
return _list[index];
}
if (_rand.Next(_totalWeight) >= _probabilities[index])
{
return _list[_alias[index]];
}
return _list[index];
}
public void AddWeightToAll(int weight)
{
if (weight + _minWeight <= 0 && BadWeightErrorHandling == WeightErrorHandlingType.ThrowExceptionOnAdd)
{
throw new ArgumentException($"Subtracting {-1 * weight} from all items would set weight to non-positive for at least one element.");
}
for (int i = 0; i < Count; i++)
{
_weights[i] = FixWeight(_weights[i] + weight);
}
Recalculate();
}
public void SubtractWeightFromAll(int weight)
{
AddWeightToAll(weight * -1);
}
public void SetWeightOfAll(int weight)
{
if (weight <= 0 && BadWeightErrorHandling == WeightErrorHandlingType.ThrowExceptionOnAdd)
{
throw new ArgumentException("Weight cannot be non-positive.");
}
for (int i = 0; i < Count; i++)
{
_weights[i] = FixWeight(weight);
}
Recalculate();
}
public IEnumerator<T> GetEnumerator()
{
return _list.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
return _list.GetEnumerator();
}
public void Add(T item, int weight)
{
_list.Add(item);
_weights.Add(FixWeight(weight));
Recalculate();
}
public void Add(ICollection<WeightedListItem<T>> listItems)
{
foreach (WeightedListItem<T> listItem in listItems)
{
_list.Add(listItem._item);
_weights.Add(FixWeight(listItem._weight));
}
Recalculate();
}
public void Clear()
{
_list.Clear();
_weights.Clear();
Recalculate();
}
public bool Contains(T item)
{
return _list.Contains(item);
}
public int IndexOf(T item)
{
return _list.IndexOf(item);
}
public void Insert(int index, T item, int weight)
{
_list.Insert(index, item);
_weights.Insert(index, FixWeight(weight));
Recalculate();
}
public void Remove(T item)
{
int index = IndexOf(item);
RemoveAt(index);
Recalculate();
}
public void RemoveAt(int index)
{
_list.RemoveAt(index);
_weights.RemoveAt(index);
Recalculate();
}
public void SetWeight(T item, int newWeight)
{
SetWeightAtIndex(IndexOf(item), FixWeight(newWeight));
}
public int GetWeightOf(T item)
{
return GetWeightAtIndex(IndexOf(item));
}
public void SetWeightAtIndex(int index, int newWeight)
{
_weights[index] = FixWeight(newWeight);
Recalculate();
}
public int GetWeightAtIndex(int index)
{
return _weights[index];
}
public override string ToString()
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.Append("WeightedList<");
stringBuilder.Append(typeof(T).Name);
stringBuilder.Append(">: TotalWeight:");
stringBuilder.Append(TotalWeight);
stringBuilder.Append(", Min:");
stringBuilder.Append(_minWeight);
stringBuilder.Append(", Max:");
stringBuilder.Append(_maxWeight);
stringBuilder.Append(", Count:");
stringBuilder.Append(Count);
stringBuilder.Append(", {");
for (int i = 0; i < _list.Count; i++)
{
T val = _list[i];
stringBuilder.Append((val != null) ? val.ToString() : null);
stringBuilder.Append(":");
stringBuilder.Append(_weights[i].ToString());
if (i < _list.Count - 1)
{
stringBuilder.Append(", ");
}
}
stringBuilder.Append("}");
return stringBuilder.ToString();
}
private void Recalculate()
{
_totalWeight = 0;
_areAllProbabilitiesIdentical = false;
_minWeight = 0;
_maxWeight = 0;
bool flag = true;
_alias.Clear();
_probabilities.Clear();
List<int> list = new List<int>(Count);
List<int> list2 = new List<int>(Count);
List<int> list3 = new List<int>(Count);
foreach (int weight in _weights)
{
if (flag)
{
_minWeight = (_maxWeight = weight);
flag = false;
}
_minWeight = ((weight < _minWeight) ? weight : _minWeight);
_maxWeight = ((_maxWeight < weight) ? weight : _maxWeight);
_totalWeight += weight;
list.Add(weight * Count);
_alias.Add(0);
_probabilities.Add(0);
}
if (_minWeight == _maxWeight)
{
_areAllProbabilitiesIdentical = true;
return;
}
for (int i = 0; i < Count; i++)
{
if (list[i] < _totalWeight)
{
list2.Add(i);
}
else
{
list3.Add(i);
}
}
while (list2.Count > 0 && list3.Count > 0)
{
int index = list2[list2.Count - 1];
list2.RemoveAt(list2.Count - 1);
int num = list3[list3.Count - 1];
list3.RemoveAt(list3.Count - 1);
_probabilities[index] = list[index];
_alias[index] = num;
int num3 = (list[num] = list[num] + list[index] - _totalWeight);
if (num3 < _totalWeight)
{
list2.Add(num);
}
else
{
list3.Add(num);
}
}
while (list3.Count > 0)
{
int index2 = list3[list3.Count - 1];
list3.RemoveAt(list3.Count - 1);
_probabilities[index2] = _totalWeight;
}
}
internal static int FixWeightSetToOne(int weight)
{
if (weight > 0)
{
return weight;
}
return 1;
}
internal static int FixWeightExceptionOnAdd(int weight)
{
if (weight > 0)
{
return weight;
}
throw new ArgumentException("Weight cannot be non-positive");
}
private int FixWeight(int weight)
{
if (BadWeightErrorHandling != WeightErrorHandlingType.ThrowExceptionOnAdd)
{
return FixWeightSetToOne(weight);
}
return FixWeightExceptionOnAdd(weight);
}
}
public readonly struct WeightedListItem<T>
{
internal readonly T _item;
internal readonly int _weight;
public WeightedListItem(T item, int weight)
{
_item = item;
_weight = weight;
}
}
public enum WeightErrorHandlingType
{
SetWeightToOne,
ThrowExceptionOnAdd
}
}
namespace ChromaFlayer
{
public class ColorUtils
{
public static Color HueShiftToColor(Color color, Color target, float amount)
{
//IL_0000: Unknown result type (might be due to invalid IL or missing references)
//IL_000c: Unknown result type (might be due to invalid IL or missing references)
//IL_0024: Unknown result type (might be due to invalid IL or missing references)
float num2 = default(float);
float num3 = default(float);
float num = default(float);
Color.RGBToHSV(color, ref num, ref num2, ref num3);
float num4 = default(float);
float num5 = default(float);
float num6 = default(float);
Color.RGBToHSV(target, ref num4, ref num5, ref num6);
num = Mathf.Lerp(num, num4, amount);
return Color.HSVToRGB(num, num2, num3);
}
}
[BepInPlugin("dev.zeddevstuff.chromaflayer", "ChromaFlayer", "1.0.0")]
public class Plugin : BaseUnityPlugin
{
private class Palette : IDisposable
{
private Texture2D _originalTexture;
private Dictionary<Color, float> _colors = new Dictionary<Color, float>();
private WeightedList<KeyValuePair<Texture2D, Color>> _textures = new WeightedList<KeyValuePair<Texture2D, Color>>();
private List<float> _probabilities = new List<float>();
public Palette(Texture2D originalTexture)
{
_originalTexture = originalTexture;
}
public (Texture2D texture, Color color) GetRandomCouple()
{
//IL_0015: Unknown result type (might be due to invalid IL or missing references)
KeyValuePair<Texture2D, Color> keyValuePair = _textures.Next();
return (keyValuePair.Key, keyValuePair.Value);
}
public Texture2D GetRandom()
{
return _textures.Next().Key;
}
public void GenerateTextures()
{
//IL_002f: Unknown result type (might be due to invalid IL or missing references)
//IL_0035: Expected O, but got Unknown
//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
//IL_00c0: Unknown result type (might be due to invalid IL or missing references)
//IL_0053: Unknown result type (might be due to invalid IL or missing references)
//IL_005a: Unknown result type (might be due to invalid IL or missing references)
//IL_0064: 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)
foreach (KeyValuePair<Color, float> color in _colors)
{
Texture2D val = new Texture2D(((Texture)_originalTexture).width, ((Texture)_originalTexture).height);
Color? val2 = null;
for (int i = 0; i < ((Texture)val).width; i++)
{
for (int j = 0; j < ((Texture)val).height; j++)
{
val.SetPixel(i, j, new Color?(ColorUtils.HueShiftToColor(_originalTexture.GetPixel(i, j), color.Key, 1f)).Value);
}
}
val.Apply();
_textures.Add(new KeyValuePair<Texture2D, Color>(val, color.Key), (int)(_colors[color.Key] * 100f));
}
}
public static Palette Parse(string data, Texture2D originalTexture)
{
//IL_0092: Unknown result type (might be due to invalid IL or missing references)
//IL_008b: 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_009c: Unknown result type (might be due to invalid IL or missing references)
Palette palette = new Palette(originalTexture);
string[] array = data.Split('\n');
float num = 0f;
string[] array2 = array;
Color val = default(Color);
for (int i = 0; i < array2.Length; i++)
{
string[] array3 = array2[i].Split('=');
if (array3.Length == 2)
{
string text = array3[0];
string[] array4 = array3[1].Split('/');
if (array4.Length == 2 && float.TryParse(array4[0], out var result) && float.TryParse(array4[1], out var result2))
{
float num2 = result / result2;
num += num2;
palette._probabilities.Add(num2);
Color key = (ColorUtility.TryParseHtmlString(text, ref val) ? val : Color.white);
palette._colors.TryAdd(key, num2);
}
}
}
palette._colors = palette._colors.OrderByDescending((KeyValuePair<Color, float> x) => x.Value).ToDictionary((KeyValuePair<Color, float> x) => x.Key, (KeyValuePair<Color, float> x) => x.Value);
return palette;
}
public void Dispose()
{
foreach (KeyValuePair<Texture2D, Color> texture in _textures)
{
Object.Destroy((Object)(object)texture.Key);
}
}
}
private class Patches
{
[HarmonyPatch(typeof(Mindflayer), "Awake")]
[HarmonyPostfix]
public static void Mindflayer_Awake(Mindflayer __instance)
{
SkinnedMeshRenderer componentInChildren = ((Component)__instance).GetComponentInChildren<SkinnedMeshRenderer>();
if (!((Object)(object)componentInChildren != (Object)null))
{
return;
}
string name = ((Object)((Renderer)componentInChildren).material.mainTexture).name;
if (!(name == "T-MindFlayer"))
{
if (name == "T-MindFlayer_M")
{
(Texture2D texture, Color color) couple2 = _malePalette.GetRandomCouple();
((Renderer)componentInChildren).material.mainTexture = (Texture)(object)couple2.texture;
((Component)__instance).GetComponentsInChildren<TrailRenderer>().ToList().ForEach(delegate(TrailRenderer x)
{
//IL_0007: 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_001d: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: Unknown result type (might be due to invalid IL or missing references)
x.startColor = couple2.color;
Color item4 = couple2.color;
item4.a = 0f;
x.endColor = item4;
});
((Component)__instance).GetComponentsInChildren<LineRenderer>().ToList().ForEach(delegate(LineRenderer x)
{
//IL_0007: 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_001d: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: Unknown result type (might be due to invalid IL or missing references)
x.startColor = couple2.color;
Color item3 = couple2.color;
item3.a = 0f;
x.endColor = item3;
});
((Component)__instance).GetComponentsInChildren<Light>().ToList().ForEach(delegate(Light x)
{
//IL_0007: Unknown result type (might be due to invalid IL or missing references)
x.color = couple2.color;
});
}
}
else
{
(Texture2D texture, Color color) couple = _femalePalette.GetRandomCouple();
((Renderer)componentInChildren).material.mainTexture = (Texture)(object)couple.texture;
((Component)__instance).GetComponentsInChildren<TrailRenderer>().ToList().ForEach(delegate(TrailRenderer x)
{
//IL_0007: 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_001d: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: Unknown result type (might be due to invalid IL or missing references)
x.startColor = couple.color;
Color item2 = couple.color;
item2.a = 0f;
x.endColor = item2;
});
((Component)__instance).GetComponentsInChildren<LineRenderer>().ToList().ForEach(delegate(LineRenderer x)
{
//IL_0007: 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_001d: Unknown result type (might be due to invalid IL or missing references)
//IL_002a: Unknown result type (might be due to invalid IL or missing references)
x.startColor = couple.color;
Color item = couple.color;
item.a = 0f;
x.endColor = item;
});
((Component)__instance).GetComponentsInChildren<Light>().ToList().ForEach(delegate(Light x)
{
//IL_0007: Unknown result type (might be due to invalid IL or missing references)
x.color = couple.color;
});
}
}
}
private Harmony _patch = new Harmony("dev.zeddevstuff.chromaflayer");
private static Texture2D? _t_MindFlayer;
private static Texture2D? _t_MindFlayer_M;
private static Palette? _malePalette;
private static Palette? _femalePalette;
private void Awake()
{
//IL_001f: Unknown result type (might be due to invalid IL or missing references)
//IL_0029: Expected O, but got Unknown
//IL_0043: Unknown result type (might be due to invalid IL or missing references)
//IL_004d: Expected O, but got Unknown
_patch.PatchAll(typeof(Patches));
_t_MindFlayer = new Texture2D(128, 128);
ImageConversion.LoadImage(_t_MindFlayer, AppResources.T_MindFlayer);
_t_MindFlayer_M = new Texture2D(128, 128);
ImageConversion.LoadImage(_t_MindFlayer_M, AppResources.T_MindFlayer_M);
LoadPalettes();
((BaseUnityPlugin)this).Logger.LogInfo((object)"Plugin ChromaFlayer is loaded!");
}
private void LoadPalettes()
{
DirectoryInfo directoryInfo = new DirectoryInfo(typeof(Mindflayer).Assembly.Location).Parent?.Parent?.Parent;
if (directoryInfo != null)
{
FileInfo fileInfo = directoryInfo.GetFiles("palette.chromaflayer", SearchOption.AllDirectories).FirstOrDefault();
FileInfo fileInfo2 = directoryInfo.GetFiles("malePalette.chromaflayer", SearchOption.AllDirectories).FirstOrDefault();
FileInfo fileInfo3 = directoryInfo.GetFiles("femalePalette.chromaflayer", SearchOption.AllDirectories).FirstOrDefault();
if (fileInfo2 != null)
{
_malePalette = Palette.Parse(File.ReadAllText(fileInfo2.FullName), _t_MindFlayer_M);
_malePalette.GenerateTextures();
}
if (fileInfo3 != null)
{
_femalePalette = Palette.Parse(File.ReadAllText(fileInfo3.FullName), _t_MindFlayer);
_femalePalette.GenerateTextures();
}
if (fileInfo != null && _malePalette == null)
{
_malePalette = Palette.Parse(File.ReadAllText(fileInfo.FullName), _t_MindFlayer_M);
_malePalette.GenerateTextures();
}
if (fileInfo != null && _femalePalette == null)
{
_femalePalette = Palette.Parse(File.ReadAllText(fileInfo.FullName), _t_MindFlayer);
_femalePalette.GenerateTextures();
}
if (fileInfo == null && fileInfo2 == null)
{
_malePalette = Palette.Parse(Encoding.UTF8.GetString(AppResources.Palette), _t_MindFlayer_M);
_malePalette.GenerateTextures();
}
if (fileInfo == null && fileInfo3 == null)
{
_femalePalette = Palette.Parse(Encoding.UTF8.GetString(AppResources.Palette), _t_MindFlayer);
_femalePalette.GenerateTextures();
}
}
}
}
public static class PluginInfo
{
public const string PLUGIN_GUID = "ChromaFlayer";
public const string PLUGIN_NAME = "ChromaFlayer";
public const string PLUGIN_VERSION = "1.0.0";
}
}
namespace ChromaFlayer.Resources
{
[GeneratedCode("System.Resources.Tools.StronglyTypedResourceBuilder", "17.0.0.0")]
[DebuggerNonUserCode]
[CompilerGenerated]
internal class AppResources
{
private static ResourceManager resourceMan;
private static CultureInfo resourceCulture;
[EditorBrowsable(EditorBrowsableState.Advanced)]
internal static ResourceManager ResourceManager
{
get
{
if (resourceMan == null)
{
resourceMan = new ResourceManager("ChromaFlayer.Resources.AppResources", typeof(AppResources).Assembly);
}
return resourceMan;
}
}
[EditorBrowsable(EditorBrowsableState.Advanced)]
internal static CultureInfo Culture
{
get
{
return resourceCulture;
}
set
{
resourceCulture = value;
}
}
internal static byte[] Palette => (byte[])ResourceManager.GetObject("Palette", resourceCulture);
internal static byte[] T_MindFlayer => (byte[])ResourceManager.GetObject("T-MindFlayer", resourceCulture);
internal static byte[] T_MindFlayer_M => (byte[])ResourceManager.GetObject("T-MindFlayer_M", resourceCulture);
internal AppResources()
{
}
}
}