Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of Starstorm2 JP v1.1.0
plugins/Starstorm2Japanese.dll
Decompiled 2 days agousing System; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using System.Runtime.Serialization; using System.Runtime.Serialization.Json; using System.Runtime.Versioning; using BepInEx; using BepInEx.Bootstrap; using HarmonyLib; using MSU; using Microsoft.CodeAnalysis; using R2API.Utils; using RoR2; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("Starstorm2Japanese")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.1.0.0")] [assembly: AssemblyInformationalVersion("1.1.0")] [assembly: AssemblyProduct("Starstorm2Japanese")] [assembly: AssemblyTitle("Starstorm2Japanese")] [assembly: AssemblyVersion("1.1.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [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] [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] [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 LocalTranslations { [DataContract] public sealed class LanguageFile { [DataMember(Name = "strings")] public Dictionary<string, string> Strings = new Dictionary<string, string>(); } public static class Catalog { public static Dictionary<string, string> LoadFolder(string directory) { Dictionary<string, string> dictionary = new Dictionary<string, string>(StringComparer.Ordinal); string[] files = Directory.GetFiles(directory, "*.json"); Array.Sort(files, (IComparer<string>?)StringComparer.Ordinal); if (files.Length == 0) { throw new InvalidDataException("No translation files: " + directory); } DataContractJsonSerializer dataContractJsonSerializer = new DataContractJsonSerializer(typeof(LanguageFile), new DataContractJsonSerializerSettings { UseSimpleDictionaryFormat = true }); string[] array = files; foreach (string text in array) { using FileStream stream = File.OpenRead(text); foreach (KeyValuePair<string, string> @string in (((LanguageFile)dataContractJsonSerializer.ReadObject(stream)) ?? throw new InvalidDataException("Empty JSON document: " + text)).Strings) { if (string.IsNullOrWhiteSpace(@string.Key) || @string.Value == null) { throw new InvalidDataException("Invalid token in " + text); } if (dictionary.ContainsKey(@string.Key)) { throw new InvalidDataException("Duplicate token: " + @string.Key); } dictionary.Add(@string.Key, @string.Value); } } return dictionary; } } public static class LiteralTranslationPatch { private static readonly Dictionary<MethodBase, HashSet<string>> targets = new Dictionary<MethodBase, HashSet<string>>(); public static void Install(Harmony harmony, MethodBase method, IEnumerable<string> literals) { //IL_002a: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Expected O, but got Unknown targets.Add(method, new HashSet<string>(literals, StringComparer.Ordinal)); harmony.Patch(method, (HarmonyMethod)null, (HarmonyMethod)null, new HarmonyMethod(typeof(LiteralTranslationPatch), "Transpile", (Type[])null), (HarmonyMethod)null, (HarmonyMethod)null); } public static IEnumerable<CodeInstruction> Transpile(IEnumerable<CodeInstruction> instructions, MethodBase __originalMethod) { HashSet<string> selected = targets[__originalMethod]; MethodInfo getter = AccessTools.Method(typeof(Language), "GetString", new Type[1] { typeof(string) }, (Type[])null); HashSet<string> found = new HashSet<string>(); foreach (CodeInstruction instruction in instructions) { yield return instruction; if (instruction.opcode == OpCodes.Ldstr && instruction.operand is string item && selected.Contains(item)) { found.Add(item); yield return new CodeInstruction(OpCodes.Call, (object)getter); } } if (!selected.SetEquals(found)) { throw new InvalidOperationException("Original display text changed: " + __originalMethod); } } } } namespace LocalTranslations.Starstorm2Japanese { [BepInPlugin("localtranslations.starstorm2.japanese", "Starstorm2 JP", "1.1.0")] [BepInDependency("com.TeamMoonstorm", "0.6.41")] [NetworkCompatibility(/*Could not decode attribute arguments.*/)] public sealed class Plugin : BaseUnityPlugin { private Harmony? harmony; private void Awake() { //IL_0065: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Expected O, but got Unknown if (!((BaseUnityPlugin)this).Config.Bind<bool>("General", "Enabled", true, "Starstorm 2の日本語訳を有効にします。変更後はゲームを再起動してください。日本語表示だけを変更します。").Value) { return; } try { Dictionary<string, string> dictionary = Catalog.LoadFolder(Path.Combine(Path.GetDirectoryName(((BaseUnityPlugin)this).Info.Location), "translations", "ja")); LanguageFileLoader.AddLanguageFilesFromMod((BaseUnityPlugin)(object)this, "translations"); harmony = new Harmony(((BaseUnityPlugin)this).Info.Metadata.GUID); Assembly assembly = ((object)Chainloader.PluginInfos["com.TeamMoonstorm"].Instance).GetType().Assembly; (string, string)[] array = new(string, string)[2] { ("SS2.EliteEventMissionController+EliteObjectiveTracker", "elite kills heehaw: {0}%"), ("SS2.Components.StormController+StormObjectiveTracker", "effectIntensity: {0} hehe storm level {1}, {2}%") }; for (int i = 0; i < array.Length; i++) { (string, string) tuple = array[i]; try { MethodInfo method = AccessTools.Method(assembly.GetType(tuple.Item1, throwOnError: true), "GenerateString", (Type[])null, (Type[])null) ?? throw new MissingMethodException(tuple.Item1, "GenerateString"); LiteralTranslationPatch.Install(harmony, method, new string[1] { tuple.Item2 }); } catch (Exception ex) { ((BaseUnityPlugin)this).Logger.LogWarning((object)("Could not localize objective " + tuple.Item1 + ": " + ex)); } } ((BaseUnityPlugin)this).Logger.LogInfo((object)$"Registered {dictionary.Count} Japanese tokens for Starstorm 2 package 0.6.44 (MSU formatting enabled)."); } catch (Exception ex2) { ((BaseUnityPlugin)this).Logger.LogError((object)("Japanese dictionary could not be loaded; original text remains available. " + ex2)); } } private void OnDestroy() { Harmony? obj = harmony; if (obj != null) { obj.UnpatchSelf(); } } } }