Decompiled source of Hard Item Randomizer v1.0.6
plugins/Newtonsoft.Json.dll
Decompiled a day ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Concurrent; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Collections.Specialized; using System.ComponentModel; using System.Data; using System.Data.SqlTypes; using System.Diagnostics; using System.Diagnostics.CodeAnalysis; using System.Dynamic; using System.Globalization; using System.IO; using System.Linq; using System.Linq.Expressions; using System.Numerics; using System.Reflection; using System.Resources; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Serialization; using System.Runtime.Serialization.Formatters; using System.Runtime.Versioning; using System.Security; using System.Text; using System.Text.RegularExpressions; using System.Threading; using System.Threading.Tasks; using System.Xml; using System.Xml.Linq; using Microsoft.CodeAnalysis; using Newtonsoft.Json.Bson; using Newtonsoft.Json.Converters; using Newtonsoft.Json.Linq; using Newtonsoft.Json.Linq.JsonPath; using Newtonsoft.Json.Schema; using Newtonsoft.Json.Serialization; using Newtonsoft.Json.Utilities; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: AllowPartiallyTrustedCallers] [assembly: InternalsVisibleTo("Newtonsoft.Json.Schema, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f561df277c6c0b497d629032b410cdcf286e537c054724f7ffa0164345f62b3e642029d7a80cc351918955328c4adc8a048823ef90b0cf38ea7db0d729caf2b633c3babe08b0310198c1081995c19029bc675193744eab9d7345b8a67258ec17d112cebdbbb2a281487dceeafb9d83aa930f32103fbe1d2911425bc5744002c7")] [assembly: InternalsVisibleTo("Newtonsoft.Json.Tests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f561df277c6c0b497d629032b410cdcf286e537c054724f7ffa0164345f62b3e642029d7a80cc351918955328c4adc8a048823ef90b0cf38ea7db0d729caf2b633c3babe08b0310198c1081995c19029bc675193744eab9d7345b8a67258ec17d112cebdbbb2a281487dceeafb9d83aa930f32103fbe1d2911425bc5744002c7")] [assembly: InternalsVisibleTo("Newtonsoft.Json.Dynamic, PublicKey=0024000004800000940000000602000000240000525341310004000001000100cbd8d53b9d7de30f1f1278f636ec462cf9c254991291e66ebb157a885638a517887633b898ccbcf0d5c5ff7be85a6abe9e765d0ac7cd33c68dac67e7e64530e8222101109f154ab14a941c490ac155cd1d4fcba0fabb49016b4ef28593b015cab5937da31172f03f67d09edda404b88a60023f062ae71d0b2e4438b74cc11dc9")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("9ca358aa-317b-4925-8ada-4a29e943a363")] [assembly: CLSCompliant(true)] [assembly: TargetFramework(".NETStandard,Version=v2.0", FrameworkDisplayName = ".NET Standard 2.0")] [assembly: AssemblyCompany("Newtonsoft")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyCopyright("Copyright © James Newton-King 2008")] [assembly: AssemblyDescription("Json.NET is a popular high-performance JSON framework for .NET")] [assembly: AssemblyFileVersion("13.0.4.30916")] [assembly: AssemblyInformationalVersion("13.0.4+4e13299d4b0ec96bd4df9954ef646bd2d1b5bf2a")] [assembly: AssemblyProduct("Json.NET")] [assembly: AssemblyTitle("Json.NET .NET Standard 2.0")] [assembly: AssemblyMetadata("RepositoryUrl", "https://github.com/JamesNK/Newtonsoft.Json")] [assembly: NeutralResourcesLanguage("en-US")] [assembly: AssemblyVersion("13.0.0.0")] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class IsReadOnlyAttribute : Attribute { } [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; } } } namespace System.Diagnostics.CodeAnalysis { [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Interface | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, Inherited = false)] internal sealed class DynamicallyAccessedMembersAttribute : Attribute { public DynamicallyAccessedMemberTypes MemberTypes { get; } public DynamicallyAccessedMembersAttribute(DynamicallyAccessedMemberTypes memberTypes) { MemberTypes = memberTypes; } } [Flags] internal enum DynamicallyAccessedMemberTypes { None = 0, PublicParameterlessConstructor = 1, PublicConstructors = 3, NonPublicConstructors = 4, PublicMethods = 8, NonPublicMethods = 0x10, PublicFields = 0x20, NonPublicFields = 0x40, PublicNestedTypes = 0x80, NonPublicNestedTypes = 0x100, PublicProperties = 0x200, NonPublicProperties = 0x400, PublicEvents = 0x800, NonPublicEvents = 0x1000, Interfaces = 0x2000, All = -1 } [AttributeUsage(AttributeTargets.Property, Inherited = false, AllowMultiple = true)] internal sealed class FeatureGuardAttribute : Attribute { public Type FeatureType { get; } public FeatureGuardAttribute(Type featureType) { FeatureType = featureType; } } [AttributeUsage(AttributeTargets.Property, Inherited = false)] internal sealed class FeatureSwitchDefinitionAttribute : Attribute { public string SwitchName { get; } public FeatureSwitchDefinitionAttribute(string switchName) { SwitchName = switchName; } } [AttributeUsage(AttributeTargets.Method | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter | AttributeTargets.ReturnValue, AllowMultiple = true)] internal sealed class NotNullAttribute : Attribute { } [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false)] internal sealed class NotNullWhenAttribute : Attribute { public bool ReturnValue { get; } public NotNullWhenAttribute(bool returnValue) { ReturnValue = returnValue; } } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter | AttributeTargets.ReturnValue, Inherited = false)] internal sealed class MaybeNullAttribute : Attribute { } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, Inherited = false)] internal sealed class AllowNullAttribute : Attribute { } [AttributeUsage(AttributeTargets.Parameter, Inherited = false)] internal class DoesNotReturnIfAttribute : Attribute { public bool ParameterValue { get; } public DoesNotReturnIfAttribute(bool parameterValue) { ParameterValue = parameterValue; } } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Constructor | AttributeTargets.Method, Inherited = false)] internal sealed class RequiresDynamicCodeAttribute : Attribute { public string Message { get; } public string? Url { get; set; } public RequiresDynamicCodeAttribute(string message) { Message = message; } } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Constructor | AttributeTargets.Method, Inherited = false)] internal sealed class RequiresUnreferencedCodeAttribute : Attribute { public string Message { get; } public string? Url { get; set; } public RequiresUnreferencedCodeAttribute(string message) { Message = message; } } [AttributeUsage(AttributeTargets.All, Inherited = false, AllowMultiple = true)] internal sealed class UnconditionalSuppressMessageAttribute : Attribute { public string Category { get; } public string CheckId { get; } public string? Scope { get; set; } public string? Target { get; set; } public string? MessageId { get; set; } public string? Justification { get; set; } public UnconditionalSuppressMessageAttribute(string category, string checkId) { Category = category; CheckId = checkId; } } } namespace Newtonsoft.Json { public enum ConstructorHandling { Default, AllowNonPublicDefaultConstructor } public enum DateFormatHandling { IsoDateFormat, MicrosoftDateFormat } public enum DateParseHandling { None, DateTime, DateTimeOffset } public enum DateTimeZoneHandling { Local, Utc, Unspecified, RoundtripKind } public class DefaultJsonNameTable : JsonNameTable { private class Entry { internal readonly string Value; internal readonly int HashCode; internal Entry Next; internal Entry(string value, int hashCode, Entry next) { Value = value; HashCode = hashCode; Next = next; } } private static readonly int HashCodeRandomizer; private int _count; private Entry[] _entries; private int _mask = 31; static DefaultJsonNameTable() { HashCodeRandomizer = Environment.TickCount; } public DefaultJsonNameTable() { _entries = new Entry[_mask + 1]; } public override string? Get(char[] key, int start, int length) { if (length == 0) { return string.Empty; } int num = length + HashCodeRandomizer; num += (num << 7) ^ key[start]; int num2 = start + length; for (int i = start + 1; i < num2; i++) { num += (num << 7) ^ key[i]; } num -= num >> 17; num -= num >> 11; num -= num >> 5; int num3 = Volatile.Read(ref _mask); int num4 = num & num3; for (Entry entry = _entries[num4]; entry != null; entry = entry.Next) { if (entry.HashCode == num && TextEquals(entry.Value, key, start, length)) { return entry.Value; } } return null; } public string Add(string key) { if (key == null) { throw new ArgumentNullException("key"); } int length = key.Length; if (length == 0) { return string.Empty; } int num = length + HashCodeRandomizer; for (int i = 0; i < key.Length; i++) { num += (num << 7) ^ key[i]; } num -= num >> 17; num -= num >> 11; num -= num >> 5; for (Entry entry = _entries[num & _mask]; entry != null; entry = entry.Next) { if (entry.HashCode == num && entry.Value.Equals(key, StringComparison.Ordinal)) { return entry.Value; } } return AddEntry(key, num); } private string AddEntry(string str, int hashCode) { int num = hashCode & _mask; Entry entry = new Entry(str, hashCode, _entries[num]); _entries[num] = entry; if (_count++ == _mask) { Grow(); } return entry.Value; } private void Grow() { Entry[] entries = _entries; int num = _mask * 2 + 1; Entry[] array = new Entry[num + 1]; for (int i = 0; i < entries.Length; i++) { Entry entry = entries[i]; while (entry != null) { int num2 = entry.HashCode & num; Entry next = entry.Next; entry.Next = array[num2]; array[num2] = entry; entry = next; } } _entries = array; Volatile.Write(ref _mask, num); } private static bool TextEquals(string str1, char[] str2, int str2Start, int str2Length) { if (str1.Length != str2Length) { return false; } for (int i = 0; i < str1.Length; i++) { if (str1[i] != str2[str2Start + i]) { return false; } } return true; } } [Flags] public enum DefaultValueHandling { Include = 0, Ignore = 1, Populate = 2, IgnoreAndPopulate = 3 } public enum FloatFormatHandling { String, Symbol, DefaultValue } public enum FloatParseHandling { Double, Decimal } public enum Formatting { None, Indented } public interface IArrayPool<T> { T[] Rent(int minimumLength); void Return(T[]? array); } public interface IJsonLineInfo { int LineNumber { get; } int LinePosition { get; } bool HasLineInfo(); } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface, AllowMultiple = false)] public sealed class JsonArrayAttribute : JsonContainerAttribute { private bool _allowNullItems; public bool AllowNullItems { get { return _allowNullItems; } set { _allowNullItems = value; } } public JsonArrayAttribute() { } public JsonArrayAttribute(bool allowNullItems) { _allowNullItems = allowNullItems; } public JsonArrayAttribute(string id) : base(id) { } } [AttributeUsage(AttributeTargets.Constructor, AllowMultiple = false)] public sealed class JsonConstructorAttribute : Attribute { } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface, AllowMultiple = false)] public abstract class JsonContainerAttribute : Attribute { internal bool? _isReference; internal bool? _itemIsReference; internal ReferenceLoopHandling? _itemReferenceLoopHandling; internal TypeNameHandling? _itemTypeNameHandling; private Type? _namingStrategyType; private object[]? _namingStrategyParameters; public string? Id { get; set; } public string? Title { get; set; } public string? Description { get; set; } public Type? ItemConverterType { get; set; } public object[]? ItemConverterParameters { get; set; } public Type? NamingStrategyType { get { return _namingStrategyType; } set { _namingStrategyType = value; NamingStrategyInstance = null; } } public object[]? NamingStrategyParameters { get { return _namingStrategyParameters; } set { _namingStrategyParameters = value; NamingStrategyInstance = null; } } internal NamingStrategy? NamingStrategyInstance { get; set; } public bool IsReference { get { return _isReference.GetValueOrDefault(); } set { _isReference = value; } } public bool ItemIsReference { get { return _itemIsReference.GetValueOrDefault(); } set { _itemIsReference = value; } } public ReferenceLoopHandling ItemReferenceLoopHandling { get { return _itemReferenceLoopHandling.GetValueOrDefault(); } set { _itemReferenceLoopHandling = value; } } public TypeNameHandling ItemTypeNameHandling { get { return _itemTypeNameHandling.GetValueOrDefault(); } set { _itemTypeNameHandling = value; } } protected JsonContainerAttribute() { } protected JsonContainerAttribute(string id) { Id = id; } } public static class JsonConvert { public static readonly string True = "true"; public static readonly string False = "false"; public static readonly string Null = "null"; public static readonly string Undefined = "undefined"; public static readonly string PositiveInfinity = "Infinity"; public static readonly string NegativeInfinity = "-Infinity"; public static readonly string NaN = "NaN"; public static Func<JsonSerializerSettings>? DefaultSettings { get; set; } public static string ToString(DateTime value) { return ToString(value, DateFormatHandling.IsoDateFormat, DateTimeZoneHandling.RoundtripKind); } public static string ToString(DateTime value, DateFormatHandling format, DateTimeZoneHandling timeZoneHandling) { DateTime value2 = DateTimeUtils.EnsureDateTime(value, timeZoneHandling); using StringWriter stringWriter = StringUtils.CreateStringWriter(64); stringWriter.Write('"'); DateTimeUtils.WriteDateTimeString(stringWriter, value2, format, null, CultureInfo.InvariantCulture); stringWriter.Write('"'); return stringWriter.ToString(); } public static string ToString(DateTimeOffset value) { return ToString(value, DateFormatHandling.IsoDateFormat); } public static string ToString(DateTimeOffset value, DateFormatHandling format) { using StringWriter stringWriter = StringUtils.CreateStringWriter(64); stringWriter.Write('"'); DateTimeUtils.WriteDateTimeOffsetString(stringWriter, value, format, null, CultureInfo.InvariantCulture); stringWriter.Write('"'); return stringWriter.ToString(); } public static string ToString(bool value) { if (!value) { return False; } return True; } public static string ToString(char value) { return ToString(char.ToString(value)); } public static string ToString(Enum value) { return value.ToString("D"); } public static string ToString(int value) { return value.ToString(null, CultureInfo.InvariantCulture); } public static string ToString(short value) { return value.ToString(null, CultureInfo.InvariantCulture); } [CLSCompliant(false)] public static string ToString(ushort value) { return value.ToString(null, CultureInfo.InvariantCulture); } [CLSCompliant(false)] public static string ToString(uint value) { return value.ToString(null, CultureInfo.InvariantCulture); } public static string ToString(long value) { return value.ToString(null, CultureInfo.InvariantCulture); } private static string ToStringInternal(BigInteger value) { return value.ToString(null, CultureInfo.InvariantCulture); } [CLSCompliant(false)] public static string ToString(ulong value) { return value.ToString(null, CultureInfo.InvariantCulture); } public static string ToString(float value) { return EnsureDecimalPlace(value, value.ToString("R", CultureInfo.InvariantCulture)); } internal static string ToString(float value, FloatFormatHandling floatFormatHandling, char quoteChar, bool nullable) { return EnsureFloatFormat(value, EnsureDecimalPlace(value, value.ToString("R", CultureInfo.InvariantCulture)), floatFormatHandling, quoteChar, nullable); } private static string EnsureFloatFormat(double value, string text, FloatFormatHandling floatFormatHandling, char quoteChar, bool nullable) { if (floatFormatHandling == FloatFormatHandling.Symbol || (!double.IsInfinity(value) && !double.IsNaN(value))) { return text; } if (floatFormatHandling == FloatFormatHandling.DefaultValue) { if (nullable) { return Null; } return "0.0"; } return quoteChar + text + quoteChar; } public static string ToString(double value) { return EnsureDecimalPlace(value, value.ToString("R", CultureInfo.InvariantCulture)); } internal static string ToString(double value, FloatFormatHandling floatFormatHandling, char quoteChar, bool nullable) { return EnsureFloatFormat(value, EnsureDecimalPlace(value, value.ToString("R", CultureInfo.InvariantCulture)), floatFormatHandling, quoteChar, nullable); } private static string EnsureDecimalPlace(double value, string text) { if (double.IsNaN(value) || double.IsInfinity(value) || StringUtils.IndexOf(text, '.') != -1 || StringUtils.IndexOf(text, 'E') != -1 || StringUtils.IndexOf(text, 'e') != -1) { return text; } return text + ".0"; } private static string EnsureDecimalPlace(string text) { if (StringUtils.IndexOf(text, '.') != -1) { return text; } return text + ".0"; } public static string ToString(byte value) { return value.ToString(null, CultureInfo.InvariantCulture); } [CLSCompliant(false)] public static string ToString(sbyte value) { return value.ToString(null, CultureInfo.InvariantCulture); } public static string ToString(decimal value) { return EnsureDecimalPlace(value.ToString(null, CultureInfo.InvariantCulture)); } public static string ToString(Guid value) { return ToString(value, '"'); } internal static string ToString(Guid value, char quoteChar) { string text = value.ToString("D", CultureInfo.InvariantCulture); string text2 = quoteChar.ToString(CultureInfo.InvariantCulture); return text2 + text + text2; } public static string ToString(TimeSpan value) { return ToString(value, '"'); } internal static string ToString(TimeSpan value, char quoteChar) { return ToString(value.ToString(), quoteChar); } public static string ToString(Uri? value) { if (value == null) { return Null; } return ToString(value, '"'); } internal static string ToString(Uri value, char quoteChar) { return ToString(value.OriginalString, quoteChar); } public static string ToString(string? value) { return ToString(value, '"'); } public static string ToString(string? value, char delimiter) { return ToString(value, delimiter, StringEscapeHandling.Default); } public static string ToString(string? value, char delimiter, StringEscapeHandling stringEscapeHandling) { if (delimiter != '"' && delimiter != '\'') { throw new ArgumentException("Delimiter must be a single or double quote.", "delimiter"); } return JavaScriptUtils.ToEscapedJavaScriptString(value, delimiter, appendDelimiters: true, stringEscapeHandling); } public static string ToString(object? value) { if (value == null) { return Null; } return ConvertUtils.GetTypeCode(value.GetType()) switch { PrimitiveTypeCode.String => ToString((string)value), PrimitiveTypeCode.Char => ToString((char)value), PrimitiveTypeCode.Boolean => ToString((bool)value), PrimitiveTypeCode.SByte => ToString((sbyte)value), PrimitiveTypeCode.Int16 => ToString((short)value), PrimitiveTypeCode.UInt16 => ToString((ushort)value), PrimitiveTypeCode.Int32 => ToString((int)value), PrimitiveTypeCode.Byte => ToString((byte)value), PrimitiveTypeCode.UInt32 => ToString((uint)value), PrimitiveTypeCode.Int64 => ToString((long)value), PrimitiveTypeCode.UInt64 => ToString((ulong)value), PrimitiveTypeCode.Single => ToString((float)value), PrimitiveTypeCode.Double => ToString((double)value), PrimitiveTypeCode.DateTime => ToString((DateTime)value), PrimitiveTypeCode.Decimal => ToString((decimal)value), PrimitiveTypeCode.DBNull => Null, PrimitiveTypeCode.DateTimeOffset => ToString((DateTimeOffset)value), PrimitiveTypeCode.Guid => ToString((Guid)value), PrimitiveTypeCode.Uri => ToString((Uri)value), PrimitiveTypeCode.TimeSpan => ToString((TimeSpan)value), PrimitiveTypeCode.BigInteger => ToStringInternal((BigInteger)value), _ => throw new ArgumentException("Unsupported type: {0}. Use the JsonSerializer class to get the object's JSON representation.".FormatWith(CultureInfo.InvariantCulture, value.GetType())), }; } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value) { return SerializeObject(value, (Type?)null, (JsonSerializerSettings?)null); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, Formatting formatting) { return SerializeObject(value, formatting, (JsonSerializerSettings?)null); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, params JsonConverter[] converters) { JsonSerializerSettings settings = ((converters != null && converters.Length != 0) ? new JsonSerializerSettings { Converters = converters } : null); return SerializeObject(value, null, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, Formatting formatting, params JsonConverter[] converters) { JsonSerializerSettings settings = ((converters != null && converters.Length != 0) ? new JsonSerializerSettings { Converters = converters } : null); return SerializeObject(value, null, formatting, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, JsonSerializerSettings? settings) { return SerializeObject(value, null, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, Type? type, JsonSerializerSettings? settings) { JsonSerializer jsonSerializer = JsonSerializer.CreateDefault(settings); return SerializeObjectInternal(value, type, jsonSerializer); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, Formatting formatting, JsonSerializerSettings? settings) { return SerializeObject(value, null, formatting, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeObject(object? value, Type? type, Formatting formatting, JsonSerializerSettings? settings) { JsonSerializer jsonSerializer = JsonSerializer.CreateDefault(settings); jsonSerializer.Formatting = formatting; return SerializeObjectInternal(value, type, jsonSerializer); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] private static string SerializeObjectInternal(object? value, Type? type, JsonSerializer jsonSerializer) { StringWriter stringWriter = new StringWriter(new StringBuilder(256), CultureInfo.InvariantCulture); using (JsonTextWriter jsonTextWriter = new JsonTextWriter(stringWriter)) { jsonTextWriter.Formatting = jsonSerializer.Formatting; jsonSerializer.Serialize(jsonTextWriter, value, type); } return stringWriter.ToString(); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static object? DeserializeObject(string value) { return DeserializeObject(value, (Type?)null, (JsonSerializerSettings?)null); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static object? DeserializeObject(string value, JsonSerializerSettings settings) { return DeserializeObject(value, null, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static object? DeserializeObject(string value, Type type) { return DeserializeObject(value, type, (JsonSerializerSettings?)null); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static T? DeserializeObject<T>(string value) { return JsonConvert.DeserializeObject<T>(value, (JsonSerializerSettings?)null); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static T? DeserializeAnonymousType<T>(string value, T anonymousTypeObject) { return DeserializeObject<T>(value); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static T? DeserializeAnonymousType<T>(string value, T anonymousTypeObject, JsonSerializerSettings settings) { return DeserializeObject<T>(value, settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static T? DeserializeObject<T>(string value, params JsonConverter[] converters) { return (T)DeserializeObject(value, typeof(T), converters); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static T? DeserializeObject<T>(string value, JsonSerializerSettings? settings) { return (T)DeserializeObject(value, typeof(T), settings); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static object? DeserializeObject(string value, Type type, params JsonConverter[] converters) { JsonSerializerSettings settings = ((converters != null && converters.Length != 0) ? new JsonSerializerSettings { Converters = converters } : null); return DeserializeObject(value, type, settings); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static object? DeserializeObject(string value, Type? type, JsonSerializerSettings? settings) { ValidationUtils.ArgumentNotNull(value, "value"); JsonSerializer jsonSerializer = JsonSerializer.CreateDefault(settings); if (!jsonSerializer.IsCheckAdditionalContentSet()) { jsonSerializer.CheckAdditionalContent = true; } using JsonTextReader reader = new JsonTextReader(new StringReader(value)); return jsonSerializer.Deserialize(reader, type); } [DebuggerStepThrough] [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static void PopulateObject(string value, object target) { PopulateObject(value, target, null); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static void PopulateObject(string value, object target, JsonSerializerSettings? settings) { JsonSerializer jsonSerializer = JsonSerializer.CreateDefault(settings); using JsonReader jsonReader = new JsonTextReader(new StringReader(value)); jsonSerializer.Populate(jsonReader, target); if (settings == null || !settings.CheckAdditionalContent) { return; } while (jsonReader.Read()) { if (jsonReader.TokenType != JsonToken.Comment) { throw JsonSerializationException.Create(jsonReader, "Additional text found in JSON string after finishing deserializing object."); } } } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXmlNode(XmlNode? node) { return SerializeXmlNode(node, Formatting.None); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXmlNode(XmlNode? node, Formatting formatting) { XmlNodeConverter xmlNodeConverter = new XmlNodeConverter(); return SerializeObject(node, formatting, xmlNodeConverter); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXmlNode(XmlNode? node, Formatting formatting, bool omitRootObject) { XmlNodeConverter xmlNodeConverter = new XmlNodeConverter { OmitRootObject = omitRootObject }; return SerializeObject(node, formatting, xmlNodeConverter); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XmlDocument? DeserializeXmlNode(string value) { return DeserializeXmlNode(value, null); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XmlDocument? DeserializeXmlNode(string value, string? deserializeRootElementName) { return DeserializeXmlNode(value, deserializeRootElementName, writeArrayAttribute: false); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XmlDocument? DeserializeXmlNode(string value, string? deserializeRootElementName, bool writeArrayAttribute) { return DeserializeXmlNode(value, deserializeRootElementName, writeArrayAttribute, encodeSpecialCharacters: false); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XmlDocument? DeserializeXmlNode(string value, string? deserializeRootElementName, bool writeArrayAttribute, bool encodeSpecialCharacters) { XmlNodeConverter xmlNodeConverter = new XmlNodeConverter(); xmlNodeConverter.DeserializeRootElementName = deserializeRootElementName; xmlNodeConverter.WriteArrayAttribute = writeArrayAttribute; xmlNodeConverter.EncodeSpecialCharacters = encodeSpecialCharacters; return (XmlDocument)DeserializeObject(value, typeof(XmlDocument), xmlNodeConverter); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXNode(XObject? node) { return SerializeXNode(node, Formatting.None); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXNode(XObject? node, Formatting formatting) { return SerializeXNode(node, formatting, omitRootObject: false); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static string SerializeXNode(XObject? node, Formatting formatting, bool omitRootObject) { XmlNodeConverter xmlNodeConverter = new XmlNodeConverter { OmitRootObject = omitRootObject }; return SerializeObject(node, formatting, xmlNodeConverter); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XDocument? DeserializeXNode(string value) { return DeserializeXNode(value, null); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XDocument? DeserializeXNode(string value, string? deserializeRootElementName) { return DeserializeXNode(value, deserializeRootElementName, writeArrayAttribute: false); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XDocument? DeserializeXNode(string value, string? deserializeRootElementName, bool writeArrayAttribute) { return DeserializeXNode(value, deserializeRootElementName, writeArrayAttribute, encodeSpecialCharacters: false); } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public static XDocument? DeserializeXNode(string value, string? deserializeRootElementName, bool writeArrayAttribute, bool encodeSpecialCharacters) { XmlNodeConverter xmlNodeConverter = new XmlNodeConverter(); xmlNodeConverter.DeserializeRootElementName = deserializeRootElementName; xmlNodeConverter.WriteArrayAttribute = writeArrayAttribute; xmlNodeConverter.EncodeSpecialCharacters = encodeSpecialCharacters; return (XDocument)DeserializeObject(value, typeof(XDocument), xmlNodeConverter); } } public abstract class JsonConverter { public virtual bool CanRead => true; public virtual bool CanWrite => true; public abstract void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer); public abstract object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer); public abstract bool CanConvert(Type objectType); } public abstract class JsonConverter<T> : JsonConverter { public sealed override void WriteJson(JsonWriter writer, object? value, JsonSerializer serializer) { if (!((value != null) ? (value is T) : ReflectionUtils.IsNullable(typeof(T)))) { throw new JsonSerializationException("Converter cannot write specified value to JSON. {0} is required.".FormatWith(CultureInfo.InvariantCulture, typeof(T))); } WriteJson(writer, (T)value, serializer); } public abstract void WriteJson(JsonWriter writer, T? value, JsonSerializer serializer); public sealed override object? ReadJson(JsonReader reader, Type objectType, object? existingValue, JsonSerializer serializer) { bool flag = existingValue == null; if (!flag && !(existingValue is T)) { throw new JsonSerializationException("Converter cannot read JSON with the specified existing value. {0} is required.".FormatWith(CultureInfo.InvariantCulture, typeof(T))); } return ReadJson(reader, objectType, flag ? default(T) : ((T)existingValue), !flag, serializer); } public abstract T? ReadJson(JsonReader reader, Type objectType, T? existingValue, bool hasExistingValue, JsonSerializer serializer); public sealed override bool CanConvert(Type objectType) { return typeof(T).IsAssignableFrom(objectType); } } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Enum | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Interface | AttributeTargets.Parameter, AllowMultiple = false)] public sealed class JsonConverterAttribute : Attribute { private readonly Type _converterType; public Type ConverterType => _converterType; public object[]? ConverterParameters { get; } public JsonConverterAttribute(Type converterType) { if (converterType == null) { throw new ArgumentNullException("converterType"); } _converterType = converterType; } public JsonConverterAttribute(Type converterType, params object[] converterParameters) : this(converterType) { ConverterParameters = converterParameters; } } public class JsonConverterCollection : Collection<JsonConverter> { } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Interface, AllowMultiple = false)] public sealed class JsonDictionaryAttribute : JsonContainerAttribute { public JsonDictionaryAttribute() { } public JsonDictionaryAttribute(string id) : base(id) { } } [Serializable] public class JsonException : Exception { public JsonException() { } public JsonException(string message) : base(message) { } public JsonException(string message, Exception? innerException) : base(message, innerException) { } public JsonException(SerializationInfo info, StreamingContext context) : base(info, context) { } internal static JsonException Create(IJsonLineInfo lineInfo, string path, string message) { message = JsonPosition.FormatMessage(lineInfo, path, message); return new JsonException(message); } } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)] public class JsonExtensionDataAttribute : Attribute { public bool WriteData { get; set; } public bool ReadData { get; set; } public JsonExtensionDataAttribute() { WriteData = true; ReadData = true; } } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)] public sealed class JsonIgnoreAttribute : Attribute { } public abstract class JsonNameTable { public abstract string? Get(char[] key, int start, int length); } [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Interface, AllowMultiple = false)] public sealed class JsonObjectAttribute : JsonContainerAttribute { private MemberSerialization _memberSerialization; internal MissingMemberHandling? _missingMemberHandling; internal Required? _itemRequired; internal NullValueHandling? _itemNullValueHandling; public MemberSerialization MemberSerialization { get { return _memberSerialization; } set { _memberSerialization = value; } } public MissingMemberHandling MissingMemberHandling { get { return _missingMemberHandling.GetValueOrDefault(); } set { _missingMemberHandling = value; } } public NullValueHandling ItemNullValueHandling { get { return _itemNullValueHandling.GetValueOrDefault(); } set { _itemNullValueHandling = value; } } public Required ItemRequired { get { return _itemRequired.GetValueOrDefault(); } set { _itemRequired = value; } } public JsonObjectAttribute() { } public JsonObjectAttribute(MemberSerialization memberSerialization) { MemberSerialization = memberSerialization; } public JsonObjectAttribute(string id) : base(id) { } } internal enum JsonContainerType { None, Object, Array, Constructor } internal struct JsonPosition { private static readonly char[] SpecialCharacters = new char[18] { '.', ' ', '\'', '/', '"', '[', ']', '(', ')', '\t', '\n', '\r', '\f', '\b', '\\', '\u0085', '\u2028', '\u2029' }; internal JsonContainerType Type; internal int Position; internal string? PropertyName; internal bool HasIndex; public JsonPosition(JsonContainerType type) { Type = type; HasIndex = TypeHasIndex(type); Position = -1; PropertyName = null; } internal int CalculateLength() { switch (Type) { case JsonContainerType.Object: return PropertyName.Length + 5; case JsonContainerType.Array: case JsonContainerType.Constructor: return MathUtils.IntLength((ulong)Position) + 2; default: throw new ArgumentOutOfRangeException("Type"); } } internal void WriteTo(StringBuilder sb, ref StringWriter? writer, ref char[]? buffer) { switch (Type) { case JsonContainerType.Object: { string propertyName = PropertyName; if (propertyName.IndexOfAny(SpecialCharacters) != -1) { sb.Append("['"); if (writer == null) { writer = new StringWriter(sb); } JavaScriptUtils.WriteEscapedJavaScriptString(writer, propertyName, '\'', appendDelimiters: false, JavaScriptUtils.SingleQuoteCharEscapeFlags, StringEscapeHandling.Default, null, ref buffer); sb.Append("']"); } else { if (sb.Length > 0) { sb.Append('.'); } sb.Append(propertyName); } break; } case JsonContainerType.Array: case JsonContainerType.Constructor: sb.Append('['); sb.Append(Position); sb.Append(']'); break; } } internal static bool TypeHasIndex(JsonContainerType type) { if (type != JsonContainerType.Array) { return type == JsonContainerType.Constructor; } return true; } internal static string BuildPath(List<JsonPosition> positions, JsonPosition? currentPosition) { int num = 0; if (positions != null) { for (int i = 0; i < positions.Count; i++) { num += positions[i].CalculateLength(); } } if (currentPosition.HasValue) { num += currentPosition.GetValueOrDefault().CalculateLength(); } StringBuilder stringBuilder = new StringBuilder(num); StringWriter writer = null; char[] buffer = null; if (positions != null) { foreach (JsonPosition position in positions) { position.WriteTo(stringBuilder, ref writer, ref buffer); } } currentPosition?.WriteTo(stringBuilder, ref writer, ref buffer); return stringBuilder.ToString(); } internal static string FormatMessage(IJsonLineInfo? lineInfo, string path, string message) { if (!message.EndsWith(Environment.NewLine, StringComparison.Ordinal)) { message = message.Trim(); if (!StringUtils.EndsWith(message, '.')) { message += "."; } message += " "; } message += "Path '{0}'".FormatWith(CultureInfo.InvariantCulture, path); if (lineInfo != null && lineInfo.HasLineInfo()) { message += ", line {0}, position {1}".FormatWith(CultureInfo.InvariantCulture, lineInfo.LineNumber, lineInfo.LinePosition); } message += "."; return message; } } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Parameter, AllowMultiple = false)] public sealed class JsonPropertyAttribute : Attribute { internal NullValueHandling? _nullValueHandling; internal DefaultValueHandling? _defaultValueHandling; internal ReferenceLoopHandling? _referenceLoopHandling; internal ObjectCreationHandling? _objectCreationHandling; internal TypeNameHandling? _typeNameHandling; internal bool? _isReference; internal int? _order; internal Required? _required; internal bool? _itemIsReference; internal ReferenceLoopHandling? _itemReferenceLoopHandling; internal TypeNameHandling? _itemTypeNameHandling; public Type? ItemConverterType { get; set; } public object[]? ItemConverterParameters { get; set; } public Type? NamingStrategyType { get; set; } public object[]? NamingStrategyParameters { get; set; } public NullValueHandling NullValueHandling { get { return _nullValueHandling.GetValueOrDefault(); } set { _nullValueHandling = value; } } public DefaultValueHandling DefaultValueHandling { get { return _defaultValueHandling.GetValueOrDefault(); } set { _defaultValueHandling = value; } } public ReferenceLoopHandling ReferenceLoopHandling { get { return _referenceLoopHandling.GetValueOrDefault(); } set { _referenceLoopHandling = value; } } public ObjectCreationHandling ObjectCreationHandling { get { return _objectCreationHandling.GetValueOrDefault(); } set { _objectCreationHandling = value; } } public TypeNameHandling TypeNameHandling { get { return _typeNameHandling.GetValueOrDefault(); } set { _typeNameHandling = value; } } public bool IsReference { get { return _isReference.GetValueOrDefault(); } set { _isReference = value; } } public int Order { get { return _order.GetValueOrDefault(); } set { _order = value; } } public Required Required { get { return _required.GetValueOrDefault(); } set { _required = value; } } public string? PropertyName { get; set; } public ReferenceLoopHandling ItemReferenceLoopHandling { get { return _itemReferenceLoopHandling.GetValueOrDefault(); } set { _itemReferenceLoopHandling = value; } } public TypeNameHandling ItemTypeNameHandling { get { return _itemTypeNameHandling.GetValueOrDefault(); } set { _itemTypeNameHandling = value; } } public bool ItemIsReference { get { return _itemIsReference.GetValueOrDefault(); } set { _itemIsReference = value; } } public JsonPropertyAttribute() { } public JsonPropertyAttribute(string propertyName) { PropertyName = propertyName; } } public abstract class JsonReader : IDisposable { protected internal enum State { Start, Complete, Property, ObjectStart, Object, ArrayStart, Array, Closed, PostValue, ConstructorStart, Constructor, Error, Finished } private JsonToken _tokenType; private object? _value; internal char _quoteChar; internal State _currentState; private JsonPosition _currentPosition; private CultureInfo? _culture; private DateTimeZoneHandling _dateTimeZoneHandling; private int? _maxDepth; private bool _hasExceededMaxDepth; internal DateParseHandling _dateParseHandling; internal FloatParseHandling _floatParseHandling; private string? _dateFormatString; private List<JsonPosition>? _stack; protected State CurrentState => _currentState; public bool CloseInput { get; set; } public bool SupportMultipleContent { get; set; } public virtual char QuoteChar { get { return _quoteChar; } protected internal set { _quoteChar = value; } } public DateTimeZoneHandling DateTimeZoneHandling { get { return _dateTimeZoneHandling; } set { if (value < DateTimeZoneHandling.Local || value > DateTimeZoneHandling.RoundtripKind) { throw new ArgumentOutOfRangeException("value"); } _dateTimeZoneHandling = value; } } public DateParseHandling DateParseHandling { get { return _dateParseHandling; } set { if (value < DateParseHandling.None || value > DateParseHandling.DateTimeOffset) { throw new ArgumentOutOfRangeException("value"); } _dateParseHandling = value; } } public FloatParseHandling FloatParseHandling { get { return _floatParseHandling; } set { if (value < FloatParseHandling.Double || value > FloatParseHandling.Decimal) { throw new ArgumentOutOfRangeException("value"); } _floatParseHandling = value; } } public string? DateFormatString { get { return _dateFormatString; } set { _dateFormatString = value; } } public int? MaxDepth { get { return _maxDepth; } set { if (value <= 0) { throw new ArgumentException("Value must be positive.", "value"); } _maxDepth = value; } } public virtual JsonToken TokenType => _tokenType; public virtual object? Value => _value; public virtual Type? ValueType => _value?.GetType(); public virtual int Depth { get { int num = _stack?.Count ?? 0; if (JsonTokenUtils.IsStartToken(TokenType) || _currentPosition.Type == JsonContainerType.None) { return num; } return num + 1; } } public virtual string Path { get { if (_currentPosition.Type == JsonContainerType.None) { return string.Empty; } JsonPosition? currentPosition = ((_currentState != State.ArrayStart && _currentState != State.ConstructorStart && _currentState != State.ObjectStart) ? new JsonPosition?(_currentPosition) : null); return JsonPosition.BuildPath(_stack, currentPosition); } } public CultureInfo Culture { get { return _culture ?? CultureInfo.InvariantCulture; } set { _culture = value; } } public virtual Task<bool> ReadAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<bool>() ?? Read().ToAsync(); } public async Task SkipAsync(CancellationToken cancellationToken = default(CancellationToken)) { if (TokenType == JsonToken.PropertyName) { await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false); } if (JsonTokenUtils.IsStartToken(TokenType)) { int depth = Depth; while (await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false) && depth < Depth) { } } } internal async Task ReaderReadAndAssertAsync(CancellationToken cancellationToken) { if (!(await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false))) { throw CreateUnexpectedEndException(); } } public virtual Task<bool?> ReadAsBooleanAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<bool?>() ?? Task.FromResult(ReadAsBoolean()); } public virtual Task<byte[]?> ReadAsBytesAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<byte[]>() ?? Task.FromResult(ReadAsBytes()); } internal async Task<byte[]?> ReadArrayIntoByteArrayAsync(CancellationToken cancellationToken) { List<byte> buffer = new List<byte>(); do { if (!(await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false))) { SetToken(JsonToken.None); } } while (!ReadArrayElementIntoByteArrayReportDone(buffer)); byte[] array = buffer.ToArray(); SetToken(JsonToken.Bytes, array, updateIndex: false); return array; } public virtual Task<DateTime?> ReadAsDateTimeAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<DateTime?>() ?? Task.FromResult(ReadAsDateTime()); } public virtual Task<DateTimeOffset?> ReadAsDateTimeOffsetAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<DateTimeOffset?>() ?? Task.FromResult(ReadAsDateTimeOffset()); } public virtual Task<decimal?> ReadAsDecimalAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<decimal?>() ?? Task.FromResult(ReadAsDecimal()); } public virtual Task<double?> ReadAsDoubleAsync(CancellationToken cancellationToken = default(CancellationToken)) { return Task.FromResult(ReadAsDouble()); } public virtual Task<int?> ReadAsInt32Async(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<int?>() ?? Task.FromResult(ReadAsInt32()); } public virtual Task<string?> ReadAsStringAsync(CancellationToken cancellationToken = default(CancellationToken)) { return cancellationToken.CancelIfRequestedAsync<string>() ?? Task.FromResult(ReadAsString()); } internal async Task<bool> ReadAndMoveToContentAsync(CancellationToken cancellationToken) { bool flag = await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false); if (flag) { flag = await MoveToContentAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false); } return flag; } internal Task<bool> MoveToContentAsync(CancellationToken cancellationToken) { JsonToken tokenType = TokenType; if (tokenType == JsonToken.None || tokenType == JsonToken.Comment) { return MoveToContentFromNonContentAsync(cancellationToken); } return AsyncUtils.True; } private async Task<bool> MoveToContentFromNonContentAsync(CancellationToken cancellationToken) { JsonToken tokenType; do { if (!(await ReadAsync(cancellationToken).ConfigureAwait(continueOnCapturedContext: false))) { return false; } tokenType = TokenType; } while (tokenType == JsonToken.None || tokenType == JsonToken.Comment); return true; } internal JsonPosition GetPosition(int depth) { if (_stack != null && depth < _stack.Count) { return _stack[depth]; } return _currentPosition; } protected JsonReader() { _currentState = State.Start; _dateTimeZoneHandling = DateTimeZoneHandling.RoundtripKind; _dateParseHandling = DateParseHandling.DateTime; _floatParseHandling = FloatParseHandling.Double; _maxDepth = 64; CloseInput = true; } private void Push(JsonContainerType value) { UpdateScopeWithFinishedValue(); if (_currentPosition.Type == JsonContainerType.None) { _currentPosition = new JsonPosition(value); return; } if (_stack == null) { _stack = new List<JsonPosition>(); } _stack.Add(_currentPosition); _currentPosition = new JsonPosition(value); if (!_maxDepth.HasValue || !(Depth + 1 > _maxDepth) || _hasExceededMaxDepth) { return; } _hasExceededMaxDepth = true; throw JsonReaderException.Create(this, "The reader's MaxDepth of {0} has been exceeded.".FormatWith(CultureInfo.InvariantCulture, _maxDepth)); } private JsonContainerType Pop() { JsonPosition currentPosition; if (_stack != null && _stack.Count > 0) { currentPosition = _currentPosition; _currentPosition = _stack[_stack.Count - 1]; _stack.RemoveAt(_stack.Count - 1); } else { currentPosition = _currentPosition; _currentPosition = default(JsonPosition); } if (_maxDepth.HasValue && Depth <= _maxDepth) { _hasExceededMaxDepth = false; } return currentPosition.Type; } private JsonContainerType Peek() { return _currentPosition.Type; } public abstract bool Read(); public virtual int? ReadAsInt32() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Integer: case JsonToken.Float: { object value = Value; if (value is int) { return (int)value; } int num; if (value is BigInteger bigInteger) { num = (int)bigInteger; } else { try { num = Convert.ToInt32(value, CultureInfo.InvariantCulture); } catch (Exception ex) { throw JsonReaderException.Create(this, "Could not convert to integer: {0}.".FormatWith(CultureInfo.InvariantCulture, value), ex); } } SetToken(JsonToken.Integer, num, updateIndex: false); return num; } case JsonToken.String: { string s = (string)Value; return ReadInt32String(s); } default: throw JsonReaderException.Create(this, "Error reading integer. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal int? ReadInt32String(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (int.TryParse(s, NumberStyles.Integer, Culture, out var result)) { SetToken(JsonToken.Integer, result, updateIndex: false); return result; } SetToken(JsonToken.String, s, updateIndex: false); throw JsonReaderException.Create(this, "Could not convert string to integer: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } public virtual string? ReadAsString() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.String: return (string)Value; default: if (JsonTokenUtils.IsPrimitiveToken(contentToken)) { object value = Value; if (value != null) { string text = ((!(value is IFormattable formattable)) ? ((value is Uri uri) ? uri.OriginalString : value.ToString()) : formattable.ToString(null, Culture)); SetToken(JsonToken.String, text, updateIndex: false); return text; } } throw JsonReaderException.Create(this, "Error reading string. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } public virtual byte[]? ReadAsBytes() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.StartObject: { ReadIntoWrappedTypeObject(); byte[] array2 = ReadAsBytes(); ReaderReadAndAssert(); if (TokenType != JsonToken.EndObject) { throw JsonReaderException.Create(this, "Error reading bytes. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, TokenType)); } SetToken(JsonToken.Bytes, array2, updateIndex: false); return array2; } case JsonToken.String: { string text = (string)Value; Guid g; byte[] array3 = ((text.Length == 0) ? CollectionUtils.ArrayEmpty<byte>() : ((!ConvertUtils.TryConvertGuid(text, out g)) ? Convert.FromBase64String(text) : g.ToByteArray())); SetToken(JsonToken.Bytes, array3, updateIndex: false); return array3; } case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Bytes: if (Value is Guid guid) { byte[] array = guid.ToByteArray(); SetToken(JsonToken.Bytes, array, updateIndex: false); return array; } return (byte[])Value; case JsonToken.StartArray: return ReadArrayIntoByteArray(); default: throw JsonReaderException.Create(this, "Error reading bytes. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal byte[] ReadArrayIntoByteArray() { List<byte> list = new List<byte>(); do { if (!Read()) { SetToken(JsonToken.None); } } while (!ReadArrayElementIntoByteArrayReportDone(list)); byte[] array = list.ToArray(); SetToken(JsonToken.Bytes, array, updateIndex: false); return array; } private bool ReadArrayElementIntoByteArrayReportDone(List<byte> buffer) { switch (TokenType) { case JsonToken.None: throw JsonReaderException.Create(this, "Unexpected end when reading bytes."); case JsonToken.Integer: buffer.Add(Convert.ToByte(Value, CultureInfo.InvariantCulture)); return false; case JsonToken.EndArray: return true; case JsonToken.Comment: return false; default: throw JsonReaderException.Create(this, "Unexpected token when reading bytes: {0}.".FormatWith(CultureInfo.InvariantCulture, TokenType)); } } public virtual double? ReadAsDouble() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Integer: case JsonToken.Float: { object value = Value; if (value is double) { return (double)value; } double num = ((!(value is BigInteger bigInteger)) ? Convert.ToDouble(value, CultureInfo.InvariantCulture) : ((double)bigInteger)); SetToken(JsonToken.Float, num, updateIndex: false); return num; } case JsonToken.String: return ReadDoubleString((string)Value); default: throw JsonReaderException.Create(this, "Error reading double. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal double? ReadDoubleString(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (double.TryParse(s, NumberStyles.Float | NumberStyles.AllowThousands, Culture, out var result)) { SetToken(JsonToken.Float, result, updateIndex: false); return result; } SetToken(JsonToken.String, s, updateIndex: false); throw JsonReaderException.Create(this, "Could not convert string to double: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } public virtual bool? ReadAsBoolean() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Integer: case JsonToken.Float: { bool flag = ((!(Value is BigInteger bigInteger)) ? Convert.ToBoolean(Value, CultureInfo.InvariantCulture) : (bigInteger != 0L)); SetToken(JsonToken.Boolean, flag, updateIndex: false); return flag; } case JsonToken.String: return ReadBooleanString((string)Value); case JsonToken.Boolean: return (bool)Value; default: throw JsonReaderException.Create(this, "Error reading boolean. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal bool? ReadBooleanString(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (bool.TryParse(s, out var result)) { SetToken(JsonToken.Boolean, result, updateIndex: false); return result; } SetToken(JsonToken.String, s, updateIndex: false); throw JsonReaderException.Create(this, "Could not convert string to boolean: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } public virtual decimal? ReadAsDecimal() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Integer: case JsonToken.Float: { object value = Value; if (value is decimal) { return (decimal)value; } decimal num; if (value is BigInteger bigInteger) { num = (decimal)bigInteger; } else { try { num = Convert.ToDecimal(value, CultureInfo.InvariantCulture); } catch (Exception ex) { throw JsonReaderException.Create(this, "Could not convert to decimal: {0}.".FormatWith(CultureInfo.InvariantCulture, value), ex); } } SetToken(JsonToken.Float, num, updateIndex: false); return num; } case JsonToken.String: return ReadDecimalString((string)Value); default: throw JsonReaderException.Create(this, "Error reading decimal. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal decimal? ReadDecimalString(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (decimal.TryParse(s, NumberStyles.Number, Culture, out var result)) { SetToken(JsonToken.Float, result, updateIndex: false); return result; } if (ConvertUtils.DecimalTryParse(s.ToCharArray(), 0, s.Length, out result) == ParseResult.Success) { SetToken(JsonToken.Float, result, updateIndex: false); return result; } SetToken(JsonToken.String, s, updateIndex: false); throw JsonReaderException.Create(this, "Could not convert string to decimal: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } public virtual DateTime? ReadAsDateTime() { switch (GetContentToken()) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Date: if (Value is DateTimeOffset dateTimeOffset) { SetToken(JsonToken.Date, dateTimeOffset.DateTime, updateIndex: false); } return (DateTime)Value; case JsonToken.String: return ReadDateTimeString((string)Value); default: throw JsonReaderException.Create(this, "Error reading date. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, TokenType)); } } internal DateTime? ReadDateTimeString(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (DateTimeUtils.TryParseDateTime(s, DateTimeZoneHandling, _dateFormatString, Culture, out var dt)) { dt = DateTimeUtils.EnsureDateTime(dt, DateTimeZoneHandling); SetToken(JsonToken.Date, dt, updateIndex: false); return dt; } if (DateTime.TryParse(s, Culture, DateTimeStyles.RoundtripKind, out dt)) { dt = DateTimeUtils.EnsureDateTime(dt, DateTimeZoneHandling); SetToken(JsonToken.Date, dt, updateIndex: false); return dt; } throw JsonReaderException.Create(this, "Could not convert string to DateTime: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } public virtual DateTimeOffset? ReadAsDateTimeOffset() { JsonToken contentToken = GetContentToken(); switch (contentToken) { case JsonToken.None: case JsonToken.Null: case JsonToken.EndArray: return null; case JsonToken.Date: if (Value is DateTime dateTime) { SetToken(JsonToken.Date, new DateTimeOffset(dateTime), updateIndex: false); } return (DateTimeOffset)Value; case JsonToken.String: { string s = (string)Value; return ReadDateTimeOffsetString(s); } default: throw JsonReaderException.Create(this, "Error reading date. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, contentToken)); } } internal DateTimeOffset? ReadDateTimeOffsetString(string? s) { if (StringUtils.IsNullOrEmpty(s)) { SetToken(JsonToken.Null, null, updateIndex: false); return null; } if (DateTimeUtils.TryParseDateTimeOffset(s, _dateFormatString, Culture, out var dt)) { SetToken(JsonToken.Date, dt, updateIndex: false); return dt; } if (DateTimeOffset.TryParse(s, Culture, DateTimeStyles.RoundtripKind, out dt)) { SetToken(JsonToken.Date, dt, updateIndex: false); return dt; } SetToken(JsonToken.String, s, updateIndex: false); throw JsonReaderException.Create(this, "Could not convert string to DateTimeOffset: {0}.".FormatWith(CultureInfo.InvariantCulture, s)); } internal void ReaderReadAndAssert() { if (!Read()) { throw CreateUnexpectedEndException(); } } internal JsonReaderException CreateUnexpectedEndException() { return JsonReaderException.Create(this, "Unexpected end when reading JSON."); } internal void ReadIntoWrappedTypeObject() { ReaderReadAndAssert(); if (Value != null && Value.ToString() == "$type") { ReaderReadAndAssert(); if (Value != null && Value.ToString().StartsWith("System.Byte[]", StringComparison.Ordinal)) { ReaderReadAndAssert(); if (Value.ToString() == "$value") { return; } } } throw JsonReaderException.Create(this, "Error reading bytes. Unexpected token: {0}.".FormatWith(CultureInfo.InvariantCulture, JsonToken.StartObject)); } public void Skip() { if (TokenType == JsonToken.PropertyName) { Read(); } if (JsonTokenUtils.IsStartToken(TokenType)) { int depth = Depth; while (Read() && depth < Depth) { } } } protected void SetToken(JsonToken newToken) { SetToken(newToken, null, updateIndex: true); } protected void SetToken(JsonToken newToken, object? value) { SetToken(newToken, value, updateIndex: true); } protected void SetToken(JsonToken newToken, object? value, bool updateIndex) { _tokenType = newToken; _value = value; switch (newToken) { case JsonToken.StartObject: _currentState = State.ObjectStart; Push(JsonContainerType.Object); break; case JsonToken.StartArray: _currentState = State.ArrayStart; Push(JsonContainerType.Array); break; case JsonToken.StartConstructor: _currentState = State.ConstructorStart; Push(JsonContainerType.Constructor); break; case JsonToken.EndObject: ValidateEnd(JsonToken.EndObject); break; case JsonToken.EndArray: ValidateEnd(JsonToken.EndArray); break; case JsonToken.EndConstructor: ValidateEnd(JsonToken.EndConstructor); break; case JsonToken.PropertyName: _currentState = State.Property; _currentPosition.PropertyName = (string)value; break; case JsonToken.Raw: case JsonToken.Integer: case JsonToken.Float: case JsonToken.String: case JsonToken.Boolean: case JsonToken.Null: case JsonToken.Undefined: case JsonToken.Date: case JsonToken.Bytes: SetPostValueState(updateIndex); break; case JsonToken.Comment: break; } } internal void SetPostValueState(bool updateIndex) { if (Peek() != 0 || SupportMultipleContent) { _currentState = State.PostValue; } else { SetFinished(); } if (updateIndex) { UpdateScopeWithFinishedValue(); } } private void UpdateScopeWithFinishedValue() { if (_currentPosition.HasIndex) { _currentPosition.Position++; } } private void ValidateEnd(JsonToken endToken) { JsonContainerType jsonContainerType = Pop(); if (GetTypeForCloseToken(endToken) != jsonContainerType) { throw JsonReaderException.Create(this, "JsonToken {0} is not valid for closing JsonType {1}.".FormatWith(CultureInfo.InvariantCulture, endToken, jsonContainerType)); } if (Peek() != 0 || SupportMultipleContent) { _currentState = State.PostValue; } else { SetFinished(); } } protected void SetStateBasedOnCurrent() { JsonContainerType jsonContainerType = Peek(); switch (jsonContainerType) { case JsonContainerType.Object: _currentState = State.Object; break; case JsonContainerType.Array: _currentState = State.Array; break; case JsonContainerType.Constructor: _currentState = State.Constructor; break; case JsonContainerType.None: SetFinished(); break; default: throw JsonReaderException.Create(this, "While setting the reader state back to current object an unexpected JsonType was encountered: {0}".FormatWith(CultureInfo.InvariantCulture, jsonContainerType)); } } private void SetFinished() { _currentState = ((!SupportMultipleContent) ? State.Finished : State.Start); } private JsonContainerType GetTypeForCloseToken(JsonToken token) { return token switch { JsonToken.EndObject => JsonContainerType.Object, JsonToken.EndArray => JsonContainerType.Array, JsonToken.EndConstructor => JsonContainerType.Constructor, _ => throw JsonReaderException.Create(this, "Not a valid close JsonToken: {0}".FormatWith(CultureInfo.InvariantCulture, token)), }; } void IDisposable.Dispose() { Dispose(disposing: true); GC.SuppressFinalize(this); } protected virtual void Dispose(bool disposing) { if (_currentState != State.Closed && disposing) { Close(); } } public virtual void Close() { _currentState = State.Closed; _tokenType = JsonToken.None; _value = null; } internal void ReadAndAssert() { if (!Read()) { throw JsonSerializationException.Create(this, "Unexpected end when reading JSON."); } } internal void ReadForTypeAndAssert(JsonContract? contract, bool hasConverter) { if (!ReadForType(contract, hasConverter)) { throw JsonSerializationException.Create(this, "Unexpected end when reading JSON."); } } internal bool ReadForType(JsonContract? contract, bool hasConverter) { if (hasConverter) { return Read(); } switch (contract?.InternalReadType ?? ReadType.Read) { case ReadType.Read: return ReadAndMoveToContent(); case ReadType.ReadAsInt32: ReadAsInt32(); break; case ReadType.ReadAsInt64: { bool result = ReadAndMoveToContent(); if (TokenType == JsonToken.Undefined) { throw JsonReaderException.Create(this, "An undefined token is not a valid {0}.".FormatWith(CultureInfo.InvariantCulture, contract?.UnderlyingType ?? typeof(long))); } return result; } case ReadType.ReadAsDecimal: ReadAsDecimal(); break; case ReadType.ReadAsDouble: ReadAsDouble(); break; case ReadType.ReadAsBytes: ReadAsBytes(); break; case ReadType.ReadAsBoolean: ReadAsBoolean(); break; case ReadType.ReadAsString: ReadAsString(); break; case ReadType.ReadAsDateTime: ReadAsDateTime(); break; case ReadType.ReadAsDateTimeOffset: ReadAsDateTimeOffset(); break; default: throw new ArgumentOutOfRangeException(); } return TokenType != JsonToken.None; } internal bool ReadAndMoveToContent() { if (Read()) { return MoveToContent(); } return false; } internal bool MoveToContent() { JsonToken tokenType = TokenType; while (tokenType == JsonToken.None || tokenType == JsonToken.Comment) { if (!Read()) { return false; } tokenType = TokenType; } return true; } private JsonToken GetContentToken() { JsonToken tokenType; do { if (!Read()) { SetToken(JsonToken.None); return JsonToken.None; } tokenType = TokenType; } while (tokenType == JsonToken.Comment); return tokenType; } } [Serializable] public class JsonReaderException : JsonException { public int LineNumber { get; } public int LinePosition { get; } public string? Path { get; } public JsonReaderException() { } public JsonReaderException(string message) : base(message) { } public JsonReaderException(string message, Exception innerException) : base(message, innerException) { } public JsonReaderException(SerializationInfo info, StreamingContext context) : base(info, context) { } public JsonReaderException(string message, string path, int lineNumber, int linePosition, Exception? innerException) : base(message, innerException) { Path = path; LineNumber = lineNumber; LinePosition = linePosition; } internal static JsonReaderException Create(JsonReader reader, string message) { return Create(reader, message, null); } internal static JsonReaderException Create(JsonReader reader, string message, Exception? ex) { return Create(reader as IJsonLineInfo, reader.Path, message, ex); } internal static JsonReaderException Create(IJsonLineInfo? lineInfo, string path, string message, Exception? ex) { message = JsonPosition.FormatMessage(lineInfo, path, message); int lineNumber; int linePosition; if (lineInfo != null && lineInfo.HasLineInfo()) { lineNumber = lineInfo.LineNumber; linePosition = lineInfo.LinePosition; } else { lineNumber = 0; linePosition = 0; } return new JsonReaderException(message, path, lineNumber, linePosition, ex); } } [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = false)] public sealed class JsonRequiredAttribute : Attribute { } [Serializable] public class JsonSerializationException : JsonException { public int LineNumber { get; } public int LinePosition { get; } public string? Path { get; } public JsonSerializationException() { } public JsonSerializationException(string message) : base(message) { } public JsonSerializationException(string message, Exception innerException) : base(message, innerException) { } public JsonSerializationException(SerializationInfo info, StreamingContext context) : base(info, context) { } public JsonSerializationException(string message, string path, int lineNumber, int linePosition, Exception? innerException) : base(message, innerException) { Path = path; LineNumber = lineNumber; LinePosition = linePosition; } internal static JsonSerializationException Create(JsonReader reader, string message) { return Create(reader, message, null); } internal static JsonSerializationException Create(JsonReader reader, string message, Exception? ex) { return Create(reader as IJsonLineInfo, reader.Path, message, ex); } internal static JsonSerializationException Create(IJsonLineInfo? lineInfo, string path, string message, Exception? ex) { message = JsonPosition.FormatMessage(lineInfo, path, message); int lineNumber; int linePosition; if (lineInfo != null && lineInfo.HasLineInfo()) { lineNumber = lineInfo.LineNumber; linePosition = lineInfo.LinePosition; } else { lineNumber = 0; linePosition = 0; } return new JsonSerializationException(message, path, lineNumber, linePosition, ex); } } [RequiresUnreferencedCode("Newtonsoft.Json relies on reflection over types that may be removed when trimming.")] [RequiresDynamicCode("Newtonsoft.Json relies on dynamically creating types that may not be available with Ahead of Time compilation.")] public class JsonSerializer { internal TypeNameHandling _typeNameHandling; internal TypeNameAssemblyFormatHandling _typeNameAssemblyFormatHandling; internal PreserveReferencesHandling _preserveReferencesHandling; internal ReferenceLoopHandling _referenceLoopHandling; internal MissingMemberHandling _missingMemberHandling; internal ObjectCreationHandling _objectCreationHandling; internal NullValueHandling _nullValueHandling; internal DefaultValueHandling _defaultValueHandling; internal ConstructorHandling _constructorHandling; internal MetadataPropertyHandling _metadataPropertyHandling; internal JsonConverterCollection? _converters; internal IContractResolver _contractResolver; internal ITraceWriter? _traceWriter; internal IEqualityComparer? _equalityComparer; internal ISerializationBinder _serializationBinder; internal StreamingContext _context; private IReferenceResolver? _referenceResolver; private Formatting? _formatting; private DateFormatHandling? _dateFormatHandling; private DateTimeZoneHandling? _dateTimeZoneHandling; private DateParseHandling? _dateParseHandling; private FloatFormatHandling? _floatFormatHandling; private FloatParseHandling? _floatParseHandling; private StringEscapeHandling? _stringEscapeHandling; private CultureInfo _culture; private int? _maxDepth; private bool _maxDepthSet; private bool? _checkAdditionalContent; private string? _dateFormatString; private bool _dateFormatStringSet; public virtual IReferenceResolver? ReferenceResolver { get { return GetReferenceResolver(); } set { if (value == null) { throw new ArgumentNullException("value", "Reference resolver cannot be null."); } _referenceResolver = value; } } [Obsolete("Binder is obsolete. Use SerializationBinder instead.")] public virtual SerializationBinder Binder { get { if (_serializationBinder is SerializationBinder result) { return result; } if (_serializationBinder is SerializationBinderAdapter serializationBinderAdapter) { return serializationBinderAdapter.SerializationBinder; } throw new InvalidOperationException("Cannot get SerializationBinder because an ISerializationBinder was previously set."); } set { if (value == null) { throw new ArgumentNullException("value", "Serialization binder cannot be null."); } _serializationBinder = (value as ISerializationBinder) ?? new SerializationBinderAdapter(value); } } public virtual ISerializationBinder SerializationBinder { get { return _serializationBinder; } set { if (value == null) { throw new ArgumentNullException("value", "Serialization binder cannot be null."); } _serializationBinder = value; } } public virtual ITraceWriter? TraceWriter { get { return _traceWriter; } set { _traceWriter = value; } } public virtual IEqualityComparer? EqualityComparer { get { return _equalityComparer; } set { _equalityComparer = value; } } public virtual TypeNameHandling TypeNameHandling { get { return _typeNameHandling; } set { if (value < TypeNameHandling.None || value > TypeNameHandling.Auto) { throw new ArgumentOutOfRangeException("value"); } _typeNameHandling = value; } } [Obsolete("TypeNameAssemblyFormat is obsolete. Use TypeNameAssemblyFormatHandling instead.")] public virtual FormatterAssemblyStyle TypeNameAssemblyFormat { get { return (FormatterAssemblyStyle)_typeNameAssemblyFormatHandling; } set { if (value < FormatterAssemblyStyle.Simple || value > FormatterAssemblyStyle.Full) { throw new ArgumentOutOfRangeException("value"); } _typeNameAssemblyFormatHandling = (TypeNameAssemblyFormatHandling)value; } } public virtual TypeNameAssemblyFormatHandling TypeNameAssemblyFormatHandling { get { return _typeNameAssemblyFormatHandling; } set { if (value < TypeNameAssemblyFormatHandling.Simple || value > TypeNameAssemblyFormatHandling.Full) { throw new ArgumentOutOfRangeException("value"); } _typeNameAssemblyFormatHandling = value; } } public virtual PreserveReferencesHandling PreserveReferencesHandling { get { return _preserveReferencesHandling; } set { if (value < PreserveReferencesHandling.None || value > PreserveReferencesHandling.All) { throw new ArgumentOutOfRangeException("value"); } _preserveReferencesHandling = value; } } public virtual ReferenceLoopHandling ReferenceLoopHandling { get { return _referenceLoopHandling; } set { if (value < ReferenceLoopHandling.Error || value > ReferenceLoopHandling.Serialize) { throw new ArgumentOutOfRangeException("value"); } _referenceLoopHandling = value; } } public virtual MissingMemberHandling MissingMemberHandling { get { return _missingMemberHandling; } set { if (value < MissingMemberHandling.Ignore || value > MissingMemberHandling.Error) { throw new ArgumentOutOfRangeException("value"); } _missingMemberHandling = value; } } public virtual NullValueHandling NullValueHandling { get { return _nullValueHandling; } set { if (value < NullValueHandling.Include || value > NullValueHandling.Ignore) { throw new ArgumentOutOfRangeException("value"); } _nullValueHandling = value; } } public virtual DefaultValueHandling DefaultValueHandling { get { return _defaultValueHandling; } set { if (value < DefaultValueHandling.Include || value > DefaultValueHandling.IgnoreAndPopulate) { throw new ArgumentOutOfRangeException("value"); } _defaultValueHandling = value; } } public virtual ObjectCreationHandling ObjectCreationHandling { get { return _objectCreationHandling; } set { if (value < ObjectCreationHandling.Auto || value > ObjectCreationHandling.Replace) { throw new ArgumentOutOfRangeException("value"); } _objectCreationHandling = value; } } public virtual ConstructorHandling ConstructorHandling { get { return _constructorHandling; } set { if (value < ConstructorHandling.Default || value > ConstructorHandling.AllowNonPublicDefaultConstructor) { throw new ArgumentOutOfRangeException("value"); } _constructorHandling = value; } } public virtual MetadataPropertyHandling MetadataPropertyHandling { get { return _metadataPropertyHandling; } set { if (value < MetadataPropertyHandling.Default || value > MetadataPropertyHandling.Ignore) { throw new ArgumentOutOfRangeException("value"); } _metadataPropertyHandling = value; } } public virtual JsonConverterCollection Converters { get { if (_converters == null) { _converters = new JsonConverterCollection(); } return _converters; } } public virtual IContractResolver ContractResolver { get { return _contractResolver; } set { _contractResolver = value ?? DefaultContractResolver.Instance; } } public virtual StreamingContext Context { get { return _context; } set { _context = value; } } public virtual Formatting Formatting { get { return _formatting.GetValueOrDefault(); } set { _formatting = value; } } public virtual DateFormatHandling DateFormatHandling { get { return _dateFormatHandling.GetValueOrDefault(); } set { _dateFormatHandling = value; } } public virtual DateTimeZoneHandling DateTimeZoneHandling { get { return _dateTimeZoneHandling.GetValueOrDefault(DateTimeZoneHandling.RoundtripKind); } set { _dateTimeZoneHandling = value; } } public virtual DateParseHandling DateParseHandling { get { return _dateParseHandling.GetValueOrDefault(DateParseHandling.DateTime); } set { _dateParseHandling = value; } } public virtual FloatParseHandling FloatParseHandling { get { return _floatParseHandling.GetValueOrDefault(); } set { _floatParseHandling = value; } } public virtual FloatFormatHandling FloatFormatHandling { get { return _floatFormatHandling.GetValueOrDefault(); } set { _floatFormatHandling = value; } } public virtual StringEscapeHandling StringEscapeHandling { get { return _stringEscapeHandling.GetValueOrDefault(); } set { _stringEscapeHandling = value; } } public virtual string DateFormatString { get { return _dateFormatString ?? "yyyy'-'MM'-'dd'T'HH':'mm':'ss.FFFFFFFK"; } set { _dateFormatString = value; _dateFormatStringSet = true; } } public virtual CultureInfo Culture { get { return _culture ?? JsonSerializerSettings.DefaultCulture; } set { _culture = value; } } public virtual int? MaxDepth { get { return _maxDepth; } set { if (value <= 0) { throw new ArgumentException("Value must be positive.", "value"); } _maxDepth = value; _maxDepthSet = true; } } public virtual bool CheckAdditionalContent { get { return _checkAdditionalContent.GetValueOrDefault(); } set { _checkAdditionalContent = value; } } public virtual event EventHandler<Newtonsoft.Json.Serialization.ErrorEventArgs>? Error; internal bool IsCheckAdditionalContentSet() { return _checkAdditionalContent.HasValue; } public JsonSerializer() { _referenceLoopHandling = ReferenceLoopHandling.Error; _missingMemberHandling = MissingMemberHandling.Ignore; _nullValueHandling = NullValueHandling.Include; _defaultValueHandling = DefaultValueHandling.Include; _objectCreationHandling = ObjectCreationHandling.Auto; _preserveReferencesHandling = PreserveReferencesHandling.None; _constructorHandling = ConstructorHandling.Default; _typeNameHandling = TypeNameHandling.None; _metadataPropertyHandling = MetadataPropertyHandling.Default; _context = JsonSerializerSettings.DefaultContext; _serializationBinder = DefaultSerializationBinder.Instance; _culture = JsonSerializerSettings.DefaultCulture; _contractResolver = DefaultContractResolver.Instance; } public static JsonSerializer Create() { return new JsonSerializer(); } public static JsonSerializer Create(JsonSerializerSettings? settings) { JsonSerializer jsonSerializer = Create(); if (settings != null) { ApplySerializerSettings(jsonSerializer, settings); } return jsonSerializer; } public static JsonSerializer CreateDefault() { return Create(JsonConvert.DefaultSettings?.Invoke()); } public static JsonSerializer CreateDefault(JsonSerializerSettings? settings) { JsonSerializer jsonSerializer = CreateDefault(); if (settings != null) { ApplySerializerSettings(jsonSerializer, settings); } return jsonSerializer; } private static void ApplySerializerSettings(JsonSerializer serializer, JsonSerializerSettings settings) { if (!CollectionUtils.IsNullOrEmpty(settings.Converters)) { for (int i = 0; i < settings.Converters.Count; i++) { serializer.Converters.Insert(i, settings.Converters[i]); } } if (settings._typeNameHandling.HasValue) { serializer.TypeNameHandling = settings.TypeNameHandling; } if (settings._metadataPropertyHandling.HasValue) { serializer.MetadataPropertyHandling = settings.MetadataPropertyHandling; } if (settings._typeNameAssemblyFormatHandling.HasValue) { serializer.TypeNameAssemblyFormatHandling = settings.TypeNameAssemblyFormatHandling; } if (settings._preserveReferencesHandling.HasValue) { serializer.PreserveReferencesHandling = settings.PreserveReferencesHandling; } if (settings._referenceLoopHandling.HasValue) { serializer.ReferenceLoopHandling = settings.ReferenceLoopHandling; } if (settings._missingMemberHandling.HasValue) { serializer.MissingMemberHandling = settings.MissingMemberHandling; } if (settings._objectCreationHandling.HasValue) { serializer.ObjectCreationHandling = settings.ObjectCreationHandling; } if (settings._nullValueHandling.HasValue) { serializer.NullValueHandling = settings.NullValueHandling; } if (settings._defaultValueHandling.HasValue) { serializer.DefaultValueHandling = settings.DefaultValueHandling; } if (settings._constructorHandling.HasValue) { serializer.ConstructorHandling = settings.ConstructorHandling; } if (settings._context.HasValue) { serializer.Context = settings.Context; } if (settings._checkAdditionalContent.HasValue) { serializer._checkAdditionalContent = settings._checkAdditionalContent; } if (settings.Error != null) { serializer.Error += settings.Error; } if (settings.ContractResolver != null) { serializer.ContractResolver = settings.ContractResolver; } if (settings.ReferenceResolverProvider != null) { serializer.ReferenceResolver = settings.ReferenceResolverProvider(); } if (settings.TraceWriter != null) { serializer.TraceWriter = settings.TraceWriter; } if (settings.EqualityComparer != null) { serializer.EqualityComparer = settings.EqualityComparer; } if (settings.SerializationBinder != null) { serializer.SerializationBinder = settings.SerializationBinder; } if (settings._formatting.HasValue) { serializer._formatting = settings._formatting; } if (settings._dateFormatHandling.HasValue) { serializer._dateFormatHandling = settings._dateFormatHandling; } if (settings._dateTimeZoneHandling.HasValue) { serializer._dateTimeZoneHandling = settings._dateTimeZoneHandling; } if (settings._dateParseHandling.HasValue) { serializer._dateParseHandling = settings._dateParseHandling; } if (settings._dateFormatStringSet) { serializer._dateFormatString = settings._dateFormatString; serializer._dateFormatStringSet = settings._dateFormatStringSet; } if (settings._floatFormatHandling.HasValue) { serializer._floatFormatHandling = settings._floatFormatHandling; } if (settings._floatParseHandling.HasValue) { serializer._floatParseHandling = settings._floatParseHandling; } if (settings._stringEscapeHandling.HasValue) { serializer._stringEscapeHandling = settings._stringEscapeHandling; } if (settings._culture != null) { serializer._culture = settings._culture; } if (settings._maxDepthSet) { serializer._maxDepth = settings._maxDepth; serializer._maxDepthSet = settings._maxDepthSet; } } [DebuggerStepThrough] public void Populate(TextReader reader, object target) { Populate(new JsonTextReader(reader), target); } [DebuggerStepThrough] public void Populate(JsonReader reader, object target) { PopulateInternal(reader, target); } internal virtual void PopulateInternal(JsonReader reader, object target) { ValidationUtils.ArgumentNotNull(reader, "reader"); ValidationUtils.ArgumentNotNull(target, "target"); SetupReader(reader, out CultureInfo previousCulture, out DateTimeZoneHandling? previousDateTimeZoneHandling, out DateParseHandling? previousDateParseHandling, out FloatParseHandling? previousFloatParseHandling, out int? previousMaxDepth, out string previousDateFormatString); TraceJsonReader traceJsonReader = ((TraceWriter != null && TraceWriter.LevelFilter >= TraceLevel.Verbose) ? CreateTraceJsonReader(reader) : null); new JsonSerializerInternalReader(this).Populate(traceJsonReader ?? reader, target); if (traceJsonReader != null) { TraceWriter.Trace(TraceLevel.Verbose, traceJsonReader.GetDeserializedJsonMessage(), null); } ResetReader(reader, previousCulture, previousDateTimeZoneHandling, previousDateParseHandling, previousFloatParseHandling, previousMaxDepth, previousDateFormatString); } [DebuggerStepThrough] public object? Deserialize(JsonReader reader) { return Deserialize(reader, null); } [DebuggerStepThrough] public object? Deserialize(TextReader reader, Type objectType) { return Deserialize(new JsonTextReader(reader), objectType); } [DebuggerStepThrough] public T? Deserialize<T>(JsonReader reader) { return (T)Deserialize(reader, typeof(T)); } [DebuggerStepThrough] public object? Deserialize(JsonReader reader, Type? objectType) { return DeserializeInternal(reader, objectType); } internal virtual object? DeserializeInternal(JsonReader reader, Type? objectType) { ValidationUtils.ArgumentNotNull(reader, "reader"); SetupReader(reader, out CultureInfo previousCulture, out DateTimeZoneHandling? previousDateTimeZoneHandling, out DateParseHandling? previousDateParseHandling, out FloatParseHandling? previousFloatParseHandling, out int? previousMaxDepth, out string previousDateFormatString); TraceJsonReader traceJsonReader = ((TraceWriter != null && TraceWriter.LevelFilter >= TraceLevel.Verbose) ? CreateTraceJsonReader(reader) : null); object? result = new JsonSerializerInternalReader(this).Deserialize(traceJsonReader ?? reader, objectType, CheckAdditionalContent); if (traceJsonReader != null) { TraceWriter.Trace(TraceLevel.Verbose, traceJsonReader.GetDeserializedJsonMessage(), null); } ResetReader(reader, previousCulture, previousDateTimeZoneHandling, previousDateParseHandling, previousFloatParseHandling, previousMaxDepth, previousDateFormatString); return result; } internal void SetupReader(JsonReader reader, out CultureInfo? previousCulture, out DateTimeZoneHandling? previousDateTimeZoneHandling, out DateParseHandling? previousDateParseHandling, out FloatParseHandling? previousFloatParseHandling, out int? previousMaxDepth, out string? previousDateFormatString) { if (_culture != null && !_culture.Equals(reader.Culture)) { previousCulture = reader.Culture; reader.Culture = _culture; } else { previousCulture = null; } if (_dateTimeZoneHandling.HasValue && reader.DateTimeZoneHandling != _dateTimeZoneHandling) { previousDateTimeZoneHandling
plugins/SilksongItemRandomizer.dll
Decompiled a day agousing System; using System.Collections; 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.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using GlobalEnums; using HarmonyLib; using Microsoft.CodeAnalysis; using Newtonsoft.Json; using SilksongItemRandomizer.Hazard; using UnityEngine; using UnityEngine.Events; using UnityEngine.SceneManagement; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("SilksongItemRandomizer")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("0.1.0.0")] [assembly: AssemblyInformationalVersion("0.1.0")] [assembly: AssemblyProduct("SilksongItemRandomizer")] [assembly: AssemblyTitle("SilksongItemRandomizer")] [assembly: AssemblyMetadata("RepositoryUrl", "https://github.com/YourGitHubUsername/SilksongItemRandomizer")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.1.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 BepInEx { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class BepInAutoPluginAttribute : Attribute { public BepInAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace BepInEx.Preloader.Core.Patching { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class PatcherAutoPluginAttribute : Attribute { public PatcherAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace SilksongItemRandomizer { [HarmonyPatch(typeof(HeroController), "SetBenchRespawn", new Type[] { typeof(RespawnMarker), typeof(string), typeof(int) })] public static class BenchRespawnPatch { [CompilerGenerated] private sealed class <DelayedCrestRefresh>d__3 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public HeroController hero; private object <currentCrestObj>5__1; private string <currentCrest>5__2; private float <last>5__3; private string <targetCrest>5__4; private MethodInfo <setEquippedMethod>5__5; private Exception <ex>5__6; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <DelayedCrestRefresh>d__3(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <currentCrestObj>5__1 = null; <currentCrest>5__2 = null; <targetCrest>5__4 = null; <setEquippedMethod>5__5 = null; <ex>5__6 = null; <>1__state = -2; } private bool MoveNext() { //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = (object)new WaitForSeconds(15f); <>1__state = 1; return true; case 1: <>1__state = -1; try { <currentCrestObj>5__1 = PlayerData.instance.CurrentCrestID; if (<currentCrestObj>5__1 == null) { return false; } <currentCrest>5__2 = <currentCrestObj>5__1.ToString(); if (string.IsNullOrEmpty(<currentCrest>5__2)) { return false; } if (_lastRefreshTime.TryGetValue(<currentCrest>5__2, out <last>5__3) && Time.time - <last>5__3 < 30f) { Plugin.Log.LogInfo((object)("纹章 " + <currentCrest>5__2 + " 在冷却期内,跳过刷新")); return false; } <targetCrest>5__4 = CrestRandomizer.GetMappedCrestName(<currentCrest>5__2); if (string.IsNullOrEmpty(<targetCrest>5__4)) { return false; } if (<currentCrest>5__2 != <targetCrest>5__4) { Plugin.Log.LogInfo((object)("延迟15秒后检测到纹章不一致: 当前=" + <currentCrest>5__2 + ", 目标=" + <targetCrest>5__4 + ",开始刷新")); <setEquippedMethod>5__5 = typeof(ToolItemManager).GetMethod("SetEquippedCrest", new Type[1] { typeof(string) }); if (<setEquippedMethod>5__5 != null) { <setEquippedMethod>5__5.Invoke(null, new object[1] { <targetCrest>5__4 }); } if ((Object)(object)hero != (Object)null) { hero.ResetAllCrestState(); } _lastRefreshTime[<currentCrest>5__2] = Time.time; Plugin.Log.LogInfo((object)("延迟刷新完成,当前装备: " + <targetCrest>5__4)); <setEquippedMethod>5__5 = null; } <currentCrestObj>5__1 = null; <currentCrest>5__2 = null; <targetCrest>5__4 = null; } catch (Exception ex) { <ex>5__6 = ex; Plugin.Log.LogError((object)$"DelayedCrestRefresh异常: {<ex>5__6}"); } return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } private static Dictionary<string, float> _lastRefreshTime = new Dictionary<string, float>(); private const float COOLDOWN = 30f; private static void Postfix(HeroController __instance) { try { if (!((Object)(object)__instance == (Object)null) && PlayerData.instance != null) { ((MonoBehaviour)__instance).StartCoroutine(DelayedCrestRefresh(__instance)); } } catch (Exception arg) { Plugin.Log.LogError((object)$"BenchRespawnPatch异常: {arg}"); } } [IteratorStateMachine(typeof(<DelayedCrestRefresh>d__3))] private static IEnumerator DelayedCrestRefresh(HeroController hero) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <DelayedCrestRefresh>d__3(0) { hero = hero }; } public static void ResetCooldown() { _lastRefreshTime.Clear(); Plugin.Log.LogInfo((object)"纹章刷新冷却已清空"); } } [HarmonyPatch(typeof(ToolCrest), "Unlock")] public static class CrestRandomizePatch { private static List<ToolCrest>? _allCrests; private static HashSet<int> _processedInstanceIds = new HashSet<int>(); public static List<ToolCrest>? CrestList => _allCrests; public static void Initialize() { _allCrests = Resources.FindObjectsOfTypeAll<ToolCrest>().ToList(); } public static void ResetProcessedIds() { _processedInstanceIds.Clear(); } [HarmonyPrefix] private static bool Prefix(ToolCrest __instance) { try { if (_processedInstanceIds.Contains(((Object)__instance).GetInstanceID())) { return true; } _processedInstanceIds.Add(((Object)__instance).GetInstanceID()); string name = __instance.name; string mappedCrestName = CrestRandomizer.GetMappedCrestName(name); if (string.IsNullOrEmpty(mappedCrestName)) { return true; } if (mappedCrestName == name) { Plugin.Log.LogInfo((object)("纹章 " + name + " 映射到自身,放行原解锁")); return true; } if (_allCrests == null || _allCrests.Count == 0) { Initialize(); } ToolCrest val = null; if (_allCrests != null) { foreach (ToolCrest allCrest in _allCrests) { if (allCrest.name == mappedCrestName) { val = allCrest; break; } } } if ((Object)(object)val == (Object)null) { Plugin.Log.LogWarning((object)("无法找到目标纹章 " + mappedCrestName + ",放行原解锁")); return true; } val.Unlock(); PlayerData instance = PlayerData.instance; if (instance != null && instance.CurrentCrestID == name) { typeof(ToolItemManager).GetMethod("SetEquippedCrest", new Type[1] { typeof(string) })?.Invoke(null, new object[1] { mappedCrestName }); } return false; } catch (Exception arg) { Plugin.Log.LogError((object)$"CrestRandomizePatch异常: {arg}"); return true; } } } public static class CrestRandomizer { private static Dictionary<string, string> _crestMappings = new Dictionary<string, string>(); private static List<ToolCrest>? _allCrests; private static string FilePath => Path.Combine(Paths.ConfigPath, "SilksongItemRandomizer", "crest_mappings.json"); public static List<ToolCrest>? CrestList => _allCrests; public static void Initialize() { _allCrests = Resources.FindObjectsOfTypeAll<ToolCrest>().ToList(); LoadMappings(); if (_allCrests.Count > 0 && _crestMappings.Count < _allCrests.Count) { Plugin.Log.LogInfo((object)$"映射不完整(现有 {_crestMappings.Count}/{_allCrests.Count}),重新生成完整映射"); GenerateAllMappings(); } Plugin.Log.LogInfo((object)$"纹章随机初始化完成,共 {_crestMappings.Count} 个映射"); } public static void ResetMappings() { _crestMappings.Clear(); if (File.Exists(FilePath)) { File.Delete(FilePath); } Plugin.Log.LogInfo((object)"纹章映射已重置"); } private static void LoadMappings() { try { if (File.Exists(FilePath)) { string text = File.ReadAllText(FilePath); _crestMappings = JsonConvert.DeserializeObject<Dictionary<string, string>>(text) ?? new Dictionary<string, string>(); } else { _crestMappings.Clear(); } } catch (Exception arg) { Plugin.Log.LogError((object)$"加载纹章映射失败: {arg}"); _crestMappings.Clear(); } } private static void SaveMappings() { try { string directoryName = Path.GetDirectoryName(FilePath); if (!Directory.Exists(directoryName)) { Directory.CreateDirectory(directoryName); } string contents = JsonConvert.SerializeObject((object)_crestMappings, (Formatting)1); File.WriteAllText(FilePath, contents); } catch (Exception arg) { Plugin.Log.LogError((object)$"保存纹章映射失败: {arg}"); } } private static void GenerateAllMappings() { if (_allCrests == null || _allCrests.Count == 0) { return; } int value = Plugin.RandomSeed.Value; Random rng = new Random(value); List<ToolCrest> source2 = _allCrests.OrderBy((ToolCrest x) => rng.Next()).ToList(); foreach (ToolCrest source in _allCrests) { List<ToolCrest> list = source2.Where((ToolCrest c) => c.name != source.name).ToList(); if (list.Count == 0) { _crestMappings[source.name] = source.name; continue; } int index = rng.Next(list.Count); string name = list[index].name; _crestMappings[source.name] = name; } SaveMappings(); Plugin.Log.LogInfo((object)$"已为所有 {_allCrests.Count} 个纹章预生成映射"); } public static string GetMappedCrestName(string sourceCrestName) { if (_crestMappings.TryGetValue(sourceCrestName, out string value)) { return value; } Plugin.Log.LogWarning((object)("警告:纹章 " + sourceCrestName + " 没有映射,返回自身")); return sourceCrestName; } } [HarmonyPatch(typeof(CurrencyObjectBase), "Collect")] public class CurrencyCollectPatch { private static int _consecutiveMisses; private const int PITY_THRESHOLD = 105; private static int _dropCount; private static bool _hasGivenKey; private const int KEY_GUARANTEE_MAX = 30; private static string keyName; private static int _silkSpearAttempts; private static bool _silkSpearGiven; private const int SILK_SPEAR_PITY = 200; private static SavedItem? _silkSpearItem; static CurrencyCollectPatch() { _consecutiveMisses = 0; _dropCount = 0; _hasGivenKey = false; keyName = "Simple Key"; _silkSpearAttempts = 0; _silkSpearGiven = false; SavedItem[] source = Resources.FindObjectsOfTypeAll<SavedItem>(); _silkSpearItem = ((IEnumerable<SavedItem>)source).FirstOrDefault((Func<SavedItem, bool>)((SavedItem item) => ((Object)item).name == "Silk Spear")); if ((Object)(object)_silkSpearItem == (Object)null) { Plugin.Log.LogWarning((object)"未找到丝矛物品(Silk Spear),丝矛200次保底将禁用。"); } } public static void ResetCounters() { _consecutiveMisses = 0; _dropCount = 0; _hasGivenKey = false; _silkSpearAttempts = 0; _silkSpearGiven = false; Plugin.Log.LogInfo((object)"货币保底计数器已重置"); } private static void Postfix(bool __result) { try { if (!__result) { return; } _dropCount++; _silkSpearAttempts++; if (!_hasGivenKey && _dropCount <= 30) { SavedItem val = ((IEnumerable<SavedItem>)Resources.FindObjectsOfTypeAll<SavedItem>()).FirstOrDefault((Func<SavedItem, bool>)((SavedItem item) => ((Object)item).name == keyName)); if ((Object)(object)val != (Object)null) { val.TryGet(false, true); Plugin.Log.LogInfo((object)$"钥匙保底触发(第{_dropCount}次)"); _hasGivenKey = true; } } if ((Object)(object)_silkSpearItem != (Object)null && !_silkSpearGiven && _silkSpearAttempts >= 200) { Plugin.Log.LogInfo((object)"丝矛保底触发"); if (_silkSpearItem.TryGet(false, true)) { Plugin.Log.LogInfo((object)"丝矛保底成功给予"); Plugin.ShowNotification("获得丝矛!"); _silkSpearGiven = true; } else { Plugin.Log.LogError((object)"丝矛保底失败"); _silkSpearGiven = true; } } else if (_consecutiveMisses >= 104 || ItemRandomizer.RandomChance(1f / 105f)) { SavedItem randomItem = ItemRandomizer.GetRandomItem(); if ((Object)(object)randomItem != (Object)null) { randomItem.TryGet(false, true); } _consecutiveMisses = 0; } else { _consecutiveMisses++; } } catch (Exception arg) { Plugin.Log.LogError((object)$"Exception in CurrencyCollectPatch: {arg}"); } } } public static class ItemRandomizer { private static List<SavedItem>? _allItems; private static Random? _rng; public static readonly HashSet<string> ExcludedNames = new HashSet<string> { "Steel Spines", "Common Spine", "Plasmium", "Sliver Bell", "Seared Organ", "Shredded Organ", "Skewered Organ", "Ragpelt" }; public static Random? Rng => _rng; public static void Initialize(int seed) { //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) SavedItem[] source = Resources.FindObjectsOfTypeAll<SavedItem>(); _allItems = source.Where((SavedItem item) => (item is CollectableItem || item is ToolBase || item is CollectableRelic) && !ExcludedNames.Contains(((Object)item).name)).ToList(); if (_allItems.Count == 0) { ManualLogSource log = Plugin.Log; Scene activeScene = SceneManager.GetActiveScene(); log.LogWarning((object)("No eligible items found! Current scene: " + ((Scene)(ref activeScene)).name)); } else { _rng = ((seed == 0) ? new Random() : new Random(seed)); } } public static SavedItem? GetRandomItem() { if (_allItems == null || _allItems.Count == 0 || _rng == null) { Plugin.Log.LogWarning((object)"GetRandomItem: _allItems or _rng is null"); return null; } for (int i = 0; i < 100; i++) { int index = _rng.Next(_allItems.Count); SavedItem val = _allItems[index]; if (!((Object)(object)val == (Object)null) && !ExcludedNames.Contains(((Object)val).name)) { return val; } } Plugin.Log.LogWarning((object)"GetRandomItem failed after 100 attempts, returning null"); return null; } public static bool RandomChance(float probability) { if (_rng == null) { return false; } return _rng.NextDouble() < (double)probability; } public static SavedItem? PeekRandomItem(Random rng) { if (_allItems == null || _allItems.Count == 0 || rng == null) { return null; } for (int i = 0; i < 100; i++) { int index = rng.Next(_allItems.Count); SavedItem val = _allItems[index]; if (!((Object)(object)val == (Object)null) && !ExcludedNames.Contains(((Object)val).name)) { return val; } } return null; } public static List<SavedItem> GetAllItems() { return _allItems; } } [HarmonyPatch(typeof(CollectableItemPickup), "DoPickupAction")] public class PickupPatch { private static readonly Dictionary<string, string> ToolToSkillField = new Dictionary<string, string> { { "Silk Spear", "hasNeedleThrow" }, { "Thread Sphere", "hasThreadSphere" }, { "Harpoon Dash", "hasHarpoonDash" }, { "Silk Charge", "hasSilkCharge" }, { "Silk Bomb", "hasSilkBomb" }, { "Silk Boss Needle", "hasSilkBossNeedle" }, { "Needolin", "hasNeedolin" }, { "Dash", "hasDash" }, { "Brolly", "hasBrolly" }, { "DoubleJump", "hasDoubleJump" }, { "Charge Slash", "hasChargeSlash" }, { "SuperJump", "hasSuperJump" }, { "Wall Jump", "hasWallJump" } }; private static void Prefix(CollectableItemPickup __instance, ref bool __runOriginal) { //IL_0084: 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_009b: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: 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) try { if (!__runOriginal || (Object)(object)__instance == (Object)null) { return; } SavedItem item = __instance.Item; if ((Object)(object)item == (Object)null || ItemRandomizer.ExcludedNames.Contains(((Object)item).name)) { return; } SavedItem randomItem = ItemRandomizer.GetRandomItem(); if ((Object)(object)randomItem == (Object)null) { return; } object[] array = new object[4]; Scene scene = ((Component)__instance).gameObject.scene; array[0] = ((Scene)(ref scene)).name; array[1] = ((Component)__instance).transform.position.x; array[2] = ((Component)__instance).transform.position.y; array[3] = ((Component)__instance).transform.position.z; string key = string.Format("{0}_{1:F1}_{2:F1}_{3:F1}", array); if (item is CollectableRelic || item is ToolItem) { Plugin.AddDestroyedPickupKey(key); Plugin.Log.LogInfo((object)("特殊点 " + ((Object)item).name + " 强制销毁,给予随机物品 " + ((Object)randomItem).name)); bool flag = false; ToolItem val = (ToolItem)(object)((randomItem is ToolItem) ? randomItem : null); if (val != null) { string skillFieldName = GetSkillFieldName(val.name); if (!string.IsNullOrEmpty(skillFieldName)) { PlayerData instance = PlayerData.instance; if (instance != null) { FieldInfo field = ((object)instance).GetType().GetField(skillFieldName, BindingFlags.Instance | BindingFlags.Public); if (field != null && field.FieldType == typeof(bool)) { field.SetValue(instance, true); flag = true; } } } try { MethodInfo methodInfo = typeof(ToolItem).GetMethod("Unlock", new Type[2] { typeof(Action), typeof(PopupFlags) }) ?? typeof(ToolItem).GetMethod("Unlock", Type.EmptyTypes); if (methodInfo != null) { if (methodInfo.GetParameters().Length == 0) { methodInfo.Invoke(val, null); } else { methodInfo.Invoke(val, new object[2] { null, (object)(PopupFlags)3 }); } flag = true; } else { Plugin.Log.LogError((object)"无法找到 ToolItem.Unlock 方法"); } } catch (Exception arg) { Plugin.Log.LogError((object)$"Unlock 调用失败: {arg}"); } } else { flag = randomItem.TryGet(false, true); } if (flag) { RecentItemsUI.AddItem(randomItem); Plugin.Log.LogInfo((object)("特殊点物品 " + ((Object)randomItem).name + " 给予成功")); } else { Plugin.Log.LogError((object)("特殊点物品 " + ((Object)randomItem).name + " 给予失败!")); } __runOriginal = false; Object.Destroy((Object)(object)((Component)__instance).gameObject); } else { Plugin.AddDestroyedPickupKey(key); Plugin.Log.LogInfo((object)("普通点 " + ((Object)item).name + " 强制销毁,给予随机物品 " + ((Object)randomItem).name)); if (randomItem.TryGet(false, true)) { RecentItemsUI.AddItem(randomItem); Plugin.Log.LogInfo((object)("普通点物品 " + ((Object)randomItem).name + " 给予成功")); } else { Plugin.Log.LogError((object)("普通点物品 " + ((Object)randomItem).name + " 给予失败!")); } __runOriginal = false; Object.Destroy((Object)(object)((Component)__instance).gameObject); } } catch (Exception arg2) { Plugin.Log.LogError((object)$"Exception in PickupPatch.Prefix: {arg2}"); } } private static string GetSkillFieldName(string toolName) { ToolToSkillField.TryGetValue(toolName, out string value); return value; } } [HarmonyPatch(typeof(ShopItemStats), "SetPurchased")] public static class ShopItemStats_Purchase_Patch { [CompilerGenerated] private sealed class <DelayedRebuild>d__2 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public ShopMenuStock shop; private MethodInfo <buildMethod>5__1; private Exception <ex>5__2; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <DelayedRebuild>d__2(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <buildMethod>5__1 = null; <ex>5__2 = null; <>1__state = -2; } private bool MoveNext() { switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; try { <buildMethod>5__1 = typeof(ShopMenuStock).GetMethod("BuildItemList", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (<buildMethod>5__1 != null) { <buildMethod>5__1.Invoke(shop, null); Plugin.Log.LogInfo((object)"商店重建完成"); } else { Plugin.Log.LogError((object)"未找到 BuildItemList 方法"); } <buildMethod>5__1 = null; } catch (Exception ex) { <ex>5__2 = ex; Plugin.Log.LogError((object)$"商店重建异常: {<ex>5__2}"); } return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } private static void Prefix() { try { ToolUnlockPatch.IsShopPurchase = true; } catch { } } private static void Postfix(ShopItemStats __instance) { try { ToolUnlockPatch.IsShopPurchase = false; if ((Object)(object)((__instance != null) ? __instance.Item : null) == (Object)null) { Plugin.Log.LogWarning((object)"购买实例或物品为空,跳过处理"); return; } string name = ((Object)__instance.Item).name; if (string.IsNullOrEmpty(name) || !name.Contains("_")) { Plugin.Log.LogWarning((object)("永久ID格式错误: " + name + ",仅隐藏物体")); ((Component)__instance).gameObject.SetActive(false); return; } ShopMenuStock_BuildItemList_Patch.SetCount(name, 0); ShopMenuStock componentInParent = ((Component)__instance).GetComponentInParent<ShopMenuStock>(); if ((Object)(object)componentInParent == (Object)null) { Plugin.Log.LogError((object)"无法获取 ShopMenuStock"); return; } ((Component)__instance).gameObject.SetActive(false); ((MonoBehaviour)componentInParent).StartCoroutine(DelayedRebuild(componentInParent)); Plugin.Log.LogInfo((object)("永久ID " + name + " 已购买,触发商店重建")); } catch (Exception arg) { Plugin.Log.LogError((object)$"购买后处理异常: {arg}"); if ((Object)(object)__instance != (Object)null) { ((Component)__instance).gameObject.SetActive(false); } } } [IteratorStateMachine(typeof(<DelayedRebuild>d__2))] private static IEnumerator DelayedRebuild(ShopMenuStock shop) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <DelayedRebuild>d__2(0) { shop = shop }; } } [HarmonyPatch(typeof(ShopMenuStock), "BuildItemList")] public static class ShopMenuStock_BuildItemList_Patch { private static Dictionary<string, int> _slotCounts = new Dictionary<string, int>(); private static string FilePath => Path.Combine(Paths.ConfigPath, "SilksongItemRandomizer", "shop_slots.json"); private static void LoadCounts() { try { if (File.Exists(FilePath)) { string text = File.ReadAllText(FilePath); _slotCounts = JsonConvert.DeserializeObject<Dictionary<string, int>>(text) ?? new Dictionary<string, int>(); } else { _slotCounts.Clear(); } } catch (Exception arg) { Plugin.Log.LogError((object)$"加载商店槽位计数失败: {arg}"); _slotCounts.Clear(); } } private static void SaveCounts() { try { string directoryName = Path.GetDirectoryName(FilePath); if (!Directory.Exists(directoryName)) { Directory.CreateDirectory(directoryName); } string contents = JsonConvert.SerializeObject((object)_slotCounts, (Formatting)1); File.WriteAllText(FilePath, contents); } catch (Exception arg) { Plugin.Log.LogError((object)$"保存商店槽位计数失败: {arg}"); } } public static int GetCount(string permanentId) { int value; return (!_slotCounts.TryGetValue(permanentId, out value)) ? 1 : value; } public static void SetCount(string permanentId, int count) { _slotCounts[permanentId] = count; SaveCounts(); } public static void ResetAllCounts() { _slotCounts.Clear(); if (File.Exists(FilePath)) { File.Delete(FilePath); } Plugin.Log.LogInfo((object)"商店槽位计数已重置"); } private static void Postfix(ShopMenuStock __instance) { //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_0165: Unknown result type (might be due to invalid IL or missing references) try { if ((Object)(object)__instance == (Object)null) { return; } Scene activeScene = SceneManager.GetActiveScene(); string name = ((Scene)(ref activeScene)).name; LoadCounts(); __instance.availableStock.Clear(); float num = 0f; foreach (ShopItemStats item2 in __instance.spawnedStock) { if ((Object)(object)item2 == (Object)null) { continue; } ShopItem item = item2.Item; string text = ((item != null) ? ((Object)item).name : null); if (string.IsNullOrEmpty(text) || !text.Contains("_")) { int num2 = __instance.spawnedStock.IndexOf(item2); text = $"{name}_{num2}"; } int count = GetCount(text); if (count <= 0) { ((Component)item2).gameObject.SetActive(false); continue; } int price; SavedItem orCreateShopItem = ShopRandomizer.GetOrCreateShopItem(text, out price); if ((Object)(object)orCreateShopItem == (Object)null) { Plugin.Log.LogWarning((object)("商店随机:永久ID " + text + " 获取物品失败,跳过")); continue; } ShopItem val = CreateShopItem(orCreateShopItem, price, text); if (!((Object)(object)val == (Object)null)) { item2.SetItem(val); ((Component)item2).transform.localPosition = new Vector3(0f, num, 0f); item2.ItemNumber = __instance.availableStock.Count; __instance.availableStock.Add(item2); num += __instance.yDistance; ((Component)item2).gameObject.SetActive(true); item2.UpdateAppearance(); Plugin.Log.LogInfo((object)$"商店重建:永久ID {text} -> {((Object)orCreateShopItem).name} 价格 {price}"); } } foreach (ShopSubItemStats spawnedSubItem in __instance.spawnedSubItems) { ((Component)spawnedSubItem).gameObject.SetActive(false); } } catch (Exception arg) { Plugin.Log.LogError((object)$"商店重建补丁异常: {arg}"); } } private static ShopItem CreateShopItem(SavedItem savedItem, int price, string permanentId) { ShopItem val = ShopItem.CreateTemp(((Object)savedItem).name); ((Object)val).name = permanentId; FieldInfo field = typeof(ShopItem).GetField("savedItem", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field != null) { field.SetValue(val, savedItem); FieldInfo field2 = typeof(ShopItem).GetField("cost", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field2 != null) { field2.SetValue(val, price); FieldInfo field3 = typeof(ShopItem).GetField("costReference", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field3 != null) { field3.SetValue(val, null); } FieldInfo field4 = typeof(ShopItem).GetField("currencyType", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field4 != null) { field4.SetValue(val, (object)(CurrencyType)0); } ClearField(val, "playerDataBoolName"); ClearField(val, "playerDataIntName"); ClearField(val, "requiredItem"); ClearField(val, "upgradeFromItem"); if (val.questsAppearConditions == null) { val.questsAppearConditions = (QuestTest[])(object)new QuestTest[0]; } return val; } Plugin.Log.LogError((object)"未找到 cost 字段"); return null; } Plugin.Log.LogError((object)"未找到 savedItem 字段"); return null; } private static void ClearField(object obj, string fieldName) { FieldInfo field = obj.GetType().GetField(fieldName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field != null && field.FieldType.IsClass) { field.SetValue(obj, null); } } } public static class ShopRandomizer { private static Dictionary<string, SavedItem> _shopItemCache = new Dictionary<string, SavedItem>(); private static Dictionary<string, int> _shopPriceCache = new Dictionary<string, int>(); public static void ResetCache() { _shopItemCache.Clear(); _shopPriceCache.Clear(); Plugin.Log.LogInfo((object)"商店随机缓存已清空"); } public static SavedItem GetOrCreateShopItem(string permanentId, out int price) { if (_shopItemCache.TryGetValue(permanentId, out SavedItem value)) { if (!IsItemOwned(value)) { price = (_shopPriceCache.TryGetValue(permanentId, out var value2) ? value2 : GetDefaultPrice(value)); return value; } Plugin.Log.LogInfo((object)("商店槽位 " + permanentId + " 的物品 " + ((Object)value).name + " 已拥有,重新生成")); } string[] array = permanentId.Split('_'); string sceneName = string.Join("_", array.Take(array.Length - 1)); int originalIndex = int.Parse(array.Last()); int price2; SavedItem val = GenerateRandomShopItem(sceneName, originalIndex, permanentId, out price2); _shopItemCache[permanentId] = val; _shopPriceCache[permanentId] = price2; price = price2; return val; } public static SavedItem GetOrCreateShopItem(string sceneName, int slotIndex, out int price) { string permanentId = $"{sceneName}_{slotIndex}"; return GetOrCreateShopItem(permanentId, out price); } private static SavedItem GenerateRandomShopItem(string sceneName, int originalIndex, string permanentId, out int price) { int value = Plugin.RandomSeed.Value; int hashCode = permanentId.GetHashCode(); int seed = value ^ hashCode; Random random = new Random(seed); List<SavedItem> allItems = ItemRandomizer.GetAllItems(); if (allItems == null || allItems.Count == 0) { price = 0; return null; } List<SavedItem> list = allItems.Where((SavedItem item) => !IsItemOwned(item) && !(item is ToolCrest)).ToList(); if (list.Count == 0) { Plugin.Log.LogWarning((object)("商店随机池为空,使用所有物品中的第一个 (永久ID: " + permanentId + ")")); price = GetDefaultPrice(allItems[0]); return allItems[0]; } int index = random.Next(list.Count); SavedItem val = list[index]; price = GenerateRandomPrice(val, random); return val; } private static bool IsItemOwned(SavedItem item) { try { if (!item.CanGetMore()) { return true; } } catch { } return false; } private static int GenerateRandomPrice(SavedItem item, Random rng) { int defaultPrice = GetDefaultPrice(item); float num = (float)(rng.NextDouble() * 1.95 + 0.05); return Mathf.RoundToInt((float)defaultPrice * num); } private static int GetDefaultPrice(SavedItem item) { FieldInfo field = ((object)item).GetType().GetField("cost", BindingFlags.Instance | BindingFlags.Public); if (field != null && field.FieldType == typeof(int)) { return (int)field.GetValue(item); } return 100; } } [BepInPlugin("YourName.SilksongItemRandomizer", "Silksong Item Randomizer", "1.0.0.0")] public class Plugin : BaseUnityPlugin { [CompilerGenerated] private sealed class <DestroyMarkedPickups>d__25 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public Scene scene; public Plugin <>4__this; private CollectableItemPickup[] <pickups>5__1; private CollectableItemPickup[] <>s__2; private int <>s__3; private CollectableItemPickup <p>5__4; private string <key>5__5; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <DestroyMarkedPickups>d__25(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <pickups>5__1 = null; <>s__2 = null; <p>5__4 = null; <key>5__5 = null; <>1__state = -2; } private bool MoveNext() { //IL_00a9: 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_00e9: 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_0123: Unknown result type (might be due to invalid IL or missing references) switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; <pickups>5__1 = Resources.FindObjectsOfTypeAll<CollectableItemPickup>(); Log.LogInfo((object)$"[DestroyMarkedPickups] 开始检查场景 {((Scene)(ref scene)).name},已记录键数:{_destroyedPickupKeys.Count}"); <>s__2 = <pickups>5__1; for (<>s__3 = 0; <>s__3 < <>s__2.Length; <>s__3++) { <p>5__4 = <>s__2[<>s__3]; if (!(((Component)<p>5__4).gameObject.scene != scene)) { <key>5__5 = $"{((Scene)(ref scene)).name}_{((Component)<p>5__4).transform.position.x:F1}_{((Component)<p>5__4).transform.position.y:F1}_{((Component)<p>5__4).transform.position.z:F1}"; if (_destroyedPickupKeys.Contains(<key>5__5)) { Object.Destroy((Object)(object)((Component)<p>5__4).gameObject); Log.LogInfo((object)("[DestroyMarkedPickups] 销毁已标记点: " + <key>5__5)); } <key>5__5 = null; <p>5__4 = null; } } <>s__2 = null; return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } [CompilerGenerated] private sealed class <InitializeAfterLoad>d__24 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public int seed; public Plugin <>4__this; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <InitializeAfterLoad>d__24(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = (object)new WaitForSeconds(3f); <>1__state = 1; return true; case 1: <>1__state = -1; ItemRandomizer.Initialize(seed); ToolUnlockPatch.Initialize(); CrestRandomizer.Initialize(); Log.LogInfo((object)$"种子: {seed}"); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } internal static ManualLogSource Log; private static HashSet<string> _destroyedPickupKeys = new HashSet<string>(); private static string _notificationMessage = null; private static float _notificationEndTime = 0f; private static GUIStyle _notificationStyle; public static ConfigEntry<int> RandomSeed { get; private set; } public static Plugin Instance { get; private set; } private static string DestroyedPickupsFilePath { get { string text = Path.Combine(Paths.ConfigPath, "SilksongItemRandomizer"); if (!Directory.Exists(text)) { Directory.CreateDirectory(text); } return Path.Combine(text, "destroyed_pickups.json"); } } public static void ShowNotification(string message, float duration = 3f) { _notificationMessage = message; _notificationEndTime = Time.time + duration; } private Texture2D MakeTexture(int width, int height, Color col) { //IL_0010: 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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Expected O, but got Unknown Color[] array = (Color[])(object)new Color[width * height]; for (int i = 0; i < array.Length; i++) { array[i] = col; } Texture2D val = new Texture2D(width, height); val.SetPixels(array); val.Apply(); return val; } private void Awake() { Instance = this; Log = ((BaseUnityPlugin)this).Logger; RandomSeed = ((BaseUnityPlugin)this).Config.Bind<int>("General", "RandomSeed", 0, "随机种子 (0 表示随机)"); Harmony.CreateAndPatchAll(typeof(PickupPatch), (string)null); Harmony.CreateAndPatchAll(typeof(CurrencyCollectPatch), (string)null); Harmony.CreateAndPatchAll(typeof(TryGetPatch), (string)null); Harmony.CreateAndPatchAll(typeof(ToolUnlockPatch), (string)null); Harmony.CreateAndPatchAll(typeof(CrestRandomizePatch), (string)null); Harmony.CreateAndPatchAll(typeof(ShopMenuStock_BuildItemList_Patch), (string)null); Harmony.CreateAndPatchAll(typeof(ShopItemStats_Purchase_Patch), (string)null); Harmony.CreateAndPatchAll(typeof(SilkSpearPityPatch), (string)null); Harmony.CreateAndPatchAll(typeof(BenchRespawnPatch), (string)null); HazardSpawner.Initialize(); SceneManager.sceneLoaded += OnSceneLoaded; ((MonoBehaviour)this).StartCoroutine(InitializeAfterLoad(RandomSeed.Value)); LoadDestroyedKeys(); Log.LogInfo((object)"SilksongItemRandomizer loaded"); } private void OnSceneLoaded(Scene scene, LoadSceneMode mode) { //IL_0003: Unknown result type (might be due to invalid IL or missing references) ((MonoBehaviour)this).StartCoroutine(DestroyMarkedPickups(scene)); } private void LoadDestroyedKeys() { string destroyedPickupsFilePath = DestroyedPickupsFilePath; if (File.Exists(destroyedPickupsFilePath)) { try { string text = File.ReadAllText(destroyedPickupsFilePath); List<string> list = JsonConvert.DeserializeObject<List<string>>(text); _destroyedPickupKeys = ((list != null) ? new HashSet<string>(list) : new HashSet<string>()); return; } catch (Exception arg) { Log.LogError((object)$"加载特殊点消失记录失败: {arg}"); _destroyedPickupKeys = new HashSet<string>(); return; } } _destroyedPickupKeys = new HashSet<string>(); } private void SaveDestroyedKeys() { string destroyedPickupsFilePath = DestroyedPickupsFilePath; try { List<string> list = _destroyedPickupKeys.ToList(); string contents = JsonConvert.SerializeObject((object)list, (Formatting)1); File.WriteAllText(destroyedPickupsFilePath, contents); } catch (Exception arg) { Log.LogError((object)$"保存特殊点消失记录失败: {arg}"); } } public static void AddDestroyedPickupKey(string key) { _destroyedPickupKeys.Add(key); if ((Object)(object)Instance != (Object)null) { Instance.SaveDestroyedKeys(); } else { Log.LogError((object)"AddDestroyedPickupKey: Instance is null"); } } public static void ResetDestroyedPickupKeys() { _destroyedPickupKeys.Clear(); string destroyedPickupsFilePath = DestroyedPickupsFilePath; if (File.Exists(destroyedPickupsFilePath)) { File.Delete(destroyedPickupsFilePath); } } public static void ResetAllStaticData() { CrestRandomizer.ResetMappings(); CrestRandomizePatch.ResetProcessedIds(); CurrencyCollectPatch.ResetCounters(); ResetDestroyedPickupKeys(); ShopRandomizer.ResetCache(); ShopMenuStock_BuildItemList_Patch.ResetAllCounts(); Log.LogInfo((object)"物品随机MOD所有静态数据已重置"); Log.LogInfo((object)"物品随机MOD所有静态数据已重置"); } [IteratorStateMachine(typeof(<InitializeAfterLoad>d__24))] private IEnumerator InitializeAfterLoad(int seed) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <InitializeAfterLoad>d__24(0) { <>4__this = this, seed = seed }; } [IteratorStateMachine(typeof(<DestroyMarkedPickups>d__25))] private IEnumerator DestroyMarkedPickups(Scene scene) { //IL_000e: Unknown result type (might be due to invalid IL or missing references) //IL_000f: Unknown result type (might be due to invalid IL or missing references) //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <DestroyMarkedPickups>d__25(0) { <>4__this = this, scene = scene }; } private void Update() { //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_008f: 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_0096: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: Unknown result type (might be due to invalid IL or missing references) RecentItemsUI.UpdateAutoHide(); if (Input.GetKeyDown((KeyCode)286)) { RecentItemsUI.Toggle(); Log.LogInfo((object)("最近获得物品UI " + (RecentItemsUI.IsVisible ? "显示" : "隐藏"))); } if (Input.GetKeyDown((KeyCode)289)) { DumpAllMappings(); } if (Input.GetKeyDown((KeyCode)290)) { HeroController instance = HeroController.instance; if ((Object)(object)instance != (Object)null) { Vector3 val = instance.transform.position + HazardSpawner.GetSpawnOffset(); HazardSpawner.SpawnCustomHazard(val); Log.LogInfo((object)$"在玩家位置 + 偏移生成 hazard,最终坐标: {val}"); } } } private void OnGUI() { //IL_00de: 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_0051: Expected O, but got Unknown //IL_0074: 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) RecentItemsUI.Draw(); HazardSpawner.DrawUI(); if (_notificationMessage != null && Time.time <= _notificationEndTime) { if (_notificationStyle == null) { _notificationStyle = new GUIStyle(GUI.skin.box); _notificationStyle.fontSize = 40; _notificationStyle.alignment = (TextAnchor)4; _notificationStyle.normal.textColor = Color.white; _notificationStyle.normal.background = MakeTexture(2, 2, new Color(0f, 0f, 0f, 0.7f)); } float num = 600f; float num2 = 120f; float num3 = ((float)Screen.width - num) / 2f; float num4 = Screen.height / 2 - 100; GUI.Box(new Rect(num3, num4, num, num2), _notificationMessage, _notificationStyle); } else { _notificationMessage = null; } } private void DumpAllMappings() { //IL_0194: Unknown result type (might be due to invalid IL or missing references) int value = RandomSeed.Value; Log.LogInfo((object)$"===== 当前种子: {value} ====="); List<ToolCrest> crestList = CrestRandomizer.CrestList; if (crestList != null && crestList.Count > 0) { Log.LogInfo((object)"--- 纹章映射 ---"); foreach (ToolCrest item2 in crestList) { string name = item2.name; string mappedCrestName = CrestRandomizer.GetMappedCrestName(name); Log.LogInfo((object)(" " + name + " -> " + mappedCrestName)); } } Log.LogInfo((object)"--- 当前场景拾取点映射 ---"); CollectableItemPickup[] source = Resources.FindObjectsOfTypeAll<CollectableItemPickup>(); List<CollectableItemPickup> list = source.Where(delegate(CollectableItemPickup p) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Unknown result type (might be due to invalid IL or missing references) _ = ((Component)p).gameObject.scene; Scene scene = ((Component)p).gameObject.scene; return ((Scene)(ref scene)).isLoaded; }).ToList(); if (list.Count == 0) { Log.LogInfo((object)"当前场景无拾取点。"); } else { foreach (CollectableItemPickup item3 in list) { SavedItem item = item3.Item; if (!((Object)(object)item == (Object)null)) { int seed = value + ((Object)item3).GetInstanceID(); Random rng = new Random(seed); SavedItem val = ItemRandomizer.PeekRandomItem(rng); if ((Object)(object)val != (Object)null) { Log.LogInfo((object)$" {((Object)item).name} (位置 {((Component)item3).transform.position}) -> {((Object)val).name}"); } else { Log.LogInfo((object)(" " + ((Object)item).name + " -> 随机失败")); } } } } Log.LogInfo((object)"==============================="); } } public static class RecentItemsUI { [CompilerGenerated] private static class <>O { public static WindowFunction <0>__DoWindow; } private static Queue<SavedItem> recentItems = new Queue<SavedItem>(); private const int MaxItems = 5; private static Rect windowRect = new Rect(20f, 300f, 700f, 600f); private static bool _showWindow = false; private static float hideTime = 0f; public static bool IsVisible => _showWindow; public static void AddItem(SavedItem item) { if (!((Object)(object)item == (Object)null)) { recentItems.Enqueue(item); while (recentItems.Count > 5) { recentItems.Dequeue(); } _showWindow = true; hideTime = Time.time + 10f; } } public static void Toggle() { _showWindow = !_showWindow; if (_showWindow) { hideTime = float.MaxValue; } } public static void UpdateAutoHide() { if (_showWindow && Time.time >= hideTime) { _showWindow = false; } } public static void Draw() { //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_0043: Unknown result type (might be due to invalid IL or missing references) //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_0034: Expected O, but got Unknown if (_showWindow) { Rect val = windowRect; object obj = <>O.<0>__DoWindow; if (obj == null) { WindowFunction val2 = DoWindow; <>O.<0>__DoWindow = val2; obj = (object)val2; } windowRect = GUILayout.Window(999, val, (WindowFunction)obj, "最近获得物品", Array.Empty<GUILayoutOption>()); } } private static void DoWindow(int id) { //IL_017e: Unknown result type (might be due to invalid IL or missing references) //IL_0183: Unknown result type (might be due to invalid IL or missing references) //IL_00ba: Unknown result type (might be due to invalid IL or missing references) //IL_00bf: Unknown result type (might be due to invalid IL or missing references) //IL_01bb: 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_01d9: Unknown result type (might be due to invalid IL or missing references) //IL_01de: Unknown result type (might be due to invalid IL or missing references) //IL_01e6: Unknown result type (might be due to invalid IL or missing references) //IL_01f4: Expected O, but got Unknown //IL_01a6: Unknown result type (might be due to invalid IL or missing references) //IL_01af: Unknown result type (might be due to invalid IL or missing references) int fontSize = GUI.skin.label.fontSize; GUI.skin.label.fontSize = 32; GUILayout.BeginVertical(Array.Empty<GUILayoutOption>()); SavedItem[] array = recentItems.ToArray(); Rect val3 = default(Rect); foreach (SavedItem val in array) { GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); Sprite val2 = null; try { val2 = ((val != null) ? val.GetPopupIcon() : null); } catch { } float num = 96f; float num2 = 96f; ((Rect)(ref val3))..ctor(0f, 0f, 1f, 1f); if ((Object)(object)val2 != (Object)null && (Object)(object)val2.texture != (Object)null) { Rect textureRect = val2.textureRect; float num3 = ((Texture)val2.texture).width; float num4 = ((Texture)val2.texture).height; ((Rect)(ref val3))..ctor(((Rect)(ref textureRect)).x / num3, ((Rect)(ref textureRect)).y / num4, ((Rect)(ref textureRect)).width / num3, ((Rect)(ref textureRect)).height / num4); if (((Rect)(ref textureRect)).width > 0f && ((Rect)(ref textureRect)).height > 0f) { num2 = num * (((Rect)(ref textureRect)).height / ((Rect)(ref textureRect)).width); if (num2 > 180f) { num2 = 180f; } } } Rect rect = GUILayoutUtility.GetRect(num, num2, (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(num), GUILayout.Height(num2) }); if ((Object)(object)val2 != (Object)null && (Object)(object)val2.texture != (Object)null) { GUI.DrawTextureWithTexCoords(rect, (Texture)(object)val2.texture, val3); } else { GUI.Box(rect, ""); GUI.Label(rect, "?", new GUIStyle(GUI.skin.label) { alignment = (TextAnchor)4, fontSize = 36 }); } string text = "未知物品"; try { MethodInfo methodInfo = ((object)val)?.GetType().GetMethod("GetCollectionName", BindingFlags.Instance | BindingFlags.Public); text = ((!(methodInfo != null)) ? ((val != null) ? val.GetPopupName() : null) : (methodInfo.Invoke(val, null) as string)); if (string.IsNullOrEmpty(text)) { text = ((val != null) ? ((Object)val).name : null) ?? "未知物品"; } } catch { text = ((val != null) ? ((Object)val).name : null) ?? "未知物品"; } GUILayout.Label("• " + text, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(num2) }); GUILayout.EndHorizontal(); } GUILayout.EndVertical(); GUI.DragWindow(); GUI.skin.label.fontSize = fontSize; } } [HarmonyPatch(typeof(CurrencyObjectBase), "Collect")] public static class SilkSpearPityPatch { private static int _silkSpearAttempts; private static bool _silkSpearGiven; private const int SILK_SPEAR_PITY = 200; private static SavedItem? _silkSpearItem; public static bool IsGivingSilkSpear; static SilkSpearPityPatch() { _silkSpearAttempts = 0; _silkSpearGiven = false; IsGivingSilkSpear = false; SavedItem[] source = Resources.FindObjectsOfTypeAll<SavedItem>(); _silkSpearItem = ((IEnumerable<SavedItem>)source).FirstOrDefault((Func<SavedItem, bool>)((SavedItem item) => ((Object)item).name == "Silk Spear")); if ((Object)(object)_silkSpearItem == (Object)null) { Plugin.Log.LogWarning((object)"[丝矛独立补丁] 未找到丝矛物品,保底将禁用。"); } else { Plugin.Log.LogInfo((object)("[丝矛独立补丁] 丝矛物品已找到: " + ((Object)_silkSpearItem).name)); } } public static void ResetCounter() { _silkSpearAttempts = 0; _silkSpearGiven = false; Plugin.Log.LogInfo((object)"[丝矛独立补丁] 计数器已重置"); } private static void Postfix(bool __result) { if (!__result || (Object)(object)_silkSpearItem == (Object)null || _silkSpearGiven) { return; } _silkSpearAttempts++; if (_silkSpearGiven || _silkSpearAttempts < 200) { return; } Plugin.Log.LogInfo((object)$"[丝矛独立补丁] 保底触发(第{_silkSpearAttempts}次)"); bool flag = false; IsGivingSilkSpear = true; SavedItem? silkSpearItem = _silkSpearItem; ToolItem val = (ToolItem)(object)((silkSpearItem is ToolItem) ? silkSpearItem : null); if (val != null) { try { MethodInfo methodInfo = typeof(ToolItem).GetMethod("Unlock", Type.EmptyTypes) ?? typeof(ToolItem).GetMethod("Unlock", new Type[2] { typeof(Action), typeof(PopupFlags) }); if (methodInfo != null) { if (methodInfo.GetParameters().Length == 0) { methodInfo.Invoke(val, null); } else { methodInfo.Invoke(val, new object[2] { null, (object)(PopupFlags)3 }); } flag = true; } } catch (Exception arg) { Plugin.Log.LogError((object)$"[丝矛独立补丁] Unlock 失败: {arg}"); } } else { flag = _silkSpearItem.TryGet(false, true); } IsGivingSilkSpear = false; if (flag) { Plugin.Log.LogInfo((object)"[丝矛独立补丁] 丝矛成功给予"); Plugin.ShowNotification("获得丝矛!"); _silkSpearGiven = true; } else { Plugin.Log.LogError((object)"[丝矛独立补丁] 丝矛给予失败"); _silkSpearGiven = true; } } } public static class ToolUnlockPatch { private static List<ToolItem>? _allTools; public static bool IsShopPurchase; public static void Initialize() { _allTools = Resources.FindObjectsOfTypeAll<ToolItem>().ToList(); if (_allTools.Count == 0) { Plugin.Log.LogWarning((object)"No ToolItem found! Tool randomizer may not work."); } } [HarmonyPatch(typeof(ToolItem), "Unlock")] [HarmonyPrefix] private static bool Prefix(ToolItem __instance, Action afterTutorialMsg, PopupFlags popupFlags) { //IL_00d1: Unknown result type (might be due to invalid IL or missing references) try { if (IsShopPurchase) { return true; } if (_allTools == null || _allTools.Count == 0) { Initialize(); if (_allTools == null || _allTools.Count == 0) { Plugin.Log.LogWarning((object)"Tool list empty, cannot randomize."); return true; } } ToolItem val = _allTools[ItemRandomizer.Rng.Next(_allTools.Count)]; if ((Object)(object)val == (Object)(object)__instance) { return true; } Plugin.Log.LogInfo((object)("工具随机: " + (((__instance != null) ? __instance.name : null) ?? "null") + " -> " + val.name)); val.Unlock(afterTutorialMsg, popupFlags); return false; } catch (Exception arg) { Plugin.Log.LogError((object)$"Exception in ToolUnlockPatch.Prefix: {arg}"); return true; } } } [HarmonyPatch(typeof(SavedItem), "TryGet")] public class TryGetPatch { private static bool _isProcessing; private static void Postfix(SavedItem __instance, bool __result) { try { if (_isProcessing || !__result) { return; } if (((Object)__instance).name != "Rosary_Set_Frayed") { RecentItemsUI.AddItem(__instance); } _isProcessing = true; try { UnlockRandomAttack(); } catch (Exception arg) { Plugin.Log.LogError((object)$"Error unlocking attack: {arg}"); } finally { _isProcessing = false; } } catch (Exception arg2) { Plugin.Log.LogError((object)$"Unhandled exception in TryGetPatch.Postfix: {arg2}"); } } private static void UnlockRandomAttack() { Type type = Type.GetType("StartingAbilityPicker.Plugin, StartingAbilityPicker"); if (type == null) { return; } FieldInfo field = type.GetField("AllowUpwardAttack", BindingFlags.Static | BindingFlags.Public); FieldInfo field2 = type.GetField("AllowLeftAttack", BindingFlags.Static | BindingFlags.Public); FieldInfo field3 = type.GetField("AllowRightAttack", BindingFlags.Static | BindingFlags.Public); if (field == null || field2 == null || field3 == null) { return; } bool flag = (bool)field.GetValue(null); bool flag2 = (bool)field2.GetValue(null); bool flag3 = (bool)field3.GetValue(null); List<string> list = new List<string>(); if (!flag) { list.Add("upward"); } if (!flag2) { list.Add("left"); } if (!flag3) { list.Add("right"); } if (list.Count == 0 || ItemRandomizer.Rng == null || ItemRandomizer.Rng.NextDouble() > 0.05) { return; } string text = list[ItemRandomizer.Rng.Next(list.Count)]; PlayerData instance = PlayerData.instance; if (instance != null) { switch (text) { case "upward": field.SetValue(null, true); instance.SetBool("AllowUpwardAttack", true); Plugin.Log.LogInfo((object)"Attack direction unlocked via item: upward (saved to PlayerData)"); break; case "left": field2.SetValue(null, true); instance.SetBool("AllowLeftAttack", true); Plugin.Log.LogInfo((object)"Attack direction unlocked via item: left (saved to PlayerData)"); break; case "right": field3.SetValue(null, true); instance.SetBool("AllowRightAttack", true); Plugin.Log.LogInfo((object)"Attack direction unlocked via item: right (saved to PlayerData)"); break; } } } } } namespace SilksongItemRandomizer.Hazard { public class HazardDebug : MonoBehaviour { private void OnTriggerEnter2D(Collider2D other) { if (((Component)other).CompareTag("Hero") || ((Component)other).CompareTag("Player")) { Plugin.Log.LogInfo((object)"【调试】玩家进入 hazard 触发器!"); } } } public static class HazardSpawner { [CompilerGenerated] private static class <>O { public static WindowFunction <0>__DoUIWindow; public static UnityAction<Scene, LoadSceneMode> <1>__OnSceneLoaded; } [CompilerGenerated] private sealed class <>c__DisplayClass28_0 { public Vector3 spawnPos; internal bool <AutoGenerateForSceneCoroutine>b__0(Vector3 pos) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0002: Unknown result type (might be due to invalid IL or missing references) return Vector3.Distance(pos, spawnPos) < 2f; } } [CompilerGenerated] private sealed class <AutoGenerateForSceneCoroutine>d__28 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public string sceneName; private List<Vector3> <positions>5__1; private int <maxAttempts>5__2; private int <generated>5__3; private Random <rand>5__4; private int <attempt>5__5; private Vector3 <center>5__6; private Vector2 <randomPoint>5__7; private RaycastHit2D <hit>5__8; private <>c__DisplayClass28_0 <>8__9; private bool <tooClose>5__10; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <AutoGenerateForSceneCoroutine>d__28(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <positions>5__1 = null; <rand>5__4 = null; <>8__9 = null; <>1__state = -2; } private bool MoveNext() { //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_01b0: Unknown result type (might be due to invalid IL or missing references) //IL_01b5: Unknown result type (might be due to invalid IL or missing references) //IL_01bc: Unknown result type (might be due to invalid IL or missing references) //IL_01c1: 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) //IL_01d5: 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_020c: Unknown result type (might be due to invalid IL or missing references) //IL_0211: Unknown result type (might be due to invalid IL or missing references) //IL_0216: Unknown result type (might be due to invalid IL or missing references) //IL_026c: Unknown result type (might be due to invalid IL or missing references) //IL_0283: Unknown result type (might be due to invalid IL or missing references) switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; if (_sceneRecords.ContainsKey(sceneName)) { Plugin.Log.LogInfo((object)("场景 " + sceneName + " 已有记录,跳过生成")); return false; } if (_sceneHazardCount <= 0) { Plugin.Log.LogInfo((object)("场景 " + sceneName + " 生成数量为 0,跳过")); return false; } Plugin.Log.LogInfo((object)$"开始为场景 {sceneName} 自动生成 {_sceneHazardCount} 个 hazard"); <positions>5__1 = new List<Vector3>(); <maxAttempts>5__2 = 200; <generated>5__3 = 0; <rand>5__4 = ((_currentSeed != 0) ? new Random(_currentSeed + sceneName.GetHashCode()) : new Random()); <attempt>5__5 = 0; while (<attempt>5__5 < <maxAttempts>5__2 && <generated>5__3 < _sceneHazardCount) { <center>5__6 = new Vector3(0f, 0f, 0f); if ((Object)(object)Object.FindObjectOfType<HeroController>() != (Object)null) { <center>5__6 = Object.FindObjectOfType<HeroController>().transform.position; } <randomPoint>5__7 = new Vector2(<center>5__6.x + (float)(<rand>5__4.NextDouble() * 100.0 - 50.0), <center>5__6.y + (float)(<rand>5__4.NextDouble() * 100.0 - 50.0)); <hit>5__8 = Physics2D.Raycast(<randomPoint>5__7, Vector2.down, 100f, GROUND_LAYER_MASK); if ((Object)(object)((RaycastHit2D)(ref <hit>5__8)).collider != (Object)null) { <>8__9 = new <>c__DisplayClass28_0(); <>8__9.spawnPos = Vector2.op_Implicit(((RaycastHit2D)(ref <hit>5__8)).point); <>8__9.spawnPos.y += 0.1f; <tooClose>5__10 = <positions>5__1.Any((Vector3 pos) => Vector3.Distance(pos, <>8__9.spawnPos) < 2f); if (!<tooClose>5__10) { SpawnCustomHazard(<>8__9.spawnPos); <positions>5__1.Add(<>8__9.spawnPos); <generated>5__3++; } <>8__9 = null; } <attempt>5__5++; } _sceneRecords[sceneName] = <positions>5__1; SaveSceneRecords(); Plugin.Log.LogInfo((object)$"场景 {sceneName} 自动生成完成,实际生成 {<generated>5__3} 个"); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } private static List<GameObject> _spawnedHazards = new List<GameObject>(); private static List<Sprite> _lavaSprites = new List<Sprite>(); private static readonly int GROUND_LAYER_MASK = 1049344; private static Vector3 _spawnOffset = Vector3.zero; private static Vector2 _boxSize = new Vector2(6f, 2f); private static Vector2 _boxOffset = new Vector2(0f, 0f); private static int _damage = 2; private static HazardType _hazardType = (HazardType)4; private static Vector2 _visualSize = new Vector2(1.5f, 1.5f); private static Vector2 _visualOffset = new Vector2(0f, -1f); private static bool _sceneHazardMode = true; private static int _sceneHazardCount = 2; private static int _currentSeed; private static Dictionary<string, List<Vector3>> _sceneRecords = new Dictionary<string, List<Vector3>>(); private static string _sceneRecordFilePath; private static bool _sceneLoadedHandlerRegistered = false; private static string _logFilePath; private static readonly object _logLock = new object(); private static bool _uiVisible = false; private static Rect _uiRect = new Rect(0f, 0f, 500f, 500f); public static void ToggleUI() { _uiVisible = !_uiVisible; } public static void DrawUI() { //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_0043: Unknown result type (might be due to invalid IL or missing references) //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_0034: Expected O, but got Unknown if (_uiVisible) { Rect uiRect = _uiRect; object obj = <>O.<0>__DoUIWindow; if (obj == null) { WindowFunction val = DoUIWindow; <>O.<0>__DoUIWindow = val; obj = (object)val; } _uiRect = GUILayout.Window(999, uiRect, (WindowFunction)obj, "Hazard 参数调整", Array.Empty<GUILayoutOption>()); } } private static void DoUIWindow(int id) { } public static void Initialize() { LoadLocalSprites(); Physics2D.IgnoreLayerCollision(17, 8, false); string text = Path.Combine(Paths.ConfigPath, "SilksongItemRandomizer"); if (!Directory.Exists(text)) { Directory.CreateDirectory(text); } _logFilePath = Path.Combine(text, "HazardSpawnLog.json"); _sceneRecordFilePath = Path.Combine(text, "hazard_scene_records.json"); LoadSceneRecords(); if (!_sceneLoadedHandlerRegistered) { SceneManager.sceneLoaded += OnSceneLoaded; _sceneLoadedHandlerRegistered = true; } Plugin.Log.LogInfo((object)("HazardSpawner 初始化完成,日志文件: " + _logFilePath)); } private static void LoadLocalSprites() { //IL_00f9: Unknown result type (might be due to invalid IL or missing references) //IL_0100: Expected O, but got Unknown //IL_012c: 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) _lavaSprites.Clear(); string text = Path.Combine(Paths.PluginPath, "SilksongItemRandomizer", "Textures", "Lava"); Plugin.Log.LogInfo((object)("[LoadLocalSprites] 路径: " + text)); if (!Directory.Exists(text)) { Plugin.Log.LogError((object)("文件夹不存在!请确保贴图放在: " + text)); return; } string[] array = (from f in Directory.GetFiles(text, "*.*") where f.EndsWith(".jpg") || f.EndsWith(".jpeg") || f.EndsWith(".png") orderby f select f).ToArray(); Plugin.Log.LogInfo((object)$"找到 {array.Length} 个图片文件"); string[] array2 = array; foreach (string text2 in array2) { try { byte[] array3 = File.ReadAllBytes(text2); Texture2D val = new Texture2D(2, 2); if (ImageConversion.LoadImage(val, array3)) { Sprite item = Sprite.Create(val, new Rect(0f, 0f, (float)((Texture)val).width, (float)((Texture)val).height), new Vector2(0.5f, 0.5f)); _lavaSprites.Add(item); Plugin.Log.LogInfo((object)$"加载成功: {Path.GetFileName(text2)} {((Texture)val).width}x{((Texture)val).height}"); } else { Plugin.Log.LogError((object)("加载失败: " + Path.GetFileName(text2))); } } catch (Exception ex) { Plugin.Log.LogError((object)("加载异常: " + text2 + " - " + ex.Message)); } } Plugin.Log.LogInfo((object)$"共加载 {_lavaSprites.Count} 张精灵"); } private static void LoadSceneRecords() { if (File.Exists(_sceneRecordFilePath)) { try { string text = File.ReadAllText(_sceneRecordFilePath); _sceneRecords = JsonConvert.DeserializeObject<Dictionary<string, List<Vector3>>>(text) ?? new Dictionary<string, List<Vector3>>(); Plugin.Log.LogInfo((object)$"已加载 {_sceneRecords.Count} 个场景的 hazard 记录"); return; } catch (Exception arg) { Plugin.Log.LogError((object)$"加载场景记录失败: {arg}"); _sceneRecords = new Dictionary<string, List<Vector3>>(); return; } } _sceneRecords = new Dictionary<string, List<Vector3>>(); } private static void SaveSceneRecords() { try { string contents = JsonConvert.SerializeObject((object)_sceneRecords, (Formatting)1); File.WriteAllText(_sceneRecordFilePath, contents); Plugin.Log.LogInfo((object)$"已保存 {_sceneRecords.Count} 个场景的 hazard 记录"); } catch (Exception arg) { Plugin.Log.LogError((object)$"保存场景记录失败: {arg}"); } } private static void OnSceneLoaded(Scene scene, LoadSceneMode mode) { if (_sceneHazardMode && !(((Scene)(ref scene)).name == "Menu_Title") && !(((Scene)(ref scene)).name == "Menu") && !(((Scene)(ref scene)).name == "Loading") && !((Scene)(ref scene)).name.Contains("Menu") && (Object)(object)Plugin.Instance != (Object)null) { ((MonoBehaviour)Plugin.Instance).StartCoroutine(AutoGenerateForSceneCoroutine(((Scene)(ref scene)).name)); } } [IteratorStateMachine(typeof(<AutoGenerateForSceneCoroutine>d__28))] private static IEnumerator AutoGenerateForSceneCoroutine(string sceneName) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <AutoGenerateForSceneCoroutine>d__28(0) { sceneName = sceneName }; } public static void SetSceneHazardMode(bool enabled) { _sceneHazardMode = enabled; Plugin.Log.LogInfo((object)$"场景 Hazard 自动生成模式设置为 {enabled}"); } public static void SetSceneHazardCount(int count) { _sceneHazardCount = Mathf.Max(0, count); Plugin.Log.LogInfo((object)$"场景 Hazard 生成数量设置为 {_sceneHazardCount}"); } public static void SetSeed(int seed) { _currentSeed = seed; Plugin.Log.LogInfo((object)$"HazardSpawner 种子已设置为 {seed}"); } public static void ResetSceneRecords() { _sceneRecords.Clear(); SaveSceneRecords(); Plugin.Log.LogInfo((object)"Hazard 场景记录已重置"); } public static void ResetWorld() { ClearAll(); ResetSceneRecords(); Plugin.Log.LogInfo((object)"HazardSpawner 世界已重置"); } public static void SpawnCustomHazard(Vector3 position) { //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Expected O, but got Unknown //IL_001c: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_0039: 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: Expected O, but got Unknown //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0077: 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_00ea: Unknown result type (might be due to invalid IL or missing references) Physics2D.IgnoreLayerCollision(17, 8, false); GameObject val = new GameObject("CustomHazard_Manual"); val.transform.position = position; val.layer = 17; DamageHero val2 = val.AddComponent<DamageHero>(); val2.hazardType = _hazardType; val2.damageDealt = _damage; val2.canClashTink = false; val2.OnDamagedHero = new UnityEvent(); BoxCollider2D val3 = val.AddComponent<BoxCollider2D>(); ((Collider2D)val3).isTrigger = true; val3.size = _boxSize; ((Collider2D)val3).offset = _boxOffset; val.AddComponent<HazardDebug>(); val.AddComponent<NonBouncer>(); val.AddComponent<PersonalObjectPool>(); val.AddComponent<DamageEnemies>(); LavaBox val4 = val.AddComponent<LavaBox>(); val4.isLavaFall = false; val.SetActive(false); val.SetActive(true); AddVisual(val); _spawnedHazards.Add(val); Plugin.Log.LogInfo((object)$"生成 hazard 于 {position}"); RecordSpawnToLog(position); } private static void AddVisual(GameObject parent) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Expected O, but got Unknown //IL_003d: Unknown result type (might be due to invalid IL or missing references) //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_009f: Unknown result type (might be due to invalid IL or missing references) GameObject val = new GameObject("LavaVisual"); val.transform.SetParent(parent.transform); val.transform.localPosition = new Vector3(_visualOffset.x, _visualOffset.y, 0f); val.transform.localScale = new Vector3(_visualSize.x, _visualSize.y, 1f); SpriteRenderer val2 = val.AddComponent<SpriteRenderer>(); if (_lavaSprites.Count > 0) { val2.sprite = _lavaSprites[0]; } else { val2.sprite = CreateColorSprite(Color.red); } ((Renderer)val2).sortingLayerName = "Default"; ((Renderer)val2).sortingOrder = 100; } private static Sprite CreateColorSprite(Color color) { //IL_0003: Unknown result type (might be due to invalid IL or missing references) //IL_0009: Expected O, but got Unknown //IL_000c: 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_003e: Unknown result type (might be due to invalid IL or missing references) Texture2D val = new Texture2D(1, 1); val.SetPixel(0, 0, color); val.Apply(); return Sprite.Create(val, new Rect(0f, 0f, 1f, 1f), new Vector2(0.5f, 0.5f)); } private static void RecordSpawnToLog(Vector3 position) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0019: 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) var anon = new { timestamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"), posX = position.x, posY = position.y, posZ = position.z, boxSizeX = _boxSize.x, boxSizeY = _boxSize.y, visualSizeX = _visualSize.x, visualSizeY = _visualSize.y, damage = _damage, hazardType = ((object)(HazardType)(ref _hazardType)).ToString() }; string value = JsonConvert.SerializeObject((object)anon); lock (_logLock) { try { using StreamWriter streamWriter = new StreamWriter(_logFilePath, append: true); streamWriter.WriteLine(value); } catch (Exception ex) { Plugin.Log.LogError((object)("写入日志失败: " + ex.Message)); } } } public static void SpawnAtPlayer() { //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_0022: Unknown result type (might be due to invalid IL or missing references) HeroController instance = HeroController.instance; if ((Object)(object)instance != (Object)null) { SpawnCustomHazard(instance.transform.position + _spawnOffset); } } public static Vector3 GetSpawnOffset() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) return _spawnOffset; } public static void ClearAll() { foreach (GameObject spawnedHazard in _spawnedHazards) { if ((Object)(object)spawnedHazard != (Object)null) { Object.Destroy((Object)(object)spawnedHazard); } } _spawnedHazards.Clear(); Plugin.Log.LogInfo((object)"已清除所有生成的 hazard"); } } }
plugins/SkillRandomizerMod.dll
Decompiled a day agousing System; using System.Collections; 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.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using Microsoft.CodeAnalysis; using Newtonsoft.Json; using UnityEngine; using UnityEngine.SceneManagement; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("SkillRandomizerMod")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("0.1.0.0")] [assembly: AssemblyInformationalVersion("0.1.0")] [assembly: AssemblyProduct("SkillRandomizerMod")] [assembly: AssemblyTitle("SkillRandomizerMod")] [assembly: AssemblyMetadata("RepositoryUrl", "https://github.com/YourName/SkillRandomizerMod")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.1.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 BepInEx { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class BepInAutoPluginAttribute : Attribute { public BepInAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace BepInEx.Preloader.Core.Patching { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class PatcherAutoPluginAttribute : Attribute { public PatcherAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace SkillTriggerMod { [BepInPlugin("YourName.SkillTriggerMod", "Skill Trigger Mod", "1.0.0.0")] public class Plugin : BaseUnityPlugin { [CompilerGenerated] private sealed class <CreateTriggerDelayed>d__28 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public (string scene, float x, float y, float z) target; public int index; public Plugin <>4__this; private Vector3 <pos>5__1; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <CreateTriggerDelayed>d__28(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_006a: Unknown result type (might be due to invalid IL or missing references) switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; <pos>5__1 = new Vector3(target.x, target.y, target.z); <>4__this.CreateTriggerAt(<pos>5__1, target.scene, index); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } [CompilerGenerated] private sealed class <DisableShrinesAfterStart>d__25 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public Plugin <>4__this; private int <i>5__1; private Scene <scene>5__2; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <DisableShrinesAfterStart>d__25(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Expected O, but got Unknown //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_0071: Unknown result type (might be due to invalid IL or missing references) switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = (object)new WaitForSeconds(5f); <>1__state = 1; return true; case 1: <>1__state = -1; <i>5__1 = 0; while (<i>5__1 < SceneManager.sceneCount) { <scene>5__2 = SceneManager.GetSceneAt(<i>5__1); if (((Scene)(ref <scene>5__2)).isLoaded) { <>4__this.DisableShrinesInScene(<scene>5__2); } <i>5__1++; } return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } [CompilerGenerated] private sealed class <InitializeRandomizer>d__23 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public Plugin <>4__this; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <InitializeRandomizer>d__23(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = (object)new WaitForSeconds(3f); <>1__state = 1; return true; case 1: <>1__state = -1; SkillRandomizer.SetSeed(RandomSeed.Value); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } internal static ManualLogSource Log; internal static HashSet<string> _triggeredRecords = new HashSet<string>(); private static string _notificationMessage = null; private static float _notificationEndTime = 0f; private static GUIStyle _notificationStyle; private readonly List<(string scene, float x, float y, float z)> targetPositions = new List<(string, float, float, float)> { ("Mosstown_02", 86.922f, 52.568f, 0.004f), ("Crawl_05", 23.032f, 16.568f, 0.004f), ("Shellwood_10", 40.643f, 79.57f, 0.004f), ("Greymoor_22", 39.783f, 36.826f, 0.004f), ("Bone_East_05", 100.062f, 13.568f, 0.004f) }; private readonly string[] shrineKeywords = new string[5] { "bind orb", "shrine weaver ability", "weaver_shrine", "bellshrine", "dash shrine" }; public static ConfigEntry<int> RandomSeed { get; private set; } private static string TriggerRecordsPath => Path.Combine(Paths.ConfigPath, "SkillTriggerMod", "trigger_records.json"); internal static Plugin Instance { get; private set; } public static void ShowNotification(string message, float duration = 3f) { _notificationMessage = message; _notificationEndTime = Time.time + duration; } private void OnGUI() { //IL_00f2: Unknown result type (might be due to invalid IL or missing references) //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Expected O, but got Unknown //IL_0072: Unknown result type (might be due to invalid IL or missing references) //IL_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00bb: Unknown result type (might be due to invalid IL or missing references) //IL_00c5: Expected O, but got Unknown if (_notificationMessage == null || Time.time > _notificationEndTime) { _notificationMessage = null; return; } if (_notificationStyle == null) { _notificationStyle = new GUIStyle(GUI.skin.box); _notificationStyle.fontSize = 40; _notificationStyle.alignment = (TextAnchor)4; _notificationStyle.normal.textColor = Color.white; _notificationStyle.normal.background = MakeTexture(2, 2, new Color(0f, 0f, 0f, 0.8f)); _notificationStyle.border = new RectOffset(20, 20, 10, 10); } float num = 600f; float num2 = 120f; float num3 = ((float)Screen.width - num) / 2f; float num4 = Screen.height / 2 - 100; GUI.Box(new Rect(num3, num4, num, num2), _notificationMessage, _notificationStyle); } private Texture2D MakeTexture(int width, int height, Color col) { //IL_0010: 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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Expected O, but got Unknown Color[] array = (Color[])(object)new Color[width * height]; for (int i = 0; i < array.Length; i++) { array[i] = col; } Texture2D val = new Texture2D(width, height); val.SetPixels(array); val.Apply(); return val; } private void Awake() { Instance = this; Log = ((BaseUnityPlugin)this).Logger; RandomSeed = ((BaseUnityPlugin)this).Config.Bind<int>("General", "RandomSeed", 0, "随机种子 (0 表示随机)"); LoadTriggerRecords(); SceneManager.sceneLoaded += OnSceneLoaded; ((MonoBehaviour)this).StartCoroutine(DisableShrinesAfterStart()); ((MonoBehaviour)this).StartCoroutine(InitializeRandomizer()); } private void LoadTriggerRecords() { try { if (File.Exists(TriggerRecordsPath)) { string text = File.ReadAllText(TriggerRecordsPath); List<string> list = JsonConvert.DeserializeObject<List<string>>(text); _triggeredRecords = ((list != null) ? new HashSet<string>(list) : new HashSet<string>()); } else { _triggeredRecords.Clear(); } Log.LogInfo((object)$"技能触发器记录已加载,共 {_triggeredRecords.Count} 条"); } catch (Exception arg) { Log.LogError((object)$"加载技能触发器记录失败: {arg}"); _triggeredRecords.Clear(); } } internal void SaveTriggerRecords() { try { string directoryName = Path.GetDirectoryName(TriggerRecordsPath); if (!Directory.Exists(directoryName)) { Directory.CreateDirectory(directoryName); } string contents = JsonConvert.SerializeObject((object)_triggeredRecords.ToList(), (Formatting)1); File.WriteAllText(TriggerRecordsPath, contents); Log.LogInfo((object)$"技能触发器记录已保存,共 {_triggeredRecords.Count} 条"); } catch (Exception arg) { Log.LogError((object)$"保存技能触发器记录失败: {arg}"); } } [IteratorStateMachine(typeof(<InitializeRandomizer>d__23))] private IEnumerator InitializeRandomizer() { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <InitializeRandomizer>d__23(0) { <>4__this = this }; } private void OnDestroy() { SceneManager.sceneLoaded -= OnSceneLoaded; } [IteratorStateMachine(typeof(<DisableShrinesAfterStart>d__25))] private IEnumerator DisableShrinesAfterStart() { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <DisableShrinesAfterStart>d__25(0) { <>4__this = this }; } private void OnSceneLoaded(Scene scene, LoadSceneMode mode) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) DisableShrinesInScene(scene); for (int i = 0; i < targetPositions.Count; i++) { (string, float, float, float) target = targetPositions[i]; if (target.Item1 == ((Scene)(ref scene)).name) { ((MonoBehaviour)this).StartCoroutine(CreateTriggerDelayed(target, i)); break; } } } private void DisableShrinesInScene(Scene scene) { GameObject[] rootGameObjects = ((Scene)(ref scene)).GetRootGameObjects(); GameObject[] array = rootGameObjects; foreach (GameObject val in array) { Transform[] componentsInChildren = val.GetComponentsInChildren<Transform>(true); foreach (Transform val2 in componentsInChildren) { GameObject gameObject = ((Component)val2).gameObject; string text = ((Object)gameObject).name.ToLower(); string[] array2 = shrineKeywords; foreach (string value in array2) { if (text.Contains(value)) { Collider2D[] components = gameObject.GetComponents<Collider2D>(); Collider2D[] array3 = components; foreach (Collider2D val3 in array3) { ((Behaviour)val3).enabled = false; } Collider[] components2 = gameObject.GetComponents<Collider>(); Collider[] array4 = components2; foreach (Collider val4 in array4) { val4.enabled = false; } PlayMakerFSM[] components3 = gameObject.GetComponents<PlayMakerFSM>(); PlayMakerFSM[] array5 = components3; foreach (PlayMakerFSM val5 in array5) { ((Behaviour)val5).enabled = false; } break; } } } } } [IteratorStateMachine(typeof(<CreateTriggerDelayed>d__28))] private IEnumerator CreateTriggerDelayed((string scene, float x, float y, float z) target, int index) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <CreateTriggerDelayed>d__28(0) { <>4__this = this, target = target, index = index }; } private void CreateTriggerAt(Vector3 position, string sceneName, int index) { //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Expected O, but got Unknown //IL_0047: 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_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_009b: Unknown result type (might be due to invalid IL or missing references) string text = $"SkillTriggered_{sceneName}_{index}"; if (!_triggeredRecords.Contains(text)) { GameObject val = new GameObject($"SkillTrigger_{sceneName}_{index}"); val.transform.position = position; BoxCollider2D val2 = val.AddComponent<BoxCollider2D>(); ((Collider2D)val2).isTrigger = true; val2.size = new Vector2(8f, 8f); SkillTrigger skillTrigger = val.AddComponent<SkillTrigger>(); skillTrigger.SetInfo(sceneName, index, text); Scene sceneByName = SceneManager.GetSceneByName(sceneName); if (((Scene)(ref sceneByName)).IsValid()) { SceneManager.MoveGameObjectToScene(val, sceneByName); Log.LogInfo((object)$"触发器创建: {sceneName} 索引 {index}"); } else { Log.LogError((object)("触发器创建失败: " + sceneName)); Object.Destroy((Object)(object)val); } } } public static void ResetAllRecords() { _triggeredRecords.Clear(); if ((Object)(object)Instance != (Object)null) { Instance.SaveTriggerRecords(); } Log.LogInfo((object)"所有技能触发器记录已重置"); } } public class SkillTrigger : MonoBehaviour { private bool _triggered = false; private string _sceneName; private int _index; private string _recordKey; public void SetInfo(string sceneName, int index, string recordKey) { _sceneName = sceneName; _index = index; _recordKey = recordKey; } private void OnTriggerEnter2D(Collider2D other) { if (!_triggered && (((Component)other).CompareTag("Hero") || ((Component)other).CompareTag("Player"))) { _triggered = true; if (_sceneName == "Shellwood_10") { SkillRandomizer.GiveWallJump(); } else { SkillRandomizer.GiveRandomSkill(); } Plugin._triggeredRecords.Add(_recordKey); Plugin.Instance.SaveTriggerRecords(); Object.Destroy((Object)(object)((Component)this).gameObject); } } } public static class SkillRandomizer { private static readonly Dictionary<string, string> SkillDisplayNames = new Dictionary<string, string> { { "hasNeedleThrow", "飞针" }, { "hasThreadSphere", "丝线球" }, { "hasHarpoonDash", "鱼叉冲刺" }, { "hasSilkCharge", "丝线冲刺" }, { "hasSilkBomb", "丝线炸弹" }, { "hasSilkBossNeedle", "丝线针" }, { "hasNeedolin", "针线" }, { "hasDash", "冲刺" }, { "hasBrolly", "伞" }, { "hasDoubleJump", "二段跳" }, { "hasChargeSlash", "蓄力斩" }, { "hasSuperJump", "超级跳" }, { "hasWallJump", "爬墙" } }; private static readonly List<string> AllSkillFields = SkillDisplayNames.Keys.ToList(); private static Random? _rng; private static int _currentSeed; public static void SetSeed(int seed) { _currentSeed = seed; _rng = ((seed == 0) ? new Random() : new Random(seed)); } private static void EnsureRng() { if (_rng == null) { _rng = new Random(); } } public static void GiveRandomSkill() { EnsureRng(); try { PlayerData instance = PlayerData.instance; if (instance == null) { return; } List<string> list = new List<string>(); foreach (string allSkillField in AllSkillFields) { FieldInfo field = typeof(PlayerData).GetField(allSkillField, BindingFlags.Instance | BindingFlags.Public); if (field != null && field.FieldType == typeof(bool) && !(bool)field.GetValue(instance)) { list.Add(allSkillField); } } if (list.Count == 0) { GiveWallJump(); return; } string text = list[_rng.Next(list.Count)]; FieldInfo field2 = typeof(PlayerData).GetField(text, BindingFlags.Instance | BindingFlags.Public); if (field2 != null) { field2.SetValue(instance, true); string value; string text2 = (SkillDisplayNames.TryGetValue(text, out value) ? value : text.Replace("has", "")); Plugin.ShowNotification("获得技能: " + text2); } } catch (Exception arg) { Plugin.Log.LogError((object)$"SkillRandomizer 出错: {arg}"); } } public static void GiveWallJump() { try { PlayerData instance = PlayerData.instance; if (instance == null) { return; } string[] array = new string[3] { "hasWallJump", "hasWalljump", "hasWallJumpUnlocked" }; string[] array2 = array; foreach (string name in array2) { FieldInfo field = typeof(PlayerData).GetField(name, BindingFlags.Instance | BindingFlags.Public); if (field != null && field.FieldType == typeof(bool)) { if (!(bool)field.GetValue(instance)) { field.SetValue(instance, true); Plugin.ShowNotification("获得技能: 爬墙"); } break; } } } catch (Exception arg) { Plugin.Log.LogError((object)$"GiveWallJump 出错: {arg}"); } } } }
plugins/StartingAbilityPicker.dll
Decompiled a day agousing System; using System.Collections; 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.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using Microsoft.CodeAnalysis; using Newtonsoft.Json; using UnityEngine; using UnityEngine.SceneManagement; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("StartingAbilityPicker")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("0.1.0.0")] [assembly: AssemblyInformationalVersion("0.1.0")] [assembly: AssemblyProduct("StartingAbilityPicker")] [assembly: AssemblyTitle("StartingAbilityPicker")] [assembly: AssemblyMetadata("RepositoryUrl", "https://github.com/YourGitHubUsername/StartingAbilityPicker")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.1.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 BepInEx { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class BepInAutoPluginAttribute : Attribute { public BepInAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace BepInEx.Preloader.Core.Patching { [AttributeUsage(AttributeTargets.Class, Inherited = false, AllowMultiple = false)] [Conditional("CodeGeneration")] internal sealed class PatcherAutoPluginAttribute : Attribute { public PatcherAutoPluginAttribute(string? id = null, string? name = null, string? version = null) { } } } namespace StartingAbilityPicker { [BepInPlugin("YourName.StartingAbilityPicker", "Starting Ability Picker", "1.0.0.0")] public class Plugin : BaseUnityPlugin { [CompilerGenerated] private sealed class <ShowUIAuto>d__60 : IEnumerator<object>, IEnumerator, IDisposable { private int <>1__state; private object <>2__current; public Plugin <>4__this; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <ShowUIAuto>d__60(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = null; <>1__state = 1; return true; case 1: <>1__state = -1; if (<>4__this.currentProfileID != -1) { <>4__this.allowUpward = AllowUpwardAttack; <>4__this.allowLeft = AllowLeftAttack; <>4__this.allowRight = AllowRightAttack; <>4__this.itemCount = StartingItemCount.Value; <>4__this.resetPickups = false; <>4__this.seedInput = RandomSeed.Value.ToString(); <>4__this.showUI = true; Log.LogInfo((object)"加载存档,自动打开开局选项界面"); } return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } internal static ManualLogSource Log; public static bool AllowLeftAttack = false; public static bool AllowRightAttack = false; public static bool AllowUpwardAttack = false; private static Dictionary<string, string> _abilityConfig = new Dictionary<string, string>(); private bool _sceneHazardMode = false; private int _sceneHazardCount = 2; private bool _sceneHazardUIOpen = false; private bool skillMode = false; private int skillTotal = 0; private int skillV = 0; private int skillH = 0; private int skillS = 0; private int skillA = 0; private const int MaxVertical = 5; private const int MaxHorizontal = 4; private const int MaxSpecial = 4; private const int MaxAttack = 5; private bool _lastSceneWasMenu = true; private bool showUI = false; private Rect uiWindowRect; private bool allowUpward = false; private bool allowLeft = false; private bool allowRight = false; private int itemCount = 0; private bool resetPickups = false; private string seedInput = ""; private static HashSet<int> chosenProfileSet = new HashSet<int>(); private static string _notificationMessage = null; private static float _notificationEndTime = 0f; private static GUIStyle _notificationStyle; public static ConfigEntry<string> ChosenProfiles { get; private set; } public static ConfigEntry<int> StartingSkillCount { get; private set; } public static ConfigEntry<int> StartingItemCount { get; private set; } public static ConfigEntry<int> RandomSeed { get; private set; } private static string AbilityConfigPath => Path.Combine(Paths.ConfigPath, "StartingAbilityPicker", "ability_config.json"); private int currentProfileID => ((Object)(object)GameManager.instance != (Object)null) ? GameManager.instance.profileID : (-1); public static void ShowNotification(string message, float duration = 3f) { _notificationMessage = message; _notificationEndTime = Time.time + duration; } private Texture2D MakeTexture(int width, int height, Color col) { //IL_0010: 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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Expected O, but got Unknown Color[] array = (Color[])(object)new Color[width * height]; for (int i = 0; i < array.Length; i++) { array[i] = col; } Texture2D val = new Texture2D(width, height); val.SetPixels(array); val.Apply(); return val; } private void Awake() { Log = ((BaseUnityPlugin)this).Logger; Log.LogInfo((object)"StartingAbilityPicker loaded! Press F7 to open starting options."); ChosenProfiles = ((BaseUnityPlugin)this).Config.Bind<string>("General", "ChosenProfiles", "", "已选择过开局选项的存档ID列表"); StartingSkillCount = ((BaseUnityPlugin)this).Config.Bind<int>("General", "StartingSkillCount", 0, "开局随机技能数量 (0-5)"); StartingItemCount = ((BaseUnityPlugin)this).Config.Bind<int>("General", "StartingItemCount", 0, "开局随机物品数量 (0-5)"); RandomSeed = ((BaseUnityPlugin)this).Config.Bind<int>("General", "RandomSeed", 0, "随机种子 (0 表示随机)"); LoadChosenProfiles(); EnsureRandomSeed(); LoadAbilityConfig(); SceneManager.sceneLoaded += OnSceneLoaded; Harmony.CreateAndPatchAll(typeof(AttackPatch), (string)null); } private void LoadAbilityConfig() { try { if (File.Exists(AbilityConfigPath)) { string text = File.ReadAllText(AbilityConfigPath); _abilityConfig = JsonConvert.DeserializeObject<Dictionary<string, string>>(text) ?? new Dictionary<string, string>(); } else { _abilityConfig.Clear(); } AllowUpwardAttack = _abilityConfig.TryGetValue("AllowUpwardAttack", out string value) && value == "true"; AllowLeftAttack = _abilityConfig.TryGetValue("AllowLeftAttack", out string value2) && value2 == "true"; AllowRightAttack = _abilityConfig.TryGetValue("AllowRightAttack", out string value3) && value3 == "true"; if (_abilityConfig.TryGetValue("SceneHazardMode", out string value4) && bool.TryParse(value4, out var result)) { _sceneHazardMode = result; } else { _sceneHazardMode = false; } if (_abilityConfig.TryGetValue("SceneHazardCount", out string value5) && int.TryParse(value5, out var result2)) { _sceneHazardCount = Mathf.Clamp(result2, 0, 4); } else { _sceneHazardCount = 2; } Log.LogInfo((object)$"[LoadAbilityConfig] Loaded: up={AllowUpwardAttack}, left={AllowLeftAttack}, right={AllowRightAttack}, sceneHazardMode={_sceneHazardMode}, sceneHazardCount={_sceneHazardCount}"); } catch (Exception arg) { Log.LogError((object)$"加载配置失败: {arg}"); } } private void SaveAbilityConfig() { try { _abilityConfig["AllowUpwardAttack"] = AllowUpwardAttack.ToString(); _abilityConfig["AllowLeftAttack"] = AllowLeftAttack.ToString(); _abilityConfig["AllowRightAttack"] = AllowRightAttack.ToString(); _abilityConfig["SceneHazardMode"] = _sceneHazardMode.ToString(); _abilityConfig["SceneHazardCount"] = _sceneHazardCount.ToString(); string directoryName = Path.GetDirectoryName(AbilityConfigPath); if (!Directory.Exists(directoryName)) { Directory.CreateDirectory(directoryName); } string contents = JsonConvert.SerializeObject((object)_abilityConfig, (Formatting)1); File.WriteAllText(AbilityConfigPath, contents); Log.LogInfo((object)$"[SaveAbilityConfig] Saved: up={AllowUpwardAttack}, left={AllowLeftAttack}, right={AllowRightAttack}, sceneHazardMode={_sceneHazardMode}, sceneHazardCount={_sceneHazardCount}"); } catch (Exception arg) { Log.LogError((object)$"保存配置失败: {arg}"); } } private void NotifyHazardSettings() { try { Type type = Type.GetType("SilksongItemRandomizer.Hazard.HazardSpawner, SilksongItemRandomizer"); if (type == null) { Log.LogError((object)"未找到 HazardSpawner 类型"); return; } type.GetMethod("SetSceneHazardMode", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { _sceneHazardMode }); type.GetMethod("SetSceneHazardCount", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { _sceneHazardCount }); Log.LogInfo((object)$"已通知 HazardSpawner: 模式={_sceneHazardMode}, 数量={_sceneHazardCount}"); } catch (Exception arg) { Log.LogError((object)$"反射调用失败: {arg}"); } } private void EnsureRandomSeed() { if (RandomSeed.Value == 0) { int num = new Random().Next(1, int.MaxValue); RandomSeed.Value = num; ((BaseUnityPlugin)this).Config.Save(); Log.LogInfo((object)$"已自动生成真实种子: {num}"); } } private void OnDestroy() { SceneManager.sceneLoaded -= OnSceneLoaded; } private void OnSceneLoaded(Scene scene, LoadSceneMode mode) { if (((Scene)(ref scene)).name != "Menu_Title" && ((Scene)(ref scene)).name != "Menu" && ((Scene)(ref scene)).name != "Loading" && (Object)(object)HeroController.instance != (Object)null) { if (_lastSceneWasMenu) { ((MonoBehaviour)this).StartCoroutine(ShowUIAuto()); _lastSceneWasMenu = false; } LoadAbilityConfig(); try { PlayerData instance = PlayerData.instance; if (instance != null) { skillMode = instance.GetBool("SkillRandomMode"); skillTotal = instance.GetInt("SkillTotalCount"); skillV = instance.GetInt("SkillVerticalCount"); skillH = instance.GetInt("SkillHorizontalCount"); skillS = instance.GetInt("SkillSpecialCount"); skillA = instance.GetInt("SkillAttackCount"); if (!skillMode && skillTotal == 0) { skillTotal = StartingSkillCount.Value; } } return; } catch (Exception arg) { Log.LogError((object)$"加载技能随机设置失败: {arg}"); return; } } if (((Scene)(ref scene)).name == "Menu_Title" || ((Scene)(ref scene)).name == "Menu") { _lastSceneWasMenu = true; } } [IteratorStateMachine(typeof(<ShowUIAuto>d__60))] private IEnumerator ShowUIAuto() { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <ShowUIAuto>d__60(0) { <>4__this = this }; } private void LoadChosenProfiles() { chosenProfileSet.Clear(); string[] array = ChosenProfiles.Value.Split(','); foreach (string text in array) { if (int.TryParse(text.Trim(), out var result)) { chosenProfileSet.Add(result); } } } private void SaveChosenProfiles() { ChosenProfiles.Value = string.Join(",", chosenProfileSet); ((BaseUnityPlugin)this).Config.Save(); } private void Update() { if (Input.GetKeyDown((KeyCode)288) && currentProfileID != -1) { showUI = !showUI; if (showUI) { allowUpward = AllowUpwardAttack; allowLeft = AllowLeftAttack; allowRight = AllowRightAttack; itemCount = StartingItemCount.Value; resetPickups = false; seedInput = RandomSeed.Value.ToString(); } } } private void OnGUI() { //IL_002a: 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_0038: Unknown result type (might be due to invalid IL or missing references) //IL_0044: Unknown result type (might be due to invalid IL or missing references) //IL_0058: Expected O, but got Unknown //IL_0053: Unknown result type (might be due to invalid IL or missing references) //IL_0058: 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_0098: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Expected O, but got Unknown //IL_00c5: 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) if (showUI) { uiWindowRect = new Rect(20f, (float)((Screen.height - 950) / 2), 650f, 950f); uiWindowRect = GUILayout.Window(100, uiWindowRect, new WindowFunction(DrawUIWindow), "开局选项", Array.Empty<GUILayoutOption>()); } if (_notificationMessage != null && Time.time <= _notificationEndTime) { if (_notificationStyle == null) { _notificationStyle = new GUIStyle(GUI.skin.box); _notificationStyle.fontSize = 40; _notificationStyle.alignment = (TextAnchor)4; _notificationStyle.normal.textColor = Color.white; _notificationStyle.normal.background = MakeTexture(2, 2, new Color(0f, 0f, 0f, 0.7f)); } float num = 600f; float num2 = 120f; float num3 = ((float)Screen.width - num) / 2f; float num4 = Screen.height / 2 - 100; GUI.Box(new Rect(num3, num4, num, num2), _notificationMessage, _notificationStyle); } else { _notificationMessage = null; } } private void DrawUIWindow(int windowID) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0032: 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_0212: Unknown result type (might be due to invalid IL or missing references) //IL_0285: Unknown result type (might be due to invalid IL or missing references) //IL_0120: Unknown result type (might be due to invalid IL or missing references) //IL_02a5: Unknown result type (might be due to invalid IL or missing references) //IL_029e: Unknown result type (might be due to invalid IL or missing references) //IL_01c7: Unknown result type (might be due to invalid IL or missing references) //IL_0300: Unknown result type (might be due to invalid IL or missing references) //IL_02f9: Unknown result type (might be due to invalid IL or missing references) //IL_10d7: Unknown result type (might be due to invalid IL or missing references) //IL_10f8: Unknown result type (might be due to invalid IL or missing references) //IL_035b: Unknown result type (might be due to invalid IL or missing references) //IL_0354: Unknown result type (might be due to invalid IL or missing references) //IL_112d: Unknown result type (might be due to invalid IL or missing references) //IL_1166: Unknown result type (might be due to invalid IL or missing references) //IL_118f: Unknown result type (might be due to invalid IL or missing references) //IL_03aa: Unknown result type (might be due to invalid IL or missing references) //IL_03f8: Unknown result type (might be due to invalid IL or missing references) //IL_03f1: Unknown result type (might be due to invalid IL or missing references) //IL_0455: Unknown result type (might be due to invalid IL or missing references) //IL_044e: Unknown result type (might be due to invalid IL or missing references) //IL_04a3: Unknown result type (might be due to invalid IL or missing references) //IL_0956: Unknown result type (might be due to invalid IL or missing references) //IL_094f: Unknown result type (might be due to invalid IL or missing references) //IL_09ae: Unknown result type (might be due to invalid IL or missing references) //IL_0ca0: Unknown result type (might be due to invalid IL or missing references) //IL_0c99: Unknown result type (might be due to invalid IL or missing references) //IL_0cef: Unknown result type (might be due to invalid IL or missing references) //IL_0d51: Unknown result type (might be due to invalid IL or missing references) //IL_0d07: Unknown result type (might be due to invalid IL or missing references) //IL_0d30: Unknown result type (might be due to invalid IL or missing references) Color color = GUI.color; GUI.color = Color.black; GUI.DrawTexture(new Rect(0f, 0f, ((Rect)(ref uiWindowRect)).width, ((Rect)(ref uiWindowRect)).height), (Texture)(object)Texture2D.whiteTexture); GUI.color = color; GUILayout.BeginVertical(Array.Empty<GUILayoutOption>()); GUI.skin.label.fontSize = 20; GUI.skin.toggle.fontSize = 20; GUI.skin.button.fontSize = 24; GUI.skin.horizontalSlider.fontSize = 18; GUI.skin.textField.fontSize = 18; GUILayout.Label("当前存档开局设置:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); GUILayout.Space(15f); bool flag = chosenProfileSet.Contains(currentProfileID); if (flag) { GUILayout.Label("(此存档已设置过,只能查看)", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUI.backgroundColor = new Color(0.8f, 0.5f, 0.2f); if (GUILayout.Button("重置本存档设置", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(45f) })) { chosenProfileSet.Remove(currentProfileID); SaveChosenProfiles(); flag = false; allowUpward = false; allowLeft = false; allowRight = false; itemCount = 0; resetPickups = false; skillMode = false; skillTotal = 0; skillV = (skillH = (skillS = (skillA = 0))); return; } GUI.backgroundColor = Color.white; } GUILayout.Space(20f); GUILayout.Label("攻击方向选择:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.Space(5f); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUI.color = Color.gray; GUILayout.Label("下劈 (默认)", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(200f), GUILayout.Height(40f) }); GUI.enabled = false; GUILayout.Toggle(true, "", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(40f), GUILayout.Height(40f) }); GUI.enabled = !flag; GUI.color = Color.white; GUILayout.EndHorizontal(); GUI.color = (allowUpward ? Color.green : Color.white); bool flag2 = GUILayout.Toggle(allowUpward, "上劈", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); if (flag2 != allowUpward && !flag) { allowUpward = flag2; } GUI.color = (allowLeft ? Color.green : Color.white); bool flag3 = GUILayout.Toggle(allowLeft, "左劈", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); if (flag3 != allowLeft && !flag) { allowLeft = flag3; } GUI.color = (allowRight ? Color.green : Color.white); bool flag4 = GUILayout.Toggle(allowRight, "右劈", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); if (flag4 != allowRight && !flag) { allowRight = flag4; } GUI.color = Color.white; GUILayout.Space(20f); GUILayout.Label("技能随机模式:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUI.color = (skillMode ? Color.white : Color.green); if (GUILayout.Button("总随机", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Height(40f), GUILayout.Width(150f) }) && !flag) { skillMode = false; } GUI.color = (skillMode ? Color.green : Color.white); if (GUILayout.Button("分类随机", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Height(40f), GUILayout.Width(150f) }) && !flag) { skillMode = true; } GUI.color = Color.white; GUILayout.EndHorizontal(); GUILayout.Space(10f); if (!skillMode) { GUILayout.Label("开局随机技能总数量:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(skillTotal.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num = (int)GUILayout.HorizontalSlider((float)skillTotal, 0f, 13f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num != skillTotal && !flag) { skillTotal = num; } GUILayout.EndHorizontal(); GUILayout.Space(10f); } else { GUILayout.Label("分类随机数量:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.Label($"垂直技能 (0-{5})", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(30f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(skillV.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num2 = (int)GUILayout.HorizontalSlider((float)skillV, 0f, 5f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num2 != skillV && !flag) { skillV = num2; } GUILayout.EndHorizontal(); GUILayout.Label($"水平技能 (0-{4})", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(30f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(skillH.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num3 = (int)GUILayout.HorizontalSlider((float)skillH, 0f, 4f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num3 != skillH && !flag) { skillH = num3; } GUILayout.EndHorizontal(); GUILayout.Label($"特殊技能 (0-{4})", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(30f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(skillS.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num4 = (int)GUILayout.HorizontalSlider((float)skillS, 0f, 4f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num4 != skillS && !flag) { skillS = num4; } GUILayout.EndHorizontal(); GUILayout.Label($"攻击技能 (0-{5})", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(30f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(skillA.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num5 = (int)GUILayout.HorizontalSlider((float)skillA, 0f, 5f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num5 != skillA && !flag) { skillA = num5; } GUILayout.EndHorizontal(); GUILayout.Space(10f); } GUILayout.Label("开局随机物品数量:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label(itemCount.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(35f), GUILayout.Height(40f) }); int num6 = (int)GUILayout.HorizontalSlider((float)itemCount, 0f, 10f, (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(220f) }); if (num6 != itemCount && !flag) { itemCount = num6; } GUILayout.EndHorizontal(); GUILayout.Space(15f); GUI.color = (_sceneHazardUIOpen ? Color.green : Color.white); if (GUILayout.Button("场景随机" + (_sceneHazardUIOpen ? " ▼" : " ▶"), (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) })) { _sceneHazardUIOpen = !_sceneHazardUIOpen; } GUI.color = Color.white; if (_sceneHazardUIOpen) { GUILayout.BeginVertical(GUI.skin.box, Array.Empty<GUILayoutOption>()); GUILayout.Space(10f); GUILayout.Label("场景随机设置:", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label("启用:", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(60f), GUILayout.Height(35f) }); bool flag5 = GUILayout.Toggle(_sceneHazardMode, _sceneHazardMode ? "开" : "关", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(35f) }); if (flag5 != _sceneHazardMode && !flag) { _sceneHazardMode = flag5; SaveAbilityConfig(); NotifyHazardSettings(); } GUILayout.EndHorizontal(); if (_sceneHazardMode) { GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label("每个场景生成数量:", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(150f), GUILayout.Height(35f) }); if (GUILayout.Button("-", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(40f), GUILayout.Height(35f) }) && !flag) { _sceneHazardCount = Mathf.Max(0, _sceneHazardCount - 1); SaveAbilityConfig(); NotifyHazardSettings(); } GUILayout.Label(_sceneHazardCount.ToString(), (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(40f), GUILayout.Height(35f) }); if (GUILayout.Button("+", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(40f), GUILayout.Height(35f) }) && !flag) { _sceneHazardCount = Mathf.Min(4, _sceneHazardCount + 1); SaveAbilityConfig(); NotifyHazardSettings(); } GUILayout.Label("(最大 4)", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Width(60f) }); GUILayout.EndHorizontal(); } GUILayout.Space(10f); GUILayout.EndVertical(); } GUILayout.Space(25f); GUILayout.BeginHorizontal(Array.Empty<GUILayoutOption>()); GUILayout.Label("种子", (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(60f), GUILayout.Height(40f) }); seedInput = GUILayout.TextField(seedInput, (GUILayoutOption[])(object)new GUILayoutOption[2] { GUILayout.Width(160f), GUILayout.Height(40f) }); GUILayout.EndHorizontal(); GUILayout.Space(5f); GUI.color = (resetPickups ? Color.red : Color.white); bool flag6 = GUILayout.Toggle(resetPickups, "重置种子世界(含技能触发器)", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); if (flag6 != resetPickups && !flag) { resetPickups = flag6; } GUI.color = Color.white; if (resetPickups) { GUI.color = Color.yellow; GUILayout.Label("警告:重置后当前种子世界将重新生成,所有拾取点会重生,技能触发器也会重置。", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(70f) }); GUI.color = Color.white; } GUILayout.Space(35f); GUI.enabled = !flag; GUI.backgroundColor = Color.green; if (GUILayout.Button("确认", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(50f) }) && !flag) { AllowUpwardAttack = allowUpward; AllowLeftAttack = allowLeft; AllowRightAttack = allowRight; SaveAbilityConfig(); try { PlayerData instance = PlayerData.instance; if (instance != null) { instance.SetBool("AllowUpwardAttack", allowUpward); instance.SetBool("AllowLeftAttack", allowLeft); instance.SetBool("AllowRightAttack", allowRight); instance.SetBool("SkillRandomMode", skillMode); instance.SetInt("SkillTotalCount", skillTotal); instance.SetInt("SkillVerticalCount", skillV); instance.SetInt("SkillHorizontalCount", skillH); instance.SetInt("SkillSpecialCount", skillS); instance.SetInt("SkillAttackCount", skillA); } } catch (Exception arg) { Log.LogError((object)$"保存到 PlayerData 失败: {arg}"); } StartingSkillCount.Value = skillTotal; StartingItemCount.Value = itemCount; ((BaseUnityPlugin)this).Config.Save(); chosenProfileSet.Add(currentProfileID); SaveChosenProfiles(); if (resetPickups) { ResetSeedWorld(); } if (!skillMode) { for (int i = 0; i < skillTotal; i++) { SkillRandomizer.GiveRandomSkill(); } } else { for (int j = 0; j < skillV; j++) { SkillRandomizer.GiveRandomSkillFromCategory(SkillRandomizer.VerticalSkills); } for (int k = 0; k < skillH; k++) { SkillRandomizer.GiveRandomSkillFromCategory(SkillRandomizer.HorizontalSkills); } for (int l = 0; l < skillS; l++) { SkillRandomizer.GiveRandomSkillFromCategory(SkillRandomizer.SpecialSkills); } for (int m = 0; m < skillA; m++) { SkillRandomizer.GiveRandomSkillFromCategory(SkillRandomizer.AttackSkills); } } for (int n = 0; n < itemCount; n++) { SavedItem randomItem = ItemRandomizer.GetRandomItem(); if ((Object)(object)randomItem != (Object)null) { randomItem.TryGet(false, true); } } showUI = false; Log.LogInfo((object)string.Format("开局设置已保存: 上劈={0}, 左劈={1}, 右劈={2}, 技能模式={3}, 技能V={4}, H={5}, S={6}, A={7}, 物品={8}, 重置种子={9}, 场景随机启用={10}, 数量={11}", allowUpward, allowLeft, allowRight, skillMode ? "分类" : "总", skillV, skillH, skillS, skillA, itemCount, resetPickups, _sceneHazardMode, _sceneHazardCount)); } GUI.backgroundColor = Color.white; GUI.enabled = true; GUI.backgroundColor = new Color(0.8f, 0.2f, 0.2f); if (GUILayout.Button("关闭", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) })) { showUI = false; } GUI.backgroundColor = Color.white; GUILayout.Space(15f); int fontSize = GUI.skin.label.fontSize; GUI.skin.label.fontSize = 26; GUI.color = Color.yellow; GUILayout.Label("提示: 按 F7 呼出此窗口", (GUILayoutOption[])(object)new GUILayoutOption[1] { GUILayout.Height(40f) }); GUI.color = Color.white; GUI.skin.label.fontSize = fontSize; GUILayout.EndVertical(); GUI.DragWindow(); } private void ResetSeedWorld() { int num; if (int.TryParse(seedInput, out var result)) { if (result != RandomSeed.Value) { num = result; } else { num = new Random().Next(1, int.MaxValue); Log.LogInfo((object)$"输入种子与原种子相同,自动生成新种子: {num}"); } } else { num = new Random().Next(1, int.MaxValue); Log.LogInfo((object)$"输入无效,自动生成新种子: {num}"); } seedInput = num.ToString(); RandomSeed.Value = num; ((BaseUnityPlugin)this).Config.Save(); try { string path = Path.Combine(Paths.ConfigPath, "SilksongItemRandomizer", "destroyed_pickups.json"); if (File.Exists(path)) { File.Delete(path); } } catch (Exception arg) { Log.LogError((object)$"删除拾取点记录失败: {arg}"); } try { Type type = Type.GetType("SilksongItemRandomizer.Plugin, SilksongItemRandomizer"); if (type != null) { PropertyInfo property = type.GetProperty("RandomSeed", BindingFlags.Static | BindingFlags.Public); if (property != null) { ConfigEntry<int> val = property.GetValue(null) as ConfigEntry<int>; val.Value = num; } type.GetMethod("ResetDestroyedPickupKeys", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); } } catch (Exception arg2) { Log.LogError((object)$"重置物品随机MOD内存数据失败: {arg2}"); } try { string path2 = Path.Combine(Paths.ConfigPath, "SkillTriggerMod", "trigger_records.json"); if (File.Exists(path2)) { File.Delete(path2); } Log.LogInfo((object)"已删除技能触发器记录文件"); } catch (Exception arg3) { Log.LogError((object)$"删除技能触发器记录失败: {arg3}"); } try { Type type2 = Type.GetType("SkillTriggerMod.Plugin, SkillTriggerMod"); if (type2 != null) { PropertyInfo property2 = type2.GetProperty("RandomSeed", BindingFlags.Static | BindingFlags.Public); if (property2 != null) { ConfigEntry<int> val2 = property2.GetValue(null) as ConfigEntry<int>; val2.Value = num; } Type type3 = Type.GetType("SkillTriggerMod.SkillRandomizer, SkillTriggerMod"); if (type3 != null) { type3.GetMethod("SetSeed", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { num }); } } } catch (Exception arg4) { Log.LogError((object)$"重置技能随机MOD种子失败: {arg4}"); } try { Type type4 = Type.GetType("SilksongItemRandomizer.CrestRandomizer, SilksongItemRandomizer"); if (type4 != null) { type4.GetMethod("ResetMappings", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); type4.GetMethod("Initialize", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); } Type.GetType("SilksongItemRandomizer.CrestRandomizePatch, SilksongItemRandomizer")?.GetMethod("ResetProcessedIds", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); Type.GetType("SilksongItemRandomizer.BenchRespawnPatch, SilksongItemRandomizer")?.GetMethod("ResetCooldown", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); } catch (Exception arg5) { Log.LogError((object)$"清空纹章相关标记失败: {arg5}"); } try { Type type5 = Type.GetType("SilksongItemRandomizer.Hazard.HazardSpawner, SilksongItemRandomizer"); if (type5 != null) { type5.GetMethod("SetSeed", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { num }); type5.GetMethod("ResetSceneRecords", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, null); type5.GetMethod("SetSceneHazardMode", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { _sceneHazardMode }); type5.GetMethod("SetSceneHazardCount", BindingFlags.Static | BindingFlags.Public)?.Invoke(null, new object[1] { _sceneHazardCount }); Log.LogInfo((object)"已通知 HazardSpawner 重置世界,种子已更新"); } } catch (Exception arg6) { Log.LogError((object)$"重置 HazardSpawner 世界失败: {arg6}"); } Log.LogInfo((object)"请重载当前场景以使所有随机世界重置。"); } } [HarmonyPatch(typeof(HeroController), "DoAttack")] public class AttackPatch { private static void Prefix(HeroController __instance, ref bool __runOriginal) { //IL_0174: Unknown result type (might be due to invalid IL or missing references) try { if (!__runOriginal) { return; } FieldInfo field = typeof(HeroController).GetField("inputHandler", BindingFlags.Instance | BindingFlags.NonPublic); if (field == null) { return; } object value = field.GetValue(__instance); if (value == null) { return; } FieldInfo field2 = value.GetType().GetField("inputActions", BindingFlags.Instance | BindingFlags.Public); if (field2 == null) { return; } object value2 = field2.GetValue(value); if (value2 == null) { return; } FieldInfo field3 = value2.GetType().GetField("Up"); FieldInfo field4 = value2.GetType().GetField("Down"); if (field3 == null || field4 == null) { return; } object value3 = field3.GetValue(value2); object value4 = field4.GetValue(value2); PropertyInfo propertyInfo = value3?.GetType().GetProperty("IsPressed"); if (!(propertyInfo == null)) { bool flag = (bool)propertyInfo.GetValue(value3); bool flag2 = (bool)propertyInfo.GetValue(value4); bool flag3 = true; try { FieldInfo field5 = typeof(HeroController).GetField("facingRight", BindingFlags.Instance | BindingFlags.NonPublic); flag3 = ((!(field5 != null)) ? (__instance.transform.localScale.x > 0f) : ((bool)field5.GetValue(__instance))); } catch { } bool allowUpwardAttack = Plugin.AllowUpwardAttack; bool allowLeftAttack = Plugin.AllowLeftAttack; bool allowRightAttack = Plugin.AllowRightAttack; bool flag4 = true; if (!(flag ? allowUpwardAttack : ((flag2 && (__instance.allowAttackCancellingDownspikeRecovery || !__instance.cState.onGround)) || ((!flag3) ? allowRightAttack : allowLeftAttack)))) { __runOriginal = false; } } } catch (Exception arg) { Plugin.Log.LogError((object)$"Exception in AttackPatch: {arg}"); __runOriginal = true; } } } public static class SkillRandomizer { private static readonly Dictionary<string, string> SkillDisplayNames = new Dictionary<string, string> { { "hasNeedleThrow", "飞针" }, { "hasThreadSphere", "丝线球" }, { "hasHarpoonDash", "鱼叉冲刺" }, { "hasSilkCharge", "丝线冲刺" }, { "hasSilkBomb", "丝线炸弹" }, { "hasSilkBossNeedle", "丝线针" }, { "hasNeedolin", "针线" }, { "hasDash", "冲刺" }, { "hasBrolly", "伞" }, { "hasDoubleJump", "二段跳" }, { "hasChargeSlash", "蓄力斩" }, { "hasSuperJump", "超级跳" }, { "hasWallJump", "爬墙" } }; public static readonly List<string> VerticalSkills = new List<string> { "hasSuperJump", "hasDoubleJump", "hasWallJump", "hasBrolly", "hasHarpoonDash" }; public static readonly List<string> HorizontalSkills = new List<string> { "hasDash", "hasBrolly", "hasHarpoonDash", "hasSilkCharge" }; public static readonly List<string> SpecialSkills = new List<string> { "hasNeedolin", "hasChargeSlash", "hasBrolly", "hasHarpoonDash" }; public static readonly List<string> AttackSkills = new List<string> { "hasSilkBomb", "hasSilkBossNeedle", "hasThreadSphere", "hasSilkSpear", "hasSilkCharge" }; private static readonly List<string> AllSkillFields = SkillDisplayNames.Keys.ToList(); private static Random? _rng; private static int _currentSeed; public static void SetSeed(int seed) { _currentSeed = seed; _rng = ((seed == 0) ? new Random() : new Random(seed)); } public static void ResetSeed() { SetSeed(_currentSeed); } private static void EnsureRng() { if (_rng == null) { _rng = new Random(); Plugin.Log.LogWarning((object)"SkillRandomizer RNG was not initialized, using default seed."); } } public static void GiveRandomSkill() { EnsureRng(); try { PlayerData playerData = PlayerData.instance; if (playerData == null) { return; } List<string> list = AllSkillFields.Where(delegate(string fieldName) { FieldInfo field2 = typeof(PlayerData).GetField(fieldName, BindingFlags.Instance | BindingFlags.Public); if (field2 != null && field2.FieldType == typeof(bool)) { bool flag = (bool)field2.GetValue(playerData); return !flag; } return false; }).ToList(); if (list.Count == 0) { GiveWallJump(); return; } string text = list[_rng.Next(list.Count)]; FieldInfo field = typeof(PlayerData).GetField(text, BindingFlags.Instance | BindingFlags.Public); if (field != null) { field.SetValue(playerData, true); string value; string text2 = (SkillDisplayNames.TryGetValue(text, out value) ? value : text.Replace("has", "")); Plugin.ShowNotification("获得技能: " + text2); } } catch (Exception arg) { Plugin.Log.LogError((object)$"SkillRandomizer 出错: {arg}"); } } public static void GiveRandomSkillFromCategory(List<string> categoryFields) { EnsureRng(); try { PlayerData playerData = PlayerData.instance; if (playerData == null) { return; } List<string> list = categoryFields.Where(delegate(string fieldName) { FieldInfo field2 = typeof(PlayerData).GetField(fieldName, BindingFlags.Instance | BindingFlags.Public); if (field2 != null && field2.FieldType == typeof(bool)) { bool flag = (bool)field2.GetValue(playerData); return !flag; } return false; }).ToList(); if (list.Count != 0) { string text = list[_rng.Next(list.Count)]; FieldInfo field = typeof(PlayerData).GetField(text, BindingFlags.Instance | BindingFlags.Public); if (field != null) { field.SetValue(playerData, true); string value; string text2 = (SkillDisplayNames.TryGetValue(text, out value) ? value : text.Replace("has", "")); Plugin.ShowNotification("获得技能: " + text2); } } } catch (Exception arg) { Plugin.Log.LogError((object)$"SkillRandomizer 出错: {arg}"); } } public static void GiveWallJump() { try { PlayerData instance = PlayerData.instance; if (instance == null) { return; } string[] array = new string[3] { "hasWallJump", "hasWalljump", "hasWallJumpUnlocked" }; string[] array2 = array; foreach (string name in array2) { FieldInfo field = typeof(PlayerData).GetField(name, BindingFlags.Instance | BindingFlags.Public); if (field != null && field.FieldType == typeof(bool)) { if (!(bool)field.GetValue(instance)) { field.SetValue(instance, true); Plugin.ShowNotification("获得技能: 爬墙"); } break; } } } catch (Exception arg) { Plugin.Log.LogError((object)$"GiveWallJump 出错: {arg}"); } } } public static class ItemRandomizer { private static List<SavedItem> _allItems; private static Random _rng = new Random(); public static SavedItem GetRandomItem() { if (_allItems == null) { _allItems = (from item in Resources.FindObjectsOfTypeAll<SavedItem>() where item is CollectableItem || item is ToolBase select item).ToList(); } if (_allItems.Count == 0) { return null; } return _allItems[_rng.Next(_allItems.Count)]; } } }