Skip to content

Commit

Permalink
Merge pull request #14 from BUTR/dev
Browse files Browse the repository at this point in the history
v1.0.8
  • Loading branch information
Aragas authored Aug 30, 2020
2 parents d67ddc8 + 3e3e8be commit 0a33eb2
Show file tree
Hide file tree
Showing 4 changed files with 35 additions and 3 deletions.
2 changes: 1 addition & 1 deletion build/common.props
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<!--Development Variables-->
<PropertyGroup>
<!--Module Version-->
<Version>1.0.7</Version>
<Version>1.0.8</Version>
<!--Harmony Version-->
<HarmonyVersion>2.0.2</HarmonyVersion>
<!--Current Bannerlord Stable Version-->
Expand Down
4 changes: 4 additions & 0 deletions changelog.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
---------------------------------------------------------------------------------------------------
Version: 1.0.8
Game Versions: e1.4.3,e1.5.0,e1.5.1
* Added GetDelegate from ConstructorInfo
---------------------------------------------------------------------------------------------------
Version: 1.0.7
Game Versions: e1.4.3,e1.5.0,e1.5.1
* Restored Delegate method
Expand Down
20 changes: 20 additions & 0 deletions src/Bannerlord.ButterLib/Common/Helpers/AccessTools2.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,26 @@ namespace Bannerlord.ButterLib.Common.Helpers
/// <summary>An extension of Harmony's helper class for reflection related functions</summary>
public static class AccessTools2
{
public static TDelegate? GetDelegate<TDelegate>(ConstructorInfo constructorInfo) where TDelegate : Delegate
{
var parameters = constructorInfo.GetParameters().Select((p, i) => Expression.Parameter(p.ParameterType, $"p{i}")).ToList();
var newExpression = Expression.New(constructorInfo, parameters);
return Expression.Lambda<TDelegate>(newExpression, parameters).Compile();
}

public static TDelegate? GetConstructorDelegate<TDelegate>(Type type, Type[]? parameters = null) where TDelegate : Delegate
{
var constructorInfo = Constructor(type, parameters);
return GetDelegate<TDelegate>(constructorInfo);
}

public static TDelegate? GetDeclaredConstructorDelegate<TDelegate>(Type type, Type[]? parameters = null) where TDelegate : Delegate
{
var constructorInfo = DeclaredConstructor(type, parameters);
return GetDelegate<TDelegate>(constructorInfo);
}


/// <summary>Allows to use object as Delegate's instance type.</summary>
/// <param name="type">The type where the method is declared</param>
/// <param name="method">The name of the method (case sensitive)</param>
Expand Down
12 changes: 10 additions & 2 deletions src/Bannerlord.ButterLib/ImplementationLoaderSubModule.cs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ namespace Bannerlord.ButterLib
/// </summary>
public sealed class ImplementationLoaderSubModule : MBSubModuleBaseListWrapper
{
private delegate MBSubModuleBase ConstructorDelegate();

private static IEnumerable<MBSubModuleBase> LoadAllImplementations(ILogger? logger)
{
logger?.LogInformation("Loading implementations...");
Expand Down Expand Up @@ -135,8 +137,14 @@ private static IEnumerable<MBSubModuleBase> LoadAllImplementations(ILogger? logg
continue;
}

if (constructor.Invoke(Array.Empty<object>()) is MBSubModuleBase subModule)
yield return subModule;
var constructorFunc = AccessTools2.GetDelegate<ConstructorDelegate>(constructor);
if (constructorFunc == null)
{
logger?.LogError("SubModule {subModuleType}'s default constructor could not be converted to a delegate!", subModuleType);
continue;
}

yield return constructorFunc();
}

logger?.LogInformation("Finished loading implementations.");
Expand Down

0 comments on commit 0a33eb2

Please sign in to comment.