mirror of
https://github.com/NuclearPowered/Reactor.git
synced 2026-10-19 15:51:54 +00:00
ChainloaderHooks
This commit is contained in:
8 files changed
+74
-27
No files matched your search
+1
-1
@@ -14,7 +14,7 @@
|
|||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Reactor.MSBuild" Version="0.1.1" />
|
<PackageReference Include="Reactor.MSBuild" Version="0.1.2" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<Target Name="Copy" AfterTargets="Build" Condition="'$(AmongUs)' != ''">
|
<Target Name="Copy" AfterTargets="Build" Condition="'$(AmongUs)' != ''">
|
||||||
|
|||||||
@@ -24,8 +24,6 @@ namespace Reactor.Debugger
|
|||||||
|
|
||||||
public override void Load()
|
public override void Load()
|
||||||
{
|
{
|
||||||
RegisterInIl2CppAttribute.Register();
|
|
||||||
|
|
||||||
var gameObject = new GameObject(nameof(DebuggerPlugin)).DontDestroy();
|
var gameObject = new GameObject(nameof(DebuggerPlugin)).DontDestroy();
|
||||||
Component = gameObject.AddComponent<DebuggerComponent>();
|
Component = gameObject.AddComponent<DebuggerComponent>();
|
||||||
|
|
||||||
|
|||||||
@@ -17,9 +17,6 @@ namespace Reactor.Example
|
|||||||
|
|
||||||
public override void Load()
|
public override void Load()
|
||||||
{
|
{
|
||||||
RegisterInIl2CppAttribute.Register();
|
|
||||||
RegisterCustomRpcAttribute.Register(this);
|
|
||||||
|
|
||||||
var gameObject = new GameObject(nameof(ReactorPlugin)).DontDestroy();
|
var gameObject = new GameObject(nameof(ReactorPlugin)).DontDestroy();
|
||||||
gameObject.AddComponent<ExampleComponent>().Plugin = this;
|
gameObject.AddComponent<ExampleComponent>().Plugin = this;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -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();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
using System;
|
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
using BepInEx.IL2CPP;
|
using BepInEx.IL2CPP;
|
||||||
|
|
||||||
namespace Reactor
|
namespace Reactor
|
||||||
@@ -8,19 +8,16 @@ namespace Reactor
|
|||||||
{
|
{
|
||||||
private static T _instance;
|
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();
|
ChainloaderHooks.PluginLoad += plugin =>
|
||||||
|
|
||||||
set
|
|
||||||
{
|
{
|
||||||
if (_instance != null)
|
typeof(PluginSingleton<>).MakeGenericType(plugin.GetType())!
|
||||||
{
|
.GetField(nameof(_instance), BindingFlags.Static | BindingFlags.NonPublic)!
|
||||||
throw new Exception($"Instance for {typeof(T).FullName} is already set");
|
.SetValue(null, plugin);
|
||||||
}
|
};
|
||||||
|
|
||||||
_instance = value;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -27,17 +27,25 @@ namespace Reactor
|
|||||||
private GameObject _gameObject;
|
private GameObject _gameObject;
|
||||||
private RegionInfoWatcher RegionInfoWatcher { get; } = new RegionInfoWatcher();
|
private RegionInfoWatcher RegionInfoWatcher { get; } = new RegionInfoWatcher();
|
||||||
|
|
||||||
|
public ReactorPlugin()
|
||||||
|
{
|
||||||
|
PluginSingleton<BasePlugin>.Initialize();
|
||||||
|
RegisterInIl2CppAttribute.Initialize();
|
||||||
|
RegisterCustomRpcAttribute.Initialize();
|
||||||
|
|
||||||
|
ChainloaderHooks.OnPluginLoad(this);
|
||||||
|
}
|
||||||
|
|
||||||
public override void Load()
|
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!");
|
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 = new GameObject(nameof(ReactorPlugin)).DontDestroy();
|
||||||
_gameObject.AddComponent<ReactorComponent>().Plugin = this;
|
_gameObject.AddComponent<ReactorComponent>().Plugin = this;
|
||||||
_gameObject.AddComponent<Coroutines.Component>();
|
_gameObject.AddComponent<Coroutines.Component>();
|
||||||
|
|
||||||
Harmony.PatchAll();
|
|
||||||
ReactorVersionShower.Initialize();
|
ReactorVersionShower.Initialize();
|
||||||
SplashSkip.Initialize();
|
SplashSkip.Initialize();
|
||||||
DefaultBundle.Load();
|
DefaultBundle.Load();
|
||||||
@@ -62,6 +70,11 @@ namespace Reactor
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void OnRenderImage(RenderTexture src, RenderTexture dest)
|
||||||
|
{
|
||||||
|
Plugin.Log.LogWarning(src.GetInstanceID());
|
||||||
|
}
|
||||||
|
|
||||||
private void Update()
|
private void Update()
|
||||||
{
|
{
|
||||||
if (Plugin.RegionInfoWatcher.Reload)
|
if (Plugin.RegionInfoWatcher.Reload)
|
||||||
|
|||||||
@@ -19,9 +19,9 @@ namespace Reactor
|
|||||||
Id = id;
|
Id = id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Obsolete("You don't need to call this anymore", true)]
|
||||||
public static void Register(BasePlugin plugin)
|
public static void Register(BasePlugin plugin)
|
||||||
{
|
{
|
||||||
Register(Assembly.GetCallingAssembly(), plugin);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void Register(Assembly assembly, BasePlugin 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);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -7,14 +7,14 @@ using UnhollowerRuntimeLib;
|
|||||||
namespace Reactor
|
namespace Reactor
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Utility attribute for automatically calling <see cref="UnhollowerRuntimeLib.ClassInjector.RegisterTypeInIl2Cpp{T}"/>
|
/// Utility attribute for automatically calling <see cref="ClassInjector.RegisterTypeInIl2Cpp{T}()"/>
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[AttributeUsage(AttributeTargets.Class)]
|
[AttributeUsage(AttributeTargets.Class)]
|
||||||
public class RegisterInIl2CppAttribute : Attribute
|
public class RegisterInIl2CppAttribute : Attribute
|
||||||
{
|
{
|
||||||
|
[Obsolete("You don't need to call this anymore", true)]
|
||||||
public static void Register()
|
public static void Register()
|
||||||
{
|
{
|
||||||
Register(Assembly.GetCallingAssembly());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static readonly AccessTools.FieldRef<object, HashSet<string>> _injectedTypes
|
private static readonly AccessTools.FieldRef<object, HashSet<string>> _injectedTypes
|
||||||
@@ -58,9 +58,7 @@ namespace Reactor
|
|||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
typeof(ClassInjector).GetMethod(nameof(ClassInjector.RegisterTypeInIl2Cpp))!
|
ClassInjector.RegisterTypeInIl2Cpp(type);
|
||||||
.MakeGenericMethod(type)
|
|
||||||
.Invoke(null, new object[0]);
|
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@@ -78,5 +76,10 @@ namespace Reactor
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal static void Initialize()
|
||||||
|
{
|
||||||
|
ChainloaderHooks.PluginLoad += plugin => Register(plugin.GetType().Assembly);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Reference in new issue
Block a user