-git now should ignore .dub/dub.json
-added onAdd/onRemove to test -added onAdd/onRemove callbacks for system -generating onAdd/onRemove listeners
This commit is contained in:
parent
a82ca1e659
commit
6bbc8b5152
4 changed files with 116 additions and 2 deletions
|
|
@ -84,6 +84,12 @@ class EntityManager
|
|||
assert(register_state, "beginRegister() should be called before endRegister();");
|
||||
register_state = false;
|
||||
|
||||
foreach(ref info; &entities_infos.byValue)
|
||||
{
|
||||
if(info.systems)Mallocator.instance.dispose(info.systems);
|
||||
info.systems = Mallocator.instance.makeArray!bool(systems.length);
|
||||
}
|
||||
|
||||
foreach (ref system; systems)
|
||||
{
|
||||
if (system.m_update is null)
|
||||
|
|
@ -151,6 +157,11 @@ class EntityManager
|
|||
}
|
||||
}
|
||||
|
||||
foreach(info; &entities_infos.byValue)
|
||||
{
|
||||
generateListeners(info);
|
||||
}
|
||||
|
||||
generateDependencies();
|
||||
}
|
||||
|
||||
|
|
@ -681,7 +692,6 @@ class EntityManager
|
|||
static "~RetType.stringof~" call" ~ func
|
||||
~ "(void* system_pointer)
|
||||
{
|
||||
|
||||
Sys* s = cast(Sys*) system_pointer;
|
||||
"~ret_str~"s." ~ func ~ "();
|
||||
}
|
||||
|
|
@ -693,6 +703,32 @@ class EntityManager
|
|||
//dfmt on
|
||||
}
|
||||
|
||||
static string catchEntityFunc(RetType = void)(string member, string func)
|
||||
{
|
||||
//dfmt off
|
||||
|
||||
static if(is(RetType == void))string ret_str = "";
|
||||
else string ret_str = "return ";
|
||||
string ret = "static if (hasMember!(Sys, \"" ~ func ~ "\") &&
|
||||
Parameters!(Sys."~func~").length == 1 &&
|
||||
is(Parameters!(Sys."~func~")[0] == Sys.EntitiesData) &&
|
||||
is(ReturnType!(Sys."~func~") == "~RetType.stringof~"))
|
||||
{
|
||||
static "~RetType.stringof~" call" ~ func
|
||||
~ "(void* system_pointer)
|
||||
{
|
||||
Sys* s = cast(Sys*) system_pointer;
|
||||
Sys.EntitiesData data;
|
||||
"~ret_str~"s." ~ func ~ "(data);
|
||||
}
|
||||
|
||||
system."
|
||||
~ member ~ " = &call" ~ func ~ ";
|
||||
}";
|
||||
return ret;
|
||||
//dfmt on
|
||||
}
|
||||
|
||||
mixin(catchFunc("m_enable", "onEnable"));
|
||||
mixin(catchFunc("m_disable", "onDisable"));
|
||||
mixin(catchFunc("m_create", "onCreate"));
|
||||
|
|
@ -700,6 +736,9 @@ class EntityManager
|
|||
mixin(catchFunc!(bool)("m_begin", "onBegin"));
|
||||
mixin(catchFunc("m_end", "onEnd"));
|
||||
|
||||
mixin(catchEntityFunc("m_entity_added","onAdd"));
|
||||
mixin(catchEntityFunc("m_entity_removed","onRemove"));
|
||||
|
||||
system.m_system_pointer = cast(void*) Mallocator.instance.make!Sys;
|
||||
system.m_priority = priority;
|
||||
(cast(Sys*) system.m_system_pointer).__ecsInitialize();
|
||||
|
|
@ -1145,6 +1184,8 @@ class EntityManager
|
|||
current_delta += entites_in_block * components[id].size;
|
||||
}
|
||||
|
||||
info.systems = Mallocator.instance.makeArray!bool(systems.length);
|
||||
|
||||
foreach (i, ref system; systems)
|
||||
{
|
||||
if (system.m_update is null)
|
||||
|
|
@ -1153,10 +1194,52 @@ class EntityManager
|
|||
}
|
||||
|
||||
entities_infos.add(info.components, info);
|
||||
|
||||
generateListeners(info);
|
||||
}
|
||||
return info;
|
||||
}
|
||||
|
||||
void generateListeners(EntityInfo* info)
|
||||
{
|
||||
if(info.add_listeners)
|
||||
{
|
||||
Mallocator.instance.dispose(info.add_listeners);
|
||||
info.add_listeners = null;
|
||||
}
|
||||
if(info.remove_listeners)
|
||||
{
|
||||
Mallocator.instance.dispose(info.remove_listeners);
|
||||
info.remove_listeners = null;
|
||||
}
|
||||
|
||||
ushort[] tmp_add = (cast(ushort*)alloca(systems.length*ushort.sizeof))[0..systems.length];
|
||||
ushort[] tmp_rem = (cast(ushort*)alloca(systems.length*ushort.sizeof))[0..systems.length];
|
||||
int add_len = 0;
|
||||
int rem_len = 0;
|
||||
foreach(i;0..systems.length)
|
||||
{
|
||||
if(info.systems[i])
|
||||
{
|
||||
System* system = &systems[i];
|
||||
if(system.m_entity_added)tmp_add[add_len++] = cast(ushort)i;
|
||||
if(system.m_entity_removed)tmp_rem[rem_len++] = cast(ushort)i;
|
||||
}
|
||||
}
|
||||
|
||||
if(add_len)
|
||||
{
|
||||
info.add_listeners = Mallocator.instance.makeArray!ushort(add_len);
|
||||
memcpy(info.add_listeners.ptr,tmp_add.ptr,add_len*ushort.sizeof);
|
||||
}
|
||||
|
||||
if(rem_len)
|
||||
{
|
||||
info.remove_listeners = Mallocator.instance.makeArray!ushort(rem_len);
|
||||
memcpy(info.remove_listeners.ptr,tmp_add.ptr,rem_len*ushort.sizeof);
|
||||
}
|
||||
}
|
||||
|
||||
export void addSystemCaller(ref EntityInfo entity, uint system_id) nothrow @nogc
|
||||
{
|
||||
System* system = &systems[system_id];
|
||||
|
|
@ -1193,6 +1276,8 @@ class EntityManager
|
|||
|
||||
if (index < passes[system.m_pass].system_callers.length)
|
||||
passes[system.m_pass].system_callers[index].infos.add(&entity);
|
||||
|
||||
entity.systems[system_id] = true;
|
||||
}
|
||||
|
||||
/************************************************************************************************************************
|
||||
|
|
@ -2084,6 +2169,13 @@ class EntityManager
|
|||
///max number of entities in block
|
||||
ushort max_entities;
|
||||
|
||||
///array of systems which will update this entity
|
||||
bool[] systems;
|
||||
///systems which are listening for added entities
|
||||
ushort[] add_listeners;
|
||||
///systems which are listening for removed entities
|
||||
ushort[] remove_listeners;
|
||||
|
||||
///pointer to first block/page
|
||||
EntitiesBlock* first_block;
|
||||
///pointer to last block
|
||||
|
|
|
|||
|
|
@ -9,12 +9,15 @@ import ecs.manager;
|
|||
/************************************************************************************************************************
|
||||
*System contain data required to proper glue EntityManager with Systems.
|
||||
*System callbacks:
|
||||
*<br/>-void update(EntitesData);
|
||||
*<br/>-void onEnable()
|
||||
*<br/>-void onDisable();
|
||||
*<br/>-bool onBegin();
|
||||
*<br/>-void onEnd();
|
||||
*<br/>-void onCreate()
|
||||
*<br/>-void onDestroy();
|
||||
*<br/>-void onAdd(EntitesData);
|
||||
*<br/>-void onRemove(EntitiesData);
|
||||
*/
|
||||
struct System
|
||||
{
|
||||
|
|
@ -132,6 +135,9 @@ package:
|
|||
void* m_begin;
|
||||
void* m_end;
|
||||
|
||||
void* m_entity_added;
|
||||
void* m_entity_removed;
|
||||
|
||||
//void function(ref EntityManager.CallData data) m_initialize;
|
||||
//void function(ref EntityManager.CallData data) m_deinitilize;
|
||||
void* m_initialize;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue