Better handling of PokemonLibrary that requires less reflection (but is slightly more verbose)

This commit is contained in:
Deukhoofd 2020-05-19 14:34:20 +02:00
parent 61b5bd710e
commit 0dbc800e38
Signed by: Deukhoofd
GPG Key ID: F63E044490819F6F
6 changed files with 102 additions and 36 deletions

View File

@ -5,6 +5,10 @@ namespace PkmnLibSharp.Library.GrowthRates
{ {
public class GrowthRateLibrary : PointerWrapper public class GrowthRateLibrary : PointerWrapper
{ {
internal GrowthRateLibrary(IntPtr ptr) : base(ptr)
{
}
public GrowthRateLibrary(ulong initialCapacity) : base( public GrowthRateLibrary(ulong initialCapacity) : base(
Creatureliblibrary.Generated.GrowthRateLibrary.Construct(initialCapacity)) Creatureliblibrary.Generated.GrowthRateLibrary.Construct(initialCapacity))
{ {

View File

@ -62,7 +62,7 @@ namespace PkmnLibSharp.Library.Moves
return new MoveLibrary(ptr); return new MoveLibrary(ptr);
} }
private MoveLibrary(IntPtr ptr) : base(ptr) internal MoveLibrary(IntPtr ptr) : base(ptr)
{ {
} }

View File

@ -8,8 +8,13 @@ namespace PkmnLibSharp.Library
{ {
private readonly Dictionary<string, Nature> _cache = private readonly Dictionary<string, Nature> _cache =
new Dictionary<string, Nature>(StringComparer.InvariantCultureIgnoreCase); new Dictionary<string, Nature>(StringComparer.InvariantCultureIgnoreCase);
private readonly Dictionary<IntPtr, string> _natureNames = new Dictionary<IntPtr, string>(); private readonly Dictionary<IntPtr, string> _natureNames = new Dictionary<IntPtr, string>();
internal NatureLibrary(IntPtr ptr) : base(ptr)
{
}
public NatureLibrary(ulong initialCapacity) : base(Pkmnlib.Generated.NatureLibrary.Construct(initialCapacity)) public NatureLibrary(ulong initialCapacity) : base(Pkmnlib.Generated.NatureLibrary.Construct(initialCapacity))
{ {
} }
@ -33,6 +38,7 @@ namespace PkmnLibSharp.Library
_natureNames.Add(ptr, name); _natureNames.Add(ptr, name);
return nature; return nature;
} }
nature = new Nature(ptr); nature = new Nature(ptr);
_cache.Add(name, nature); _cache.Add(name, nature);
_natureNames.Add(ptr, name); _natureNames.Add(ptr, name);

View File

@ -11,37 +11,111 @@ namespace PkmnLibSharp.Library
{ {
private LibrarySettings _settings; private LibrarySettings _settings;
public LibrarySettings Settings => public LibrarySettings Settings
_settings ??= ResolveOrCreatePtr<LibrarySettings>(DataLibrary.GetSettings(Ptr)); {
get
{
if (_settings != null) return _settings;
var ptr = DataLibrary.GetSettings(Ptr);
if (TryResolvePointer(ptr, out _settings))
return _settings;
_settings = new LibrarySettings(ptr);
return _settings;
}
}
private SpeciesLibrary _species; private SpeciesLibrary _species;
public SpeciesLibrary SpeciesLibrary => public SpeciesLibrary SpeciesLibrary
_species ??= ResolveOrCreatePtr<SpeciesLibrary>(DataLibrary.GetSpeciesLibrary(Ptr)); {
get
{
if (_species != null) return _species;
var ptr = DataLibrary.GetSpeciesLibrary(Ptr);
if (TryResolvePointer(ptr, out _species))
return _species;
_species = new SpeciesLibrary(ptr);
return _species;
}
}
private MoveLibrary _moves; private MoveLibrary _moves;
public MoveLibrary MoveLibrary => _moves ??= ResolveOrCreatePtr<MoveLibrary>(DataLibrary.GetAttackLibrary(Ptr));
public MoveLibrary MoveLibrary
{
get
{
if (_moves != null) return _moves;
var ptr = DataLibrary.GetAttackLibrary(Ptr);
if (TryResolvePointer(ptr, out _moves))
return _moves;
_moves = new MoveLibrary(ptr);
return _moves;
}
}
private ItemLibrary _items; private ItemLibrary _items;
public ItemLibrary ItemLibrary => _items ??= ResolveOrCreatePtr<ItemLibrary>(DataLibrary.GetItemLibrary(Ptr));
public ItemLibrary ItemLibrary
{
get
{
if (_items != null) return _items;
var ptr = DataLibrary.GetItemLibrary(Ptr);
if (TryResolvePointer(ptr, out _items))
return _items;
_items = new ItemLibrary(ptr);
return _items;
}
}
private GrowthRateLibrary _growthRateLibrary; private GrowthRateLibrary _growthRateLibrary;
public GrowthRateLibrary GrowthRateLibrary => _growthRateLibrary ??= public GrowthRateLibrary GrowthRateLibrary
ResolveOrCreatePtr<GrowthRateLibrary>(DataLibrary.GetGrowthRates(Ptr)); {
get
{
if (_growthRateLibrary != null) return _growthRateLibrary;
var ptr = DataLibrary.GetGrowthRates(Ptr);
if (TryResolvePointer(ptr, out _growthRateLibrary))
return _growthRateLibrary;
_growthRateLibrary = new GrowthRateLibrary(ptr);
return _growthRateLibrary;
}
}
private TypeLibrary _typeLibrary; private TypeLibrary _typeLibrary;
public TypeLibrary TypeLibrary => public TypeLibrary TypeLibrary
_typeLibrary ??= ResolveOrCreatePtr<TypeLibrary>(DataLibrary.GetTypeLibrary(Ptr)); {
get
{
if (_typeLibrary != null) return _typeLibrary;
var ptr = DataLibrary.GetTypeLibrary(Ptr);
if (TryResolvePointer(ptr, out _typeLibrary))
return _typeLibrary;
_typeLibrary = new TypeLibrary(ptr);
return _typeLibrary;
}
}
private NatureLibrary _natureLibrary; private NatureLibrary _natureLibrary;
public NatureLibrary NatureLibrary => _natureLibrary ??= public NatureLibrary NatureLibrary
ResolveOrCreatePtr<NatureLibrary>(Pkmnlib.Generated.PokemonLibrary.GetNatureLibrary(Ptr)); {
get
{
if (_natureLibrary != null) return _natureLibrary;
var ptr = Pkmnlib.Generated.PokemonLibrary.GetNatureLibrary(Ptr);
if (TryResolvePointer(ptr, out _natureLibrary))
return _natureLibrary;
_natureLibrary = new NatureLibrary(ptr);
return _natureLibrary;
}
}
internal PokemonLibrary(IntPtr ptr) : base(ptr) private PokemonLibrary(IntPtr ptr) : base(ptr)
{ {
} }

View File

@ -9,6 +9,10 @@ namespace PkmnLibSharp.Library
private readonly Dictionary<string, byte> _cache = private readonly Dictionary<string, byte> _cache =
new Dictionary<string, byte>(StringComparer.InvariantCultureIgnoreCase); new Dictionary<string, byte>(StringComparer.InvariantCultureIgnoreCase);
internal TypeLibrary(IntPtr ptr) : base(ptr)
{
}
public TypeLibrary(ulong initialCapacity) : base( public TypeLibrary(ulong initialCapacity) : base(
Creatureliblibrary.Generated.TypeLibrary.Construct(initialCapacity)) Creatureliblibrary.Generated.TypeLibrary.Construct(initialCapacity))
{ {

View File

@ -63,28 +63,6 @@ namespace PkmnLibSharp.Utilities
return false; return false;
} }
public static T ResolveOrCreatePtr<T>(IntPtr p) where T : PointerWrapper
{
if (TryResolvePointer<T>(p, out var result))
return result;
var ctor = typeof(T)
.GetConstructors(
BindingFlags.NonPublic |
BindingFlags.Public |
BindingFlags.Instance
)
.FirstOrDefault(x =>
{
var pars = x.GetParameters();
return pars.Length == 1 && pars[0].ParameterType == typeof(IntPtr);
});
if (ctor == null)
{
throw new Exception($"Unable to find constructor of type {typeof(T).FullName} with a single parameter of IntPtr.");
}
var instance = ctor.Invoke(new object[] {p}) as T;
return instance;
}
protected abstract void DeletePtr(); protected abstract void DeletePtr();