PkmnLibRSharp/PkmnLibRSharp/Utils/Resolver.cs

218 lines
9.0 KiB
C#

using System;
using System.Collections.Generic;
using System.Reflection;
using PkmnLibSharp.DynamicData;
using PkmnLibSharp.DynamicData.Libraries;
using PkmnLibSharp.StaticData;
using PkmnLibSharp.StaticData.Libraries;
namespace PkmnLibSharp.Utils
{
/// <summary>
/// This class is used to resolve FFIHandles to their respective classes. We use this so we can handle inheritance
/// in our objects. By overriding a method in this class, we can return a different object than the default throughout
/// the library.
///
/// This class is a singleton, so you can replace the default resolver with your own by setting the Instance property.
/// </summary>
public class Resolver
{
/// <summary>
/// The global resolver instance. This is used throughout the library to resolve FFIHandles to their respective
/// classes.
/// </summary>
public static Resolver Instance { get; set; } = new();
private static readonly Dictionary<FFIHandle, object> Instances = new();
/// <summary>
/// Either returns an existing instance of the given type, or creates a new one and returns it.
/// </summary>
protected static T GetOrCreateInstance<T>(FFIHandle handle)
{
if (!Instances.TryGetValue(handle, out var instance))
{
instance = typeof(T)
.GetConstructor(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null,
new[] { typeof(FFIHandle) }, null)
?.Invoke(new object[] { handle });
Instances.Add(handle, instance!);
}
return (T)instance!;
}
/// <summary>
/// Resolve an effect parameter from the given handle.
/// </summary>
public virtual EffectParameter ResolveEffectParameter(FFIHandle handle) =>
GetOrCreateInstance<EffectParameter>(handle);
/// <summary>
/// Resolve a move effect from the given handle.
/// </summary>
public virtual Ability ResolveAbility(FFIHandle handle) => GetOrCreateInstance<Ability>(handle);
/// <summary>
/// Resolve a form from the given handle.
/// </summary>
public virtual Form ResolveForm(FFIHandle handle) => GetOrCreateInstance<Form>(handle);
/// <summary>
/// Resolve a static statistic set from the given handle.
/// </summary>
public virtual StaticStatisticSet<T> ResolveStaticStatisticSet<T>(FFIHandle handle)
where T : struct, IConvertible =>
GetOrCreateInstance<StaticStatisticSet<T>>(handle);
/// <summary>
/// Resolve a statistic set from the given handle.
/// </summary>
public virtual StatisticSet<T> ResolveStatisticSet<T>(FFIHandle handle) where T : struct, IConvertible =>
GetOrCreateInstance<StatisticSet<T>>(handle);
/// <summary>
/// Resolve a learnable moves object from the given handle.
/// </summary>
public virtual LearnableMoves ResolveLearnableMoves(FFIHandle handle) =>
GetOrCreateInstance<LearnableMoves>(handle);
/// <summary>
/// Resolve an item object from the given handle.
/// </summary>
public virtual Item ResolveItem(FFIHandle handle) => GetOrCreateInstance<Item>(handle);
/// <summary>
/// Resolve a secondary effect object from the given handle.
/// </summary>
public virtual SecondaryEffect ResolveSecondaryEffect(FFIHandle handle) =>
GetOrCreateInstance<SecondaryEffect>(handle);
/// <summary>
/// Resolve a move data object from the given handle.
/// </summary>
public virtual MoveData ResolveMoveData(FFIHandle handle) => GetOrCreateInstance<MoveData>(handle);
/// <summary>
/// Resolve an nature from the given handle.
/// </summary>
public virtual Nature ResolveNature(FFIHandle handle) => GetOrCreateInstance<Nature>(handle);
/// <summary>
/// Resolve a species object from the given handle.
/// </summary>
public virtual Species ResolveSpecies(FFIHandle handle) => GetOrCreateInstance<Species>(handle);
/// <summary>
/// Resolve a growthrate object from the given handle.
/// </summary>
public virtual LookupGrowthRate ResolveLookupGrowthRate(FFIHandle ptr) =>
GetOrCreateInstance<LookupGrowthRate>(ptr);
/// <summary>
/// Resolve an ability library object from the given handle.
/// </summary>
public virtual AbilityLibrary ResolveAbilityLibrary(FFIHandle handle) =>
GetOrCreateInstance<AbilityLibrary>(handle);
/// <summary>
/// Resolve an item library object from the given handle.
/// </summary>
public virtual ItemLibrary ResolveItemLibrary(FFIHandle handle) => GetOrCreateInstance<ItemLibrary>(handle);
/// <summary>
/// Resolve a growthrate library object from the given handle.
/// </summary>
public virtual GrowthRateLibrary ResolveGrowthRateLibrary(FFIHandle handle) =>
GetOrCreateInstance<GrowthRateLibrary>(handle);
/// <summary>
/// Resolve a move library object from the given handle.
/// </summary>
public virtual MoveLibrary ResolveMoveLibrary(FFIHandle handle) => GetOrCreateInstance<MoveLibrary>(handle);
/// <summary>
/// Resolve a nature library object from the given handle.
/// </summary>
public virtual NatureLibrary ResolveNatureLibrary(FFIHandle handle) =>
GetOrCreateInstance<NatureLibrary>(handle);
/// <summary>
/// Resolve a species library object from the given handle.
/// </summary>
public virtual SpeciesLibrary ResolveSpeciesLibrary(FFIHandle handle) =>
GetOrCreateInstance<SpeciesLibrary>(handle);
/// <summary>
/// Resolve a library settings object from the given handle.
/// </summary>
public virtual LibrarySettings ResolveLibrarySettings(FFIHandle handle) =>
GetOrCreateInstance<LibrarySettings>(handle);
/// <summary>
/// Resolve a type library object from the given handle.
/// </summary>
public virtual TypeLibrary ResolveTypeLibrary(FFIHandle handle) => GetOrCreateInstance<TypeLibrary>(handle);
/// <summary>
/// Resolve a static data object from the given handle.
/// </summary>
public virtual StaticData.Libraries.StaticData ResolveStaticData(FFIHandle handle) =>
GetOrCreateInstance<StaticData.Libraries.StaticData>(handle);
/// <summary>
/// Resolve a learned move object from the given handle.
/// </summary>
public virtual LearnedMove ResolveLearnedMove(FFIHandle resolve) => GetOrCreateInstance<LearnedMove>(resolve);
/// <summary>
/// Resolve a battle stat calculator object from the given handle.
/// </summary>
public virtual BattleStatCalculator ResolveBattleStatCalculator(FFIHandle handle) =>
GetOrCreateInstance<Gen7BattleStatCalculator>(handle);
/// <summary>
/// Resolve a damage library object from the given handle.
/// </summary>
public virtual DamageLibrary ResolveDamageLibrary(FFIHandle handle) =>
GetOrCreateInstance<Gen7DamageLibrary>(handle);
/// <summary>
/// Resolve a misc library object from the given handle.
/// </summary>
public virtual MiscLibrary ResolveMiscLibrary(FFIHandle handle) => GetOrCreateInstance<Gen7MiscLibrary>(handle);
/// <summary>
/// Resolve an empty script resolver object from the given handle.
/// </summary>
public virtual EmptyScriptResolver ResolveEmptyScriptResolver(FFIHandle handle) =>
GetOrCreateInstance<EmptyScriptResolver>(handle);
/// <summary>
/// Resolve a script resolver object from the given handle.
/// </summary>
#if WASM
public virtual ScriptResolver ResolveScriptResolver(FFIHandle handle) =>
GetOrCreateInstance<WasmScriptResolver>(handle);
#else
public virtual ScriptResolver ResolveScriptResolver(FFIHandle handle) => ResolveEmptyScriptResolver(handle);
#endif
/// <summary>
/// Resolve a dynamic library object from the given handle.
/// </summary>
public virtual DynamicLibrary ResolveDynamicLibrary(FFIHandle resolve) =>
GetOrCreateInstance<DynamicLibrary>(resolve);
/// <summary>
/// Resolve a pokemon object from the given handle.
/// </summary>
public virtual Pokemon ResolvePokemon(FFIHandle resolve) => GetOrCreateInstance<Pokemon>(resolve);
/// <summary>
/// Resolve a pokemon party object from the given handle.
/// </summary>
public virtual PokemonParty ResolvePokemonParty(FFIHandle resolve) =>
GetOrCreateInstance<PokemonParty>(resolve);
}
}