mirror of
https://github.com/DCFApixels/DragonECS.git
synced 2025-09-19 02:24:37 +08:00
update
This commit is contained in:
parent
7ef556556b
commit
5d6c095142
@ -30,6 +30,13 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
void Run();
|
void Run();
|
||||||
}
|
}
|
||||||
|
[MetaName(nameof(RunFinally))]
|
||||||
|
[MetaColor(MetaColor.DragonRose)]
|
||||||
|
[MetaGroup(EcsConsts.PACK_GROUP, EcsConsts.PROCESSES_GROUP)]
|
||||||
|
public interface IEcsRunFinally : IEcsProcess
|
||||||
|
{
|
||||||
|
void RunFinally();
|
||||||
|
}
|
||||||
[MetaName(nameof(Destroy))]
|
[MetaName(nameof(Destroy))]
|
||||||
[MetaColor(MetaColor.DragonRose)]
|
[MetaColor(MetaColor.DragonRose)]
|
||||||
[MetaGroup(EcsConsts.PACK_GROUP, EcsConsts.PROCESSES_GROUP)]
|
[MetaGroup(EcsConsts.PACK_GROUP, EcsConsts.PROCESSES_GROUP)]
|
||||||
@ -97,26 +104,45 @@ namespace DCFApixels.DragonECS.Internal
|
|||||||
[MetaID("2098527C9201F260C840BFD50BC7E0BA")]
|
[MetaID("2098527C9201F260C840BFD50BC7E0BA")]
|
||||||
internal sealed class EcsRunRunner : EcsRunner<IEcsRun>, IEcsRun
|
internal sealed class EcsRunRunner : EcsRunner<IEcsRun>, IEcsRun
|
||||||
{
|
{
|
||||||
|
private readonly struct Pair
|
||||||
|
{
|
||||||
|
public readonly IEcsRun run;
|
||||||
|
public readonly IEcsRunFinally cleanup;
|
||||||
|
public Pair(IEcsRun run)
|
||||||
|
{
|
||||||
|
this.run = run;
|
||||||
|
cleanup = run as IEcsRunFinally;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
private Pair[] _pairs;
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
private EcsProfilerMarker[] _markers;
|
private EcsProfilerMarker[] _markers;
|
||||||
|
#endif
|
||||||
protected override void OnSetup()
|
protected override void OnSetup()
|
||||||
{
|
{
|
||||||
|
_pairs = new Pair[Process.Length];
|
||||||
|
for (int i = 0; i < Process.Length; i++)
|
||||||
|
{
|
||||||
|
_pairs[i] = new Pair(Process[i]);
|
||||||
|
}
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
_markers = new EcsProfilerMarker[Process.Length];
|
_markers = new EcsProfilerMarker[Process.Length];
|
||||||
for (int i = 0; i < Process.Length; i++)
|
for (int i = 0; i < Process.Length; i++)
|
||||||
{
|
{
|
||||||
_markers[i] = new EcsProfilerMarker($"{Process[i].GetMeta().Name}.{nameof(Run)}");
|
_markers[i] = new EcsProfilerMarker($"{Process[i].GetMeta().Name}.{nameof(Run)}");
|
||||||
}
|
}
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
}
|
||||||
public void Run()
|
public void Run()
|
||||||
{
|
{
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
for (int i = 0, n = Process.Length < _markers.Length ? Process.Length : _markers.Length; i < n; i++)
|
for (int i = 0, n = _pairs.Length < _markers.Length ? _pairs.Length : _markers.Length; i < n; i++)
|
||||||
{
|
{
|
||||||
|
var pair = _pairs[i];
|
||||||
_markers[i].Begin();
|
_markers[i].Begin();
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Process[i].Run();
|
pair.run.Run();
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@ -125,6 +151,10 @@ namespace DCFApixels.DragonECS.Internal
|
|||||||
#endif
|
#endif
|
||||||
EcsDebug.PrintError(e);
|
EcsDebug.PrintError(e);
|
||||||
}
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
pair.cleanup?.RunFinally();
|
||||||
|
}
|
||||||
_markers[i].End();
|
_markers[i].End();
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
|
@ -25,7 +25,63 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
public static implicit operator Singleton<T>(SingletonMarker a) { return new Singleton<T>(a.Builder.World.ID); }
|
public static implicit operator Singleton<T>(SingletonMarker a) { return new Singleton<T>(a.Builder.World.ID); }
|
||||||
}
|
}
|
||||||
public abstract class EcsAspect : ITemplateNode, IComponentMask
|
public interface IEcsAspect
|
||||||
|
{
|
||||||
|
EcsMask Mask { get; set; }
|
||||||
|
}
|
||||||
|
|
||||||
|
#region IEcsAspectExtensions tmp
|
||||||
|
// public static class IEcsAspectExtensions
|
||||||
|
// {
|
||||||
|
// public static void Apply(this IEcsAspect aspect, short worldID, int entityID)
|
||||||
|
// {
|
||||||
|
// EcsWorld world = EcsWorld.GetWorld(worldID);
|
||||||
|
// EcsMask mask = aspect.Mask;
|
||||||
|
// foreach (var incTypeID in mask._incs)
|
||||||
|
// {
|
||||||
|
// var pool = world.FindPoolInstance(incTypeID);
|
||||||
|
// if (pool != null)
|
||||||
|
// {
|
||||||
|
// if (pool.Has(entityID) == false)
|
||||||
|
// {
|
||||||
|
// pool.AddEmpty(entityID);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//#if DEBUG
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// EcsDebug.PrintWarning("Component has not been added because the pool has not been initialized yet.");
|
||||||
|
// }
|
||||||
|
//#endif
|
||||||
|
// }
|
||||||
|
// foreach (var excTypeID in mask._excs)
|
||||||
|
// {
|
||||||
|
// var pool = world.FindPoolInstance(excTypeID);
|
||||||
|
// if (pool != null && pool.Has(entityID))
|
||||||
|
// {
|
||||||
|
// pool.Del(entityID);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
public static partial class API
|
||||||
|
{
|
||||||
|
public static IncludeMarker Inc
|
||||||
|
{
|
||||||
|
get { return EcsAspect.CurrentBuilder.Inc; }
|
||||||
|
}
|
||||||
|
public static ExcludeMarker Exc
|
||||||
|
{
|
||||||
|
get { return EcsAspect.CurrentBuilder.Exc; }
|
||||||
|
}
|
||||||
|
public static OptionalMarker Opt
|
||||||
|
{
|
||||||
|
get { return EcsAspect.CurrentBuilder.Opt; }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public abstract class EcsAspect : IEcsAspect, ITemplateNode, IComponentMask
|
||||||
{
|
{
|
||||||
#region Initialization Halpers
|
#region Initialization Halpers
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
@ -43,7 +99,7 @@ namespace DCFApixels.DragonECS
|
|||||||
return _constructorBuildersStack[_constructorBuildersStackIndex];
|
return _constructorBuildersStack[_constructorBuildersStackIndex];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
protected static Builder CurrentBuilder
|
public static Builder CurrentBuilder
|
||||||
{
|
{
|
||||||
get { return B; }
|
get { return B; }
|
||||||
}
|
}
|
||||||
@ -77,6 +133,7 @@ namespace DCFApixels.DragonECS
|
|||||||
public EcsMask Mask
|
public EcsMask Mask
|
||||||
{
|
{
|
||||||
get { return _mask; }
|
get { return _mask; }
|
||||||
|
set { }
|
||||||
}
|
}
|
||||||
public EcsWorld World
|
public EcsWorld World
|
||||||
{
|
{
|
||||||
@ -138,7 +195,8 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
#region Constructors/New
|
#region Constructors/New
|
||||||
private Builder() { }
|
private Builder() { }
|
||||||
internal static unsafe TAspect New<TAspect>(EcsWorld world) where TAspect : EcsAspect, new()
|
|
||||||
|
internal static unsafe (TAspect aspect, EcsMask mask) New<TAspect>(EcsWorld world) where TAspect : new()
|
||||||
{
|
{
|
||||||
//Get Builder
|
//Get Builder
|
||||||
if (_constructorBuildersStack == null)
|
if (_constructorBuildersStack == null)
|
||||||
@ -168,26 +226,34 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
//Building
|
//Building
|
||||||
TAspect newAspect = new TAspect();
|
TAspect newAspect = new TAspect();
|
||||||
newAspect._source = world;
|
EcsAspect builtinAspect = newAspect as EcsAspect;
|
||||||
newAspect.Init(builder);
|
if(builtinAspect != null)
|
||||||
|
{
|
||||||
|
builtinAspect._source = world;
|
||||||
|
builtinAspect.Init(builder);
|
||||||
|
}
|
||||||
|
|
||||||
//Build Mask
|
//Build Mask
|
||||||
if (staticMask == null)
|
if (staticMask == null)
|
||||||
{
|
{
|
||||||
staticMask = builder._maskBuilder.Build();
|
staticMask = builder._maskBuilder.Build();
|
||||||
builder._maskBuilder = default;
|
builder._maskBuilder = default;
|
||||||
if (newAspect.IsStaticInitialization)
|
if (builtinAspect == null || builtinAspect.IsStaticInitialization)
|
||||||
{
|
{
|
||||||
_staticMaskCache.Add(typeof(TAspect), staticMask);
|
_staticMaskCache.Add(typeof(TAspect), staticMask);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
newAspect._mask = staticMask.ToMask(world);
|
EcsMask mask = staticMask.ToMask(world);
|
||||||
|
if(builtinAspect != null)
|
||||||
|
{
|
||||||
|
builtinAspect._mask = mask;
|
||||||
//var pools = new IEcsPool[builder._poolsBufferCount];
|
//var pools = new IEcsPool[builder._poolsBufferCount];
|
||||||
//Array.Copy(builder._poolsBuffer, pools, pools.Length);
|
//Array.Copy(builder._poolsBuffer, pools, pools.Length);
|
||||||
newAspect._isBuilt = true;
|
builtinAspect._isBuilt = true;
|
||||||
|
}
|
||||||
|
|
||||||
_constructorBuildersStackIndex--;
|
_constructorBuildersStackIndex--;
|
||||||
return newAspect;
|
return (newAspect, mask);
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
@ -386,7 +452,9 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
}
|
||||||
|
namespace DCFApixels.DragonECS.Core
|
||||||
|
{
|
||||||
#region Constraint Markers
|
#region Constraint Markers
|
||||||
public readonly ref struct IncludeMarker
|
public readonly ref struct IncludeMarker
|
||||||
{
|
{
|
||||||
|
@ -214,7 +214,7 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
case IEcsProcess system: return AddSystem_Internal(system, settedAddParams);
|
case IEcsProcess system: return AddSystem_Internal(system, settedAddParams);
|
||||||
case IEcsModule module: return AddModule_Internal(module, settedAddParams);
|
case IEcsModule module: return AddModule_Internal(module, settedAddParams);
|
||||||
default: Throw.ArgumentException("Unsupported type"); return this;
|
default: Throw.ArgumentException($"{raw.GetMeta().TypeName} Unsupported type"); return this;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
@ -68,7 +68,7 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
get { return _isInit; }
|
get { return _isInit; }
|
||||||
}
|
}
|
||||||
public bool IsDestoryed
|
public bool IsDestroyed
|
||||||
{
|
{
|
||||||
get { return _isDestoryed; }
|
get { return _isDestoryed; }
|
||||||
}
|
}
|
||||||
@ -250,7 +250,7 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
public static bool IsNullOrDestroyed(this EcsPipeline self)
|
public static bool IsNullOrDestroyed(this EcsPipeline self)
|
||||||
{
|
{
|
||||||
return self == null || self.IsDestoryed;
|
return self == null || self.IsDestroyed;
|
||||||
}
|
}
|
||||||
public static EcsPipeline.Builder Add(this EcsPipeline.Builder self, IEnumerable<IEcsProcess> range, string layerName = null)
|
public static EcsPipeline.Builder Add(this EcsPipeline.Builder self, IEnumerable<IEcsProcess> range, string layerName = null)
|
||||||
{
|
{
|
||||||
|
333
src/EcsRunner.cs
333
src/EcsRunner.cs
@ -4,6 +4,7 @@ using System;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Runtime.CompilerServices;
|
using System.Runtime.CompilerServices;
|
||||||
using static DCFApixels.DragonECS.EcsDebugUtility;
|
using static DCFApixels.DragonECS.EcsDebugUtility;
|
||||||
|
#pragma warning disable CS0162 // Обнаружен недостижимый код
|
||||||
|
|
||||||
namespace DCFApixels.DragonECS
|
namespace DCFApixels.DragonECS
|
||||||
{
|
{
|
||||||
@ -16,6 +17,7 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
namespace RunnersCore
|
namespace RunnersCore
|
||||||
{
|
{
|
||||||
|
//добавить инъекцию в раннеры
|
||||||
public abstract class EcsRunner
|
public abstract class EcsRunner
|
||||||
{
|
{
|
||||||
internal abstract void Init_Internal(EcsPipeline source);
|
internal abstract void Init_Internal(EcsPipeline source);
|
||||||
@ -57,6 +59,8 @@ namespace DCFApixels.DragonECS
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
public delegate void ActionWithData<in TProcess, T>(TProcess process, ref T Data);
|
||||||
}
|
}
|
||||||
|
|
||||||
[MetaColor(MetaColor.DragonRose)]
|
[MetaColor(MetaColor.DragonRose)]
|
||||||
@ -124,7 +128,12 @@ namespace DCFApixels.DragonECS
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region RunHelper
|
#region RunHelper
|
||||||
public struct RunHelper
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
public
|
||||||
|
#else
|
||||||
|
public readonly
|
||||||
|
#endif
|
||||||
|
struct RunHelper
|
||||||
{
|
{
|
||||||
private readonly EcsProcess<TProcess> _process;
|
private readonly EcsProcess<TProcess> _process;
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
@ -182,7 +191,6 @@ namespace DCFApixels.DragonECS
|
|||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
#region Do
|
#region Do
|
||||||
#pragma warning disable CS0162 // Обнаружен недостижимый код
|
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void Run(Action<TProcess> translationCallback)
|
public void Run(Action<TProcess> translationCallback)
|
||||||
{
|
{
|
||||||
@ -223,7 +231,7 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
|
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void Run<T0>(Action<TProcess, T0> translationCallback, T0 t0)
|
public void Run<TData>(ActionWithData<TProcess, TData> translationCallback, ref TData data)
|
||||||
{
|
{
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
CheckCache(translationCallback);
|
CheckCache(translationCallback);
|
||||||
@ -232,7 +240,7 @@ namespace DCFApixels.DragonECS
|
|||||||
_markers[i].Begin();
|
_markers[i].Begin();
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
translationCallback(_process[i], t0);
|
translationCallback(_process[i], ref data);
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@ -248,7 +256,7 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
translationCallback(item, t0);
|
translationCallback(item, ref data);
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
{
|
{
|
||||||
@ -260,128 +268,205 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
|
||||||
public void Run<T0, T1>(Action<TProcess, T0, T1> translationCallback, T0 t0, T1 t1)
|
|
||||||
{
|
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
|
||||||
CheckCache(translationCallback);
|
|
||||||
for (int i = 0, n = _process.Length < _markers.Length ? _process.Length : _markers.Length; i < n; i++)
|
|
||||||
{
|
|
||||||
_markers[i].Begin();
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(_process[i], t0, t1);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
_markers[i].End();
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
foreach (var item in _process)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(item, t0, t1);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
|
||||||
public void Run<T0, T1, T2>(Action<TProcess, T0, T1, T2> translationCallback, T0 t0, T1 t1, T2 t2)
|
|
||||||
{
|
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
|
||||||
CheckCache(translationCallback);
|
|
||||||
for (int i = 0, n = _process.Length < _markers.Length ? _process.Length : _markers.Length; i < n; i++)
|
|
||||||
{
|
|
||||||
_markers[i].Begin();
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(_process[i], t0, t1, t2);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
_markers[i].End();
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
foreach (var item in _process)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(item, t0, t1, t2);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
|
||||||
public void Run<T0, T1, T2, T3>(Action<TProcess, T0, T1, T2, T3> translationCallback, T0 t0, T1 t1, T2 t2, T3 t3)
|
|
||||||
{
|
|
||||||
#if DEBUG && !DISABLE_DEBUG
|
|
||||||
CheckCache(translationCallback);
|
|
||||||
for (int i = 0, n = _process.Length < _markers.Length ? _process.Length : _markers.Length; i < n; i++)
|
|
||||||
{
|
|
||||||
_markers[i].Begin();
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(_process[i], t0, t1, t2, t3);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
_markers[i].End();
|
|
||||||
}
|
|
||||||
#else
|
|
||||||
foreach (var item in _process)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
translationCallback(item, t0, t1, t2, t3);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
#if DISABLE_CATH_EXCEPTIONS
|
|
||||||
throw;
|
|
||||||
#endif
|
|
||||||
EcsDebug.PrintError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
#pragma warning restore CS0162 // Обнаружен недостижимый код
|
|
||||||
//------------------------
|
|
||||||
#endregion
|
#endregion
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
|
#region RunHelperWithFinally
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
public
|
||||||
|
#else
|
||||||
|
public readonly
|
||||||
|
#endif
|
||||||
|
struct RunHelperWithFinally<TProcessFinally> where TProcessFinally : class, IEcsProcess
|
||||||
|
{
|
||||||
|
private readonly Pair[] _pairs;
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
private Delegate _cacheCheck;
|
||||||
|
private Delegate _cacheCheckF;
|
||||||
|
private bool _cacheCheckInit;
|
||||||
|
private readonly EcsProfilerMarker[] _markers;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#region Constructors
|
||||||
|
public RunHelperWithFinally(EcsRunner<TProcess> runner) : this(runner,
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
typeof(TProcess).ToMeta().Name)
|
||||||
|
#else
|
||||||
|
string.Empty)
|
||||||
|
#endif
|
||||||
|
{ }
|
||||||
|
|
||||||
|
public RunHelperWithFinally(EcsRunner<TProcess> runner, string methodName)
|
||||||
|
{
|
||||||
|
_pairs = new Pair[runner.Process.Length];
|
||||||
|
for (int i = 0; i < runner.Process.Length; i++)
|
||||||
|
{
|
||||||
|
_pairs[i] = new Pair(runner.Process[i]);
|
||||||
|
}
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
_cacheCheck = null;
|
||||||
|
_cacheCheckF = null;
|
||||||
|
_cacheCheckInit = false;
|
||||||
|
_markers = new EcsProfilerMarker[_pairs.Length];
|
||||||
|
for (int i = 0; i < _pairs.Length; i++)
|
||||||
|
{
|
||||||
|
_markers[i] = new EcsProfilerMarker($"{_pairs[i].run.GetMeta().Name}.{methodName}");
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Utils
|
||||||
|
private readonly struct Pair
|
||||||
|
{
|
||||||
|
public readonly TProcess run;
|
||||||
|
public readonly TProcessFinally runFinally;
|
||||||
|
public Pair(TProcess run)
|
||||||
|
{
|
||||||
|
this.run = run;
|
||||||
|
runFinally = run as TProcessFinally;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
private void CheckCache(Delegate d, Delegate df)
|
||||||
|
{
|
||||||
|
if (_cacheCheckInit == false)
|
||||||
|
{
|
||||||
|
if (_cacheCheck == null)
|
||||||
|
{
|
||||||
|
_cacheCheck = d;
|
||||||
|
_cacheCheckF = df;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (ReferenceEquals(_cacheCheck, d) == false || ReferenceEquals(_cacheCheckF, df) == false)
|
||||||
|
{
|
||||||
|
EcsDebug.PrintWarning("The delegate is not cached");
|
||||||
|
}
|
||||||
|
_cacheCheckInit = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Do
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public void Run(
|
||||||
|
Action<TProcess> translationCallback,
|
||||||
|
Action<TProcessFinally> translationFinnalyCallback)
|
||||||
|
{
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
CheckCache(translationCallback, translationFinnalyCallback);
|
||||||
|
for (int i = 0, n = _pairs.Length < _markers.Length ? _pairs.Length : _markers.Length; i < n; i++)
|
||||||
|
{
|
||||||
|
var pair = _pairs[i];
|
||||||
|
_markers[i].Begin();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
translationCallback(pair.run);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
#if DISABLE_CATH_EXCEPTIONS
|
||||||
|
throw;
|
||||||
|
#endif
|
||||||
|
EcsDebug.PrintError(e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if(pair.runFinally != null)
|
||||||
|
{
|
||||||
|
translationFinnalyCallback(pair.runFinally);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_markers[i].End();
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
foreach (var item in _pairs)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
translationCallback(item.run);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
#if DISABLE_CATH_EXCEPTIONS
|
||||||
|
throw;
|
||||||
|
#endif
|
||||||
|
EcsDebug.PrintError(e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
translationFinnalyCallback(item.runFinally);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public void Run<TData>(
|
||||||
|
ActionWithData<TProcess, TData> translationCallback,
|
||||||
|
ActionWithData<TProcessFinally, TData> translationFinnalyCallback,
|
||||||
|
ref TData data)
|
||||||
|
{
|
||||||
|
#if DEBUG && !DISABLE_DEBUG
|
||||||
|
CheckCache(translationCallback, translationFinnalyCallback);
|
||||||
|
for (int i = 0, n = _pairs.Length < _markers.Length ? _pairs.Length : _markers.Length; i < n; i++)
|
||||||
|
{
|
||||||
|
var pair = _pairs[i];
|
||||||
|
_markers[i].Begin();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
translationCallback(pair.run, ref data);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
#if DISABLE_CATH_EXCEPTIONS
|
||||||
|
throw;
|
||||||
|
#endif
|
||||||
|
EcsDebug.PrintError(e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (pair.runFinally != null)
|
||||||
|
{
|
||||||
|
translationFinnalyCallback(pair.runFinally, ref data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_markers[i].End();
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
foreach (var pair in _pairs)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
translationCallback(pair.run, t0);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
#if DISABLE_CATH_EXCEPTIONS
|
||||||
|
throw;
|
||||||
|
#endif
|
||||||
|
EcsDebug.PrintError(e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (pair.runFinally != null)
|
||||||
|
{
|
||||||
|
translationFinnalyCallback(pair.runFinally, t0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
//----
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -20,13 +20,22 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
internal readonly struct AspectCache<T> : IEcsWorldComponent<AspectCache<T>>
|
internal readonly struct AspectCache<T> : IEcsWorldComponent<AspectCache<T>>
|
||||||
where T : EcsAspect, new()
|
where T : new()
|
||||||
{
|
{
|
||||||
public readonly T Instance;
|
public readonly T Instance;
|
||||||
public AspectCache(T instance) { Instance = instance; }
|
public readonly EcsMask Mask;
|
||||||
|
public AspectCache(T instance, EcsMask mask)
|
||||||
|
{
|
||||||
|
Instance = instance;
|
||||||
|
Mask = mask;
|
||||||
|
}
|
||||||
void IEcsWorldComponent<AspectCache<T>>.Init(ref AspectCache<T> component, EcsWorld world)
|
void IEcsWorldComponent<AspectCache<T>>.Init(ref AspectCache<T> component, EcsWorld world)
|
||||||
{
|
{
|
||||||
component = new AspectCache<T>(EcsAspect.Builder.New<T>(world));
|
#if DEBUG
|
||||||
|
AllowedInWorldsAttribute.CheckAllows<T>(world);
|
||||||
|
#endif
|
||||||
|
var result = EcsAspect.Builder.New<T>(world);
|
||||||
|
component = new AspectCache<T>(result.aspect, result.mask);
|
||||||
}
|
}
|
||||||
void IEcsWorldComponent<AspectCache<T>>.OnDestroy(ref AspectCache<T> component, EcsWorld world)
|
void IEcsWorldComponent<AspectCache<T>>.OnDestroy(ref AspectCache<T> component, EcsWorld world)
|
||||||
{
|
{
|
||||||
@ -36,7 +45,7 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
internal readonly struct WhereQueryCache<TExecutor, TAspcet> : IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>
|
internal readonly struct WhereQueryCache<TExecutor, TAspcet> : IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>
|
||||||
where TExecutor : MaskQueryExecutor, new()
|
where TExecutor : MaskQueryExecutor, new()
|
||||||
where TAspcet : EcsAspect, new()
|
where TAspcet : new()
|
||||||
{
|
{
|
||||||
public readonly TExecutor Executor;
|
public readonly TExecutor Executor;
|
||||||
public readonly TAspcet Aspcet;
|
public readonly TAspcet Aspcet;
|
||||||
@ -47,9 +56,9 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
void IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>.Init(ref WhereQueryCache<TExecutor, TAspcet> component, EcsWorld world)
|
void IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>.Init(ref WhereQueryCache<TExecutor, TAspcet> component, EcsWorld world)
|
||||||
{
|
{
|
||||||
TAspcet aspect = world.GetAspect<TAspcet>();
|
TAspcet aspect = world.GetAspect<TAspcet>(out EcsMask mask);
|
||||||
TExecutor instance = world.GetExecutorForMask<TExecutor>(aspect.Mask);
|
TExecutor instance = world.GetExecutorForMask<TExecutor>(mask);
|
||||||
instance.Initialize(world, aspect.Mask);
|
instance.Initialize(world, mask);
|
||||||
component = new WhereQueryCache<TExecutor, TAspcet>(instance, aspect);
|
component = new WhereQueryCache<TExecutor, TAspcet>(instance, aspect);
|
||||||
}
|
}
|
||||||
void IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>.OnDestroy(ref WhereQueryCache<TExecutor, TAspcet> component, EcsWorld world)
|
void IEcsWorldComponent<WhereQueryCache<TExecutor, TAspcet>>.OnDestroy(ref WhereQueryCache<TExecutor, TAspcet> component, EcsWorld world)
|
||||||
|
@ -250,14 +250,21 @@ namespace DCFApixels.DragonECS
|
|||||||
[UnityEngine.Scripting.Preserve]
|
[UnityEngine.Scripting.Preserve]
|
||||||
#endif
|
#endif
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public TAspect GetAspect<TAspect>() where TAspect : EcsAspect, new()
|
public TAspect GetAspect<TAspect>() where TAspect : new()
|
||||||
{
|
{
|
||||||
return Get<AspectCache<TAspect>>().Instance;
|
return Get<AspectCache<TAspect>>().Instance;
|
||||||
}
|
}
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public TAspect GetAspect<TAspect>(out EcsMask mask) where TAspect : new()
|
||||||
|
{
|
||||||
|
var result = Get<AspectCache<TAspect>>();
|
||||||
|
mask = result.Mask;
|
||||||
|
return result.Instance;
|
||||||
|
}
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public void GetQueryCache<TExecutor, TAspect>(out TExecutor executor, out TAspect aspect)
|
public void GetQueryCache<TExecutor, TAspect>(out TExecutor executor, out TAspect aspect)
|
||||||
where TExecutor : MaskQueryExecutor, new()
|
where TExecutor : MaskQueryExecutor, new()
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
ref var cmp = ref Get<WhereQueryCache<TExecutor, TAspect>>();
|
ref var cmp = ref Get<WhereQueryCache<TExecutor, TAspect>>();
|
||||||
executor = cmp.Executor;
|
executor = cmp.Executor;
|
||||||
@ -270,6 +277,11 @@ namespace DCFApixels.DragonECS
|
|||||||
return ref WorldComponentPool<T>.GetForWorld(ID);
|
return ref WorldComponentPool<T>.GetForWorld(ID);
|
||||||
}
|
}
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public bool Has<T>() where T : struct
|
||||||
|
{
|
||||||
|
return WorldComponentPool<T>.Has(ID);
|
||||||
|
}
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public ref T GetUnchecked<T>() where T : struct
|
public ref T GetUnchecked<T>() where T : struct
|
||||||
{
|
{
|
||||||
return ref WorldComponentPool<T>.GetForWorldUnchecked(ID);
|
return ref WorldComponentPool<T>.GetForWorldUnchecked(ID);
|
||||||
@ -280,6 +292,11 @@ namespace DCFApixels.DragonECS
|
|||||||
return ref WorldComponentPool<T>.GetForWorld(worldID);
|
return ref WorldComponentPool<T>.GetForWorld(worldID);
|
||||||
}
|
}
|
||||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
|
public static bool Has<T>(short worldID) where T : struct
|
||||||
|
{
|
||||||
|
return WorldComponentPool<T>.Has(worldID);
|
||||||
|
}
|
||||||
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||||
public static ref T GetUnchecked<T>(short worldID) where T : struct
|
public static ref T GetUnchecked<T>(short worldID) where T : struct
|
||||||
{
|
{
|
||||||
return ref WorldComponentPool<T>.GetForWorldUnchecked(worldID);
|
return ref WorldComponentPool<T>.GetForWorldUnchecked(worldID);
|
||||||
@ -874,6 +891,8 @@ namespace DCFApixels.DragonECS
|
|||||||
#region Debug Components
|
#region Debug Components
|
||||||
[ThreadStatic]
|
[ThreadStatic]
|
||||||
private static int[] _componentIDsBuffer;
|
private static int[] _componentIDsBuffer;
|
||||||
|
[ThreadStatic]
|
||||||
|
private static object[] _componentsBuffer;
|
||||||
public ReadOnlySpan<int> GetComponentTypeIDsFor(int entityID)
|
public ReadOnlySpan<int> GetComponentTypeIDsFor(int entityID)
|
||||||
{
|
{
|
||||||
int count = GetComponentTypeIDsFor_Internal(entityID, ref _componentIDsBuffer);
|
int count = GetComponentTypeIDsFor_Internal(entityID, ref _componentIDsBuffer);
|
||||||
@ -920,6 +939,19 @@ namespace DCFApixels.DragonECS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
public ReadOnlySpan<object> GetComponentsFor(int entityID)
|
||||||
|
{
|
||||||
|
int count = GetComponentTypeIDsFor_Internal(entityID, ref _componentIDsBuffer);
|
||||||
|
if (_componentsBuffer == null || _componentsBuffer.Length < count)
|
||||||
|
{
|
||||||
|
_componentsBuffer = new object[count];
|
||||||
|
}
|
||||||
|
for (int i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
_componentsBuffer[i] = _pools[_componentIDsBuffer[i]].GetRaw(entityID);
|
||||||
|
}
|
||||||
|
return new ReadOnlySpan<object>(_componentsBuffer, 0, count);
|
||||||
|
}
|
||||||
public void GetComponentsFor(int entityID, List<object> list)
|
public void GetComponentsFor(int entityID, List<object> list)
|
||||||
{
|
{
|
||||||
list.Clear();
|
list.Clear();
|
||||||
|
@ -169,6 +169,10 @@ namespace DCFApixels.DragonECS
|
|||||||
Array.Resize(ref _items, _items.Length << 1);
|
Array.Resize(ref _items, _items.Length << 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if DEBUG
|
||||||
|
AllowedInWorldsAttribute.CheckAllows<T>(_worlds[worldID]);
|
||||||
|
#endif
|
||||||
|
|
||||||
_interface.Init(ref _items[itemIndex], _worlds[worldID]);
|
_interface.Init(ref _items[itemIndex], _worlds[worldID]);
|
||||||
|
|
||||||
var world = GetWorld(worldID);
|
var world = GetWorld(worldID);
|
||||||
|
@ -13,7 +13,7 @@ namespace DCFApixels.DragonECS
|
|||||||
{
|
{
|
||||||
#region Where
|
#region Where
|
||||||
public static EcsSpan Where<TCollection, TAspect>(this TCollection entities, out TAspect aspect)
|
public static EcsSpan Where<TCollection, TAspect>(this TCollection entities, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
where TCollection : IEntityStorage
|
where TCollection : IEntityStorage
|
||||||
{
|
{
|
||||||
if (ReferenceEquals(entities, entities.World))
|
if (ReferenceEquals(entities, entities.World))
|
||||||
@ -24,12 +24,12 @@ namespace DCFApixels.DragonECS
|
|||||||
return entities.ToSpan().Where(out aspect);
|
return entities.ToSpan().Where(out aspect);
|
||||||
}
|
}
|
||||||
public static EcsSpan Where<TAspect>(this EcsReadonlyGroup group, out TAspect aspect)
|
public static EcsSpan Where<TAspect>(this EcsReadonlyGroup group, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
return group.ToSpan().Where(out aspect);
|
return group.ToSpan().Where(out aspect);
|
||||||
}
|
}
|
||||||
public static EcsSpan Where<TAspect>(this EcsSpan span, out TAspect aspect)
|
public static EcsSpan Where<TAspect>(this EcsSpan span, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
span.World.GetQueryCache(out EcsWhereExecutor executor, out aspect);
|
span.World.GetQueryCache(out EcsWhereExecutor executor, out aspect);
|
||||||
return executor.ExecuteFor(span);
|
return executor.ExecuteFor(span);
|
||||||
@ -58,7 +58,7 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
#region Where with sort
|
#region Where with sort
|
||||||
public static EcsSpan Where<TCollection, TAspect>(this TCollection entities, out TAspect aspect, Comparison<int> comparison)
|
public static EcsSpan Where<TCollection, TAspect>(this TCollection entities, out TAspect aspect, Comparison<int> comparison)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
where TCollection : IEntityStorage
|
where TCollection : IEntityStorage
|
||||||
{
|
{
|
||||||
if (ReferenceEquals(entities, entities.World))
|
if (ReferenceEquals(entities, entities.World))
|
||||||
@ -69,12 +69,12 @@ namespace DCFApixels.DragonECS
|
|||||||
return entities.ToSpan().Where(out aspect, comparison);
|
return entities.ToSpan().Where(out aspect, comparison);
|
||||||
}
|
}
|
||||||
public static EcsSpan Where<TAspect>(this EcsReadonlyGroup group, out TAspect aspect, Comparison<int> comparison)
|
public static EcsSpan Where<TAspect>(this EcsReadonlyGroup group, out TAspect aspect, Comparison<int> comparison)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
return group.ToSpan().Where(out aspect, comparison);
|
return group.ToSpan().Where(out aspect, comparison);
|
||||||
}
|
}
|
||||||
public static EcsSpan Where<TAspect>(this EcsSpan span, out TAspect aspect, Comparison<int> comparison)
|
public static EcsSpan Where<TAspect>(this EcsSpan span, out TAspect aspect, Comparison<int> comparison)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
span.World.GetQueryCache(out EcsWhereExecutor executor, out aspect);
|
span.World.GetQueryCache(out EcsWhereExecutor executor, out aspect);
|
||||||
return executor.ExecuteFor(span, comparison);
|
return executor.ExecuteFor(span, comparison);
|
||||||
@ -103,7 +103,7 @@ namespace DCFApixels.DragonECS
|
|||||||
|
|
||||||
#region WhereToGroup
|
#region WhereToGroup
|
||||||
public static EcsReadonlyGroup WhereToGroup<TCollection, TAspect>(this TCollection entities, out TAspect aspect)
|
public static EcsReadonlyGroup WhereToGroup<TCollection, TAspect>(this TCollection entities, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
where TCollection : IEntityStorage
|
where TCollection : IEntityStorage
|
||||||
{
|
{
|
||||||
if (ReferenceEquals(entities, entities.World))
|
if (ReferenceEquals(entities, entities.World))
|
||||||
@ -114,12 +114,12 @@ namespace DCFApixels.DragonECS
|
|||||||
return entities.ToSpan().WhereToGroup(out aspect);
|
return entities.ToSpan().WhereToGroup(out aspect);
|
||||||
}
|
}
|
||||||
public static EcsReadonlyGroup WhereToGroup<TAspect>(this EcsReadonlyGroup group, out TAspect aspect)
|
public static EcsReadonlyGroup WhereToGroup<TAspect>(this EcsReadonlyGroup group, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
return group.ToSpan().WhereToGroup(out aspect);
|
return group.ToSpan().WhereToGroup(out aspect);
|
||||||
}
|
}
|
||||||
public static EcsReadonlyGroup WhereToGroup<TAspect>(this EcsSpan span, out TAspect aspect)
|
public static EcsReadonlyGroup WhereToGroup<TAspect>(this EcsSpan span, out TAspect aspect)
|
||||||
where TAspect : EcsAspect, new()
|
where TAspect : new()
|
||||||
{
|
{
|
||||||
span.World.GetQueryCache(out EcsWhereToGroupExecutor executor, out aspect);
|
span.World.GetQueryCache(out EcsWhereToGroupExecutor executor, out aspect);
|
||||||
return executor.ExecuteFor(span);
|
return executor.ExecuteFor(span);
|
||||||
|
43
src/Utils/AllowedInWorldsAttribute.cs
Normal file
43
src/Utils/AllowedInWorldsAttribute.cs
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
using DCFApixels.DragonECS.Internal;
|
||||||
|
using System;
|
||||||
|
|
||||||
|
namespace DCFApixels.DragonECS
|
||||||
|
{
|
||||||
|
[AttributeUsage(AttributeTargets.Struct | AttributeTargets.Class, Inherited = false, AllowMultiple = true)]
|
||||||
|
public sealed class AllowedInWorldsAttribute : Attribute
|
||||||
|
{
|
||||||
|
public object[] AllowedWorlds;
|
||||||
|
public AllowedInWorldsAttribute(params object[] allowedWorlds)
|
||||||
|
{
|
||||||
|
AllowedWorlds = allowedWorlds;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public static void CheckAllows<T>(EcsWorld world)
|
||||||
|
{
|
||||||
|
Type componentType = typeof(T);
|
||||||
|
Type worldType = world.GetType();
|
||||||
|
if (componentType.TryGetAttribute(out AllowedInWorldsAttribute attribute))
|
||||||
|
{
|
||||||
|
foreach (var worldTag in attribute.AllowedWorlds)
|
||||||
|
{
|
||||||
|
bool result = false;
|
||||||
|
if (worldTag is Type worldTypeTag)
|
||||||
|
{
|
||||||
|
result = worldTypeTag == worldType;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
string worldStringTag = worldTag.ToString();
|
||||||
|
result = world.Name == worldStringTag;
|
||||||
|
}
|
||||||
|
if (result)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw new EcsFrameworkException($"Using component {componentType.ToMeta().TypeName} is not allowed in the {worldType.ToMeta().TypeName} world.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
11
src/Utils/AllowedInWorldsAttribute.cs.meta
Normal file
11
src/Utils/AllowedInWorldsAttribute.cs.meta
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: a39694cb8b5876346968ef45a8272000
|
||||||
|
MonoImporter:
|
||||||
|
externalObjects: {}
|
||||||
|
serializedVersion: 2
|
||||||
|
defaultReferences: []
|
||||||
|
executionOrder: 0
|
||||||
|
icon: {instanceID: 0}
|
||||||
|
userData:
|
||||||
|
assetBundleName:
|
||||||
|
assetBundleVariant:
|
Loading…
Reference in New Issue
Block a user