parent
af2f460356
commit
5b5b6bd483
|
@ -12,7 +12,7 @@ namespace BizHawk.Client.Common
|
|||
|
||||
public IReadOnlyCollection<Type> AvailableApis => _libs.Keys.ToList();
|
||||
|
||||
public BasicApiProvider(IReadOnlyDictionary<Type, IExternalApi> libs) => _libs = libs;
|
||||
public BasicApiProvider(IApiContainer apiContainer) => _libs = apiContainer.Libraries;
|
||||
|
||||
public object? GetApi(Type t) => _libs.TryGetValue(t, out var api) ? api : null;
|
||||
|
||||
|
|
|
@ -1,39 +1,49 @@
|
|||
using System;
|
||||
#nullable enable
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
|
||||
using BizHawk.Emulation.Common;
|
||||
using BizHawk.Client.Common;
|
||||
using BizHawk.Emulation.Common;
|
||||
|
||||
namespace BizHawk.Client.EmuHawk
|
||||
|
||||
{
|
||||
public static class ApiManager
|
||||
{
|
||||
/// <remarks>TODO do we need to keep this reference around? --yoshi</remarks>
|
||||
private static ApiContainer _container;
|
||||
private static readonly Type[] CtorParamTypes = { typeof(Action<string>) };
|
||||
|
||||
private static IExternalApiProvider Register(IEmulatorServiceProvider serviceProvider)
|
||||
/// <remarks>TODO do we need to keep references to these because of GC weirdness? --yoshi</remarks>
|
||||
private static ApiContainer? _container;
|
||||
|
||||
private static ApiContainer? _luaContainer;
|
||||
|
||||
private static ApiContainer Register(IEmulatorServiceProvider serviceProvider, Action<string> logCallback)
|
||||
{
|
||||
var ctorParamTypes = CtorParamTypes;
|
||||
var libDict = new Dictionary<Type, IExternalApi>();
|
||||
foreach (var api in Assembly.GetAssembly(typeof(ApiSubsetContainer)).GetTypes()
|
||||
.Concat(Assembly.GetAssembly(typeof(ApiContainer)).GetTypes())
|
||||
.Where(t => /*t.IsClass && */t.IsSealed && typeof(IExternalApi).IsAssignableFrom(t) && ServiceInjector.IsAvailable(serviceProvider, t)))
|
||||
.Where(t => /*t.IsClass && */t.IsSealed
|
||||
&& typeof(IExternalApi).IsAssignableFrom(t)
|
||||
&& ServiceInjector.IsAvailable(serviceProvider, t)))
|
||||
{
|
||||
var instance = (IExternalApi)Activator.CreateInstance(api);
|
||||
var instance = api.GetConstructor(ctorParamTypes)?.Invoke(new object[] { logCallback })
|
||||
?? Activator.CreateInstance(api);
|
||||
ServiceInjector.UpdateServices(serviceProvider, instance);
|
||||
Libraries.Add(api.GetInterfaces().First(intf => typeof(IExternalApi).IsAssignableFrom(intf) && intf != typeof(IExternalApi)), instance);
|
||||
libDict.Add(
|
||||
api.GetInterfaces().First(intf => typeof(IExternalApi).IsAssignableFrom(intf) && intf != typeof(IExternalApi)),
|
||||
(IExternalApi) instance
|
||||
);
|
||||
}
|
||||
_container = new ApiContainer(Libraries);
|
||||
return new BasicApiProvider(Libraries);
|
||||
return new ApiContainer(libDict);
|
||||
}
|
||||
|
||||
private static readonly Dictionary<Type, IExternalApi> Libraries = new Dictionary<Type, IExternalApi>();
|
||||
|
||||
public static IExternalApiProvider Restart(IEmulatorServiceProvider newServiceProvider)
|
||||
{
|
||||
Libraries.Clear();
|
||||
return Register(newServiceProvider);
|
||||
}
|
||||
=> new BasicApiProvider(_container = Register(newServiceProvider, Console.WriteLine));
|
||||
|
||||
public static ApiContainer RestartLua(IEmulatorServiceProvider newServiceProvider, Action<string> logCallback)
|
||||
=> _luaContainer = Register(newServiceProvider, logCallback);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -27,23 +27,6 @@ namespace BizHawk.Client.EmuHawk
|
|||
{
|
||||
_mainForm = mainForm;
|
||||
|
||||
static ApiContainer InitApiContainer(IEmulatorServiceProvider sp, Action<string> logCallback)
|
||||
{
|
||||
var ctorParamTypes = new[] { typeof(Action<string>) };
|
||||
var ctorParams = new object[] { logCallback };
|
||||
var libDict = new Dictionary<Type, IExternalApi>();
|
||||
foreach (var api in Assembly.GetAssembly(typeof(EmuApi)).GetTypes()
|
||||
.Concat(Assembly.GetAssembly(typeof(ToolApi)).GetTypes())
|
||||
.Where(t => t.IsSealed && typeof(IExternalApi).IsAssignableFrom(t) && ServiceInjector.IsAvailable(sp, t)))
|
||||
{
|
||||
var ctorWithParams = api.GetConstructor(ctorParamTypes);
|
||||
var instance = (IExternalApi) (ctorWithParams == null ? Activator.CreateInstance(api) : ctorWithParams.Invoke(ctorParams));
|
||||
ServiceInjector.UpdateServices(sp, instance);
|
||||
libDict.Add(api, instance);
|
||||
}
|
||||
return ApiContainerInstance = new ApiContainer(libDict);
|
||||
}
|
||||
|
||||
LuaWait = new AutoResetEvent(false);
|
||||
Docs.Clear();
|
||||
|
||||
|
@ -73,7 +56,7 @@ namespace BizHawk.Client.EmuHawk
|
|||
clientLib.MainForm = _mainForm;
|
||||
}
|
||||
|
||||
ApiContainerInstance = InitApiContainer(serviceProvider, ConsoleLuaLibrary.LogOutput);
|
||||
ApiContainerInstance = ApiManager.RestartLua(serviceProvider, ConsoleLuaLibrary.LogOutput);
|
||||
if (instance is DelegatingLuaLibraryEmu dlgInstanceEmu) dlgInstanceEmu.APIs = ApiContainerInstance; // this is necessary as the property has the `new` modifier
|
||||
else if (instance is DelegatingLuaLibrary dlgInstance) dlgInstance.APIs = ApiContainerInstance;
|
||||
|
||||
|
|
Loading…
Reference in New Issue