ChainloaderHooks

This commit is contained in:
js6pak committed 2021-06-13 16:15:46 +02:00
1 parent 1b077ed6ad
commit ad95e34fa4
8 files changed
+74 -27

No files matched your search

+1 -1
View File
@@ -14,7 +14,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Reactor.MSBuild" Version="0.1.1" />
<PackageReference Include="Reactor.MSBuild" Version="0.1.2" />
</ItemGroup>
<Target Name="Copy" AfterTargets="Build" Condition="'$(AmongUs)' != ''">
-2
View File
@@ -24,8 +24,6 @@ namespace Reactor.Debugger
public override void Load()
{
RegisterInIl2CppAttribute.Register();
var gameObject = new GameObject(nameof(DebuggerPlugin)).DontDestroy();
Component = gameObject.AddComponent<DebuggerComponent>();
-3
View File
@@ -17,9 +17,6 @@ namespace Reactor.Example
public override void Load()
{
RegisterInIl2CppAttribute.Register();
RegisterCustomRpcAttribute.Register(this);
var gameObject = new GameObject(nameof(ReactorPlugin)).DontDestroy();
gameObject.AddComponent<ExampleComponent>().Plugin = this;
}
+34
View File
@@ -0,0 +1,34 @@
using System.Collections.Generic;
using System.Reflection.Emit;
using BepInEx.IL2CPP;
using HarmonyLib;
namespace Reactor
{
public static class ChainloaderHooks
{
public delegate void PluginLoadHandler(BasePlugin plugin);
public static event PluginLoadHandler PluginLoad;
internal static void OnPluginLoad(BasePlugin plugin)
{
PluginLoad?.Invoke(plugin);
}
[HarmonyPatch(typeof(IL2CPPChainloader), nameof(IL2CPPChainloader.LoadPlugin))]
private static class LoadPluginPatch
{
public static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions)
{
return new CodeMatcher(instructions)
.MatchForward(false, new CodeMatch(OpCodes.Callvirt, AccessTools.Method(typeof(BasePlugin), nameof(BasePlugin.Load))))
.Insert(
new CodeInstruction(OpCodes.Dup),
new CodeInstruction(OpCodes.Call, AccessTools.Method(typeof(ChainloaderHooks), nameof(OnPluginLoad)))
)
.InstructionEnumeration();
}
}
}
}
+9 -12
View File
@@ -1,5 +1,5 @@
using System;
using System.Linq;
using System.Reflection;
using BepInEx.IL2CPP;
namespace Reactor
@@ -8,19 +8,16 @@ namespace Reactor
{
private static T _instance;
public static T Instance
public static T Instance => _instance ??= IL2CPPChainloader.Instance.Plugins.Values.Select(x => x.Instance).OfType<T>().Single();
internal static void Initialize()
{
get => _instance ??= IL2CPPChainloader.Instance.Plugins.Values.Select(x => x.Instance).OfType<T>().Single();
set
ChainloaderHooks.PluginLoad += plugin =>
{
if (_instance != null)
{
throw new Exception($"Instance for {typeof(T).FullName} is already set");
}
_instance = value;
}
typeof(PluginSingleton<>).MakeGenericType(plugin.GetType())!
.GetField(nameof(_instance), BindingFlags.Static | BindingFlags.NonPublic)!
.SetValue(null, plugin);
};
}
}
}
+16 -3
View File
@@ -27,17 +27,25 @@ namespace Reactor
private GameObject _gameObject;
private RegionInfoWatcher RegionInfoWatcher { get; } = new RegionInfoWatcher();
public ReactorPlugin()
{
PluginSingleton<BasePlugin>.Initialize();
RegisterInIl2CppAttribute.Initialize();
RegisterCustomRpcAttribute.Initialize();
ChainloaderHooks.OnPluginLoad(this);
}
public override void Load()
{
RegisterInIl2CppAttribute.Register();
AllowVanillaServers = Config.Bind("Features", "Allow vanilla servers", false, "Whether reactor should ignore servers not responding to modded handshake. This config is ignored if any plugin uses custom rpcs!");
Harmony.PatchAll();
_gameObject = new GameObject(nameof(ReactorPlugin)).DontDestroy();
_gameObject.AddComponent<ReactorComponent>().Plugin = this;
_gameObject.AddComponent<Coroutines.Component>();
Harmony.PatchAll();
ReactorVersionShower.Initialize();
SplashSkip.Initialize();
DefaultBundle.Load();
@@ -62,6 +70,11 @@ namespace Reactor
{
}
private void OnRenderImage(RenderTexture src, RenderTexture dest)
{
Plugin.Log.LogWarning(src.GetInstanceID());
}
private void Update()
{
if (Plugin.RegionInfoWatcher.Reload)
+6 -1
View File
@@ -19,9 +19,9 @@ namespace Reactor
Id = id;
}
[Obsolete("You don't need to call this anymore", true)]
public static void Register(BasePlugin plugin)
{
Register(Assembly.GetCallingAssembly(), plugin);
}
public static void Register(Assembly assembly, BasePlugin plugin)
@@ -42,5 +42,10 @@ namespace Reactor
}
}
}
internal static void Initialize()
{
ChainloaderHooks.PluginLoad += plugin => Register(plugin.GetType().Assembly, plugin);
}
}
}
+8 -5
View File
@@ -7,14 +7,14 @@ using UnhollowerRuntimeLib;
namespace Reactor
{
/// <summary>
/// Utility attribute for automatically calling <see cref="UnhollowerRuntimeLib.ClassInjector.RegisterTypeInIl2Cpp{T}"/>
/// Utility attribute for automatically calling <see cref="ClassInjector.RegisterTypeInIl2Cpp{T}()"/>
/// </summary>
[AttributeUsage(AttributeTargets.Class)]
public class RegisterInIl2CppAttribute : Attribute
{
[Obsolete("You don't need to call this anymore", true)]
public static void Register()
{
Register(Assembly.GetCallingAssembly());
}
private static readonly AccessTools.FieldRef<object, HashSet<string>> _injectedTypes
@@ -58,9 +58,7 @@ namespace Reactor
try
{
typeof(ClassInjector).GetMethod(nameof(ClassInjector.RegisterTypeInIl2Cpp))!
.MakeGenericMethod(type)
.Invoke(null, new object[0]);
ClassInjector.RegisterTypeInIl2Cpp(type);
}
catch (Exception e)
{
@@ -78,5 +76,10 @@ namespace Reactor
}
}
}
internal static void Initialize()
{
ChainloaderHooks.PluginLoad += plugin => Register(plugin.GetType().Assembly);
}
}
}