Test runner #7

Merged
Mergul merged 6 commits from TestRunner into master 2020-04-25 10:19:17 +02:00
2 changed files with 250 additions and 22 deletions
Showing only changes of commit f7a1e9bd05 - Show all commits

View file

@ -1187,7 +1187,7 @@ export struct EntityManager
(cast(Ev*) pointer).onDestroy(); (cast(Ev*) pointer).onDestroy();
} }
info.destroy_callback = &callDestroy; info.destroy_callback = cast(void function(void*) nothrow @nogc)&callDestroy;
} }
info.size = Ev.sizeof; info.size = Ev.sizeof;
@ -1214,7 +1214,7 @@ export struct EntityManager
"Can't call function with system which hasn't EntitesData structure."); "Can't call function with system which hasn't EntitesData structure.");
static assert(__traits(hasMember, Sys, "onUpdate"), static assert(__traits(hasMember, Sys, "onUpdate"),
"Can't call function with system which hasn't onUpdate function callback."); "Can't call function with system which hasn't onUpdate function callback.");
static assert(is(T == typeof(&s.onUpdate)), "Function must match system update function."); static assert(is(SetFunctionAttributes!(T,functionLinkage!(s.onUpdate), functionAttributes!(s.onUpdate)) == typeof(&s.onUpdate)), "Function must match system update function.");
static assert(__traits(hasMember, Sys, "system_id"), "Sys must be system type."); static assert(__traits(hasMember, Sys, "system_id"), "Sys must be system type.");
System* system = getSystem(Sys.system_id); System* system = getSystem(Sys.system_id);
@ -1527,8 +1527,8 @@ export struct EntityManager
ids[j] = ids[i]; ids[j] = ids[i];
j++; j++;
} }
else //else
debug assert(0, "Duplicated components in template!!!"); // debug assert(0, "Duplicated components in template!!!");
} }
ids = ids[0 .. j]; ids = ids[0 .. j];
} }
@ -1544,8 +1544,6 @@ export struct EntityManager
{ {
memcpy(temp.entity_data.ptr + info.tmpl_deltas[comp], memcpy(temp.entity_data.ptr + info.tmpl_deltas[comp],
components[comp].init_data.ptr, components[comp].size); components[comp].init_data.ptr, components[comp].size);
/*temp.entity_data[info.tmpl_deltas[comp] .. info.tmpl_deltas[comp] + components[comp].size]
= components[comp].init_data;*/
} }
return temp; return temp;
@ -1593,8 +1591,8 @@ export struct EntityManager
ids[j] = ids[i]; ids[j] = ids[i];
j++; j++;
} }
else //else
debug assert(0, "Duplicated components in template!!!"); // debug assert(0, "Duplicated components in template!!!");
} }
ids = ids[0 .. j]; ids = ids[0 .. j];
} }
@ -1747,7 +1745,7 @@ export struct EntityManager
int j; int j;
for (j = 0; j < add_len; j++) for (j = 0; j < add_len; j++)
{ {
if (systems[i].priority > systems[tmp_add[j]].priority) if (systems[i].priority < systems[tmp_add[j]].priority)
break; break;
} }
add_len++; add_len++;
@ -1767,7 +1765,7 @@ export struct EntityManager
int j; int j;
for (j = 0; j < rem_len; j++) for (j = 0; j < rem_len; j++)
{ {
if (systems[i].priority > systems[tmp_rem[j]].priority) if (systems[i].priority < systems[tmp_rem[j]].priority)
break; break;
} }
rem_len++; rem_len++;
@ -1787,7 +1785,7 @@ export struct EntityManager
int j; int j;
for (j = 0; j < ch_len; j++) for (j = 0; j < ch_len; j++)
{ {
if (systems[i].priority > systems[tmp_ch[j]].priority) if (systems[i].priority < systems[tmp_ch[j]].priority)
break; break;
} }
ch_len++; ch_len++;
@ -2727,6 +2725,7 @@ export struct EntityManager
call_data); call_data);
} }
} }
if(events[i].destroy_callback)events[i].destroy_callback(event_pointer);
event_pointer += events[i].size; event_pointer += events[i].size;
} }
block = block.next; block = block.next;
@ -2957,7 +2956,7 @@ export struct EntityManager
ushort size; ushort size;
ushort alignment; ushort alignment;
EventCaller[] callers; EventCaller[] callers;
void function(void* pointer) destroy_callback; void function(void* pointer) nothrow @nogc destroy_callback;
} }
/************************************************************************************************************************ /************************************************************************************************************************

View file

@ -5,6 +5,8 @@ import ecs.manager;
import ecs.system; import ecs.system;
import ecs.attributes; import ecs.attributes;
import std.array : staticArray;
struct CInt struct CInt
{ {
mixin ECS.Component; mixin ECS.Component;
@ -137,6 +139,13 @@ unittest
assert(entity.getComponent!CFloat); assert(entity.getComponent!CFloat);
assert(*entity.getComponent!CInt == 1); assert(*entity.getComponent!CInt == 1);
assert(*entity.getComponent!CFloat == 2.0); assert(*entity.getComponent!CFloat == 2.0);
*entity.getComponent!CInt = 2;
Entity* entity2 = gEM.addEntityCopy(entity.id);
assert(entity2.getComponent!CInt);
assert(entity2.getComponent!CFloat);
assert(*entity2.getComponent!CInt == 2);
assert(*entity2.getComponent!CFloat == 2.0);
} }
//allocate templates //allocate templates
@ -146,6 +155,8 @@ unittest
//basic template allocation //basic template allocation
ushort[2] ids = [CInt.component_id, CFloat.component_id]; ushort[2] ids = [CInt.component_id, CFloat.component_id];
EntityTemplate* tmpl_ = gEM.allocateTemplate(ids); EntityTemplate* tmpl_ = gEM.allocateTemplate(ids);
EntityTemplate* tmpl_d = gEM.allocateTemplate([CFloat.component_id, CInt.component_id, CFloat.component_id].staticArray);
assert(tmpl_d.info == tmpl_.info);
assert(tmpl_.info.components.length == 2); assert(tmpl_.info.components.length == 2);
assert(tmpl_.getComponent!CInt); assert(tmpl_.getComponent!CInt);
assert(tmpl_.getComponent!CFloat); assert(tmpl_.getComponent!CFloat);
@ -221,6 +232,7 @@ unittest
assert(*tmpl_7.getComponent!CDouble == 3.0); assert(*tmpl_7.getComponent!CDouble == 3.0);
assert(*tmpl_7.getComponent!CLong == 10); assert(*tmpl_7.getComponent!CLong == 10);
gEM.freeTemplate(tmpl_d);
gEM.freeTemplate(tmpl_); gEM.freeTemplate(tmpl_);
gEM.freeTemplate(tmpl_2); gEM.freeTemplate(tmpl_2);
gEM.freeTemplate(tmpl_3); gEM.freeTemplate(tmpl_3);
@ -497,7 +509,9 @@ unittest
@("SystemEntityCallbacks") @("SystemEntityCallbacks")
unittest unittest
{ {
//TODO: this test is WIP by now static int add_order = 0;
static int rem_order = 0;
static int change_order = 0;
struct TestSystem struct TestSystem
{ {
mixin ECS.System!16; mixin ECS.System!16;
@ -514,16 +528,22 @@ unittest
void onAddEntity(EntitiesData data) void onAddEntity(EntitiesData data)
{ {
add++; add++;
assert(add_order == 1);
add_order++;
} }
void onRemoveEntity(EntitiesData data) void onRemoveEntity(EntitiesData data)
{ {
remove++; remove++;
assert(rem_order == 1);
rem_order++;
} }
void onChangeEntity(EntitiesData data) void onChangeEntity(EntitiesData data)
{ {
change++; change++;
assert(change_order == 1);
change_order++;
} }
void onUpdate(EntitiesData data) void onUpdate(EntitiesData data)
@ -535,9 +555,83 @@ unittest
int change = 0; int change = 0;
} }
struct TestSystem2
{
mixin ECS.System!16;
mixin ECS.ExcludedComponents!(CShort);
struct EntitiesData
{
int length;
CLong[] long_;
@optional CInt[] int_;
}
void onAddEntity(EntitiesData data)
{
assert(add_order == 2);
add_order = 0;
}
void onRemoveEntity(EntitiesData data)
{
assert(rem_order == 2);
rem_order = 0 ;
}
void onChangeEntity(EntitiesData data)
{
assert(change_order == 2);
change_order = 0;
}
void onUpdate(EntitiesData data)
{
}
}
struct TestSystem3
{
mixin ECS.System!16;
mixin ECS.ExcludedComponents!(CShort);
struct EntitiesData
{
int length;
CLong[] long_;
@optional CInt[] int_;
}
void onAddEntity(EntitiesData data)
{
assert(add_order == 0);
add_order++;
}
void onRemoveEntity(EntitiesData data)
{
assert(rem_order == 0);
rem_order++;
}
void onChangeEntity(EntitiesData data)
{
assert(change_order == 0);
change_order++;
}
void onUpdate(EntitiesData data)
{
}
}
gEM.beginRegister(); gEM.beginRegister();
gEM.registerSystem!TestSystem3(-1);
gEM.registerSystem!TestSystem(0); gEM.registerSystem!TestSystem(0);
gEM.registerSystem!TestSystem2(1);
gEM.endRegister(); gEM.endRegister();
@ -547,28 +641,80 @@ unittest
assert(system.remove == 0); assert(system.remove == 0);
assert(system.change == 0); assert(system.change == 0);
ushort[2] ids = [CLong.component_id,CFloat.component_id]; EntityTemplate* tmpl = gEM.allocateTemplate([CLong.component_id,CFloat.component_id].staticArray);
EntityTemplate* tmpl = gEM.allocateTemplate(ids);
scope (exit) gEM.freeTemplate(tmpl); scope (exit) gEM.freeTemplate(tmpl);
EntityID id0 = gEM.addEntity(tmpl).id; EntityID id0 = gEM.addEntity(tmpl).id;
gEM.commit(); gEM.commit();
assert(system.add == 1); assert(system.add == 1);
ushort[2] ids2 = [CLong.component_id, CInt.component_id]; EntityTemplate* tmpl2 = gEM.allocateTemplate([CLong.component_id, CInt.component_id].staticArray);
EntityTemplate* tmpl2 = gEM.allocateTemplate(ids2);
scope (exit) gEM.freeTemplate(tmpl2); scope (exit) gEM.freeTemplate(tmpl2);
EntityID id1 = gEM.addEntity(tmpl2).id; EntityID id1 = gEM.addEntity(tmpl2).id;
gEM.commit(); gEM.commit();
assert(system.add == 2); assert(system.add == 2);
ushort[2] ids3 = [CLong.component_id, CShort.component_id]; EntityTemplate* tmpl3 = gEM.allocateTemplate([CLong.component_id, CShort.component_id].staticArray);
EntityTemplate* tmpl3 = gEM.allocateTemplate(ids3);
scope (exit) gEM.freeTemplate(tmpl3); scope (exit) gEM.freeTemplate(tmpl3);
EntityID id2 = gEM.addEntity(tmpl3).id; EntityID id2 = gEM.addEntity(tmpl3).id;
gEM.commit(); gEM.commit();
assert(system.add == 2); assert(system.add == 2);
gEM.beginRegister();
gEM.endRegister();
gEM.removeComponents(id0, [CFloat.component_id].staticArray);
gEM.commit(); gEM.commit();
assert(system.add == 2);
assert(system.remove == 0);
assert(system.change == 0);
gEM.removeComponents(id1, [CInt.component_id].staticArray);
gEM.commit();
assert(system.add == 2);
assert(system.remove == 0);
assert(system.change == 1);
gEM.removeComponents(id2, [CShort.component_id].staticArray);
gEM.commit();
assert(system.add == 3);
assert(system.remove == 0);
assert(system.change == 1);
gEM.addComponents(id2, CShort(1));
gEM.commit();
assert(system.add == 3);
assert(system.remove == 1);
assert(system.change == 1);
gEM.removeEntity(id0);
gEM.commit();
assert(system.add == 3);
assert(system.remove == 2);
assert(system.change == 1);
gEM.addComponents(id1, CInt(1));
gEM.commit();
assert(system.add == 3);
assert(system.remove == 2);
assert(system.change == 2);
gEM.addComponents(id0, CFloat(1));
gEM.commit();
assert(system.add == 3);
assert(system.remove == 2);
assert(system.change == 2);
gEM.removeEntity(id1);
gEM.commit();
assert(system.add == 3);
assert(system.remove == 3);
assert(system.change == 2);
gEM.removeEntity(id2);
gEM.commit();
assert(system.add == 3);
assert(system.remove == 3);
assert(system.change == 2);
} }
@("TemplateCoverage") @("TemplateCoverage")
@ -699,6 +845,12 @@ unittest
TestSystem* system = gEM.getSystem!TestSystem; TestSystem* system = gEM.getSystem!TestSystem;
TestEmptySystem* empty_system = gEM.getSystem!TestEmptySystem; TestEmptySystem* empty_system = gEM.getSystem!TestEmptySystem;
ushort[2] ids = [CLong.component_id,CFloat.component_id];
EntityTemplate* tmpl = gEM.allocateTemplate(ids);
scope (exit) gEM.freeTemplate(tmpl);
EntityTemplate* tmpl2 = gEM.allocateTemplate([CLong.component_id,CInt.component_id,CShort.component_id,CFloat.component_id].staticArray);
scope (exit) gEM.freeTemplate(tmpl2);
gEM.begin(); gEM.begin();
gEM.updateMT("custom"); gEM.updateMT("custom");
@ -709,9 +861,6 @@ unittest
assert(system.entities == 0); assert(system.entities == 0);
assert(empty_system.update == 1); assert(empty_system.update == 1);
ushort[2] ids = [CLong.component_id,CFloat.component_id];
EntityTemplate* tmpl = gEM.allocateTemplate(ids);
scope (exit) gEM.freeTemplate(tmpl);
gEM.addEntity(tmpl); gEM.addEntity(tmpl);
gEM.begin(); gEM.begin();
@ -866,7 +1015,14 @@ unittest
struct ETest2 struct ETest2
{ {
mixin ECS.Event; mixin ECS.Event;
void onDestroy()
{
destory++;
}
int super_liczba = 0; int super_liczba = 0;
static int destory = 0;
} }
struct TestSystem struct TestSystem
@ -937,6 +1093,9 @@ unittest
gEM.registerEvent!ETest; gEM.registerEvent!ETest;
gEM.registerEvent!ETest2; gEM.registerEvent!ETest2;
gEM.registerEvent!ETest;
gEM.registerEvent!ETest2;
gEM.registerSystem!TestSystem2(1); gEM.registerSystem!TestSystem2(1);
gEM.registerSystem!TestSystem(0); gEM.registerSystem!TestSystem(0);
@ -961,6 +1120,7 @@ unittest
gEM.sendEvent(id2,ETest()); gEM.sendEvent(id2,ETest());
gEM.sendEvent(id2,ETest2(id2,12)); gEM.sendEvent(id2,ETest2(id2,12));
gEM.commit(); gEM.commit();
assert(ETest2.destory == 2);
entity = gEM.getEntity(id); entity = gEM.getEntity(id);
entity2 = gEM.getEntity(id2); entity2 = gEM.getEntity(id2);
@ -971,6 +1131,7 @@ unittest
gEM.sendEvent(id,ETest()); gEM.sendEvent(id,ETest());
gEM.sendEvent(id,ETest2(id,2)); gEM.sendEvent(id,ETest2(id,2));
gEM.commit(); gEM.commit();
assert(ETest2.destory == 3);
entity = gEM.getEntity(id); entity = gEM.getEntity(id);
assert(*entity.getComponent!CLong == 66); assert(*entity.getComponent!CLong == 66);
@ -986,9 +1147,77 @@ unittest
result += 8; result += 8;
} }
gEM.commit(); gEM.commit();
assert(ETest2.destory == 10003);
entity = gEM.getEntity(id); entity = gEM.getEntity(id);
assert(*entity.getComponent!CLong == result); assert(*entity.getComponent!CLong == result);
//cover funcion to clearEvents before destroying manager //cover funcion to clearEvents before destroying manager
gEM.sendEvent(id,ETest()); gEM.sendEvent(id,ETest());
}
@("EntitiesFunction")
unittest
{
struct TestSystem
{
mixin ECS.System;
struct EntitiesData
{
uint length;
CInt[] int_;
}
void onUpdate(EntitiesData entities)
{
}
}
void func1(TestSystem.EntitiesData entities)
{
foreach(i;0 .. entities.length)
{
entities.int_[i] += entities.int_[i] / 2;
}
}
void func2(TestSystem.EntitiesData entities)
{
foreach(i;0 .. entities.length)
{
entities.int_[i] += 8;
}
}
gEM.beginRegister();
gEM.registerSystem!TestSystem(1);
gEM.endRegister();
EntityTemplate* tmpl = gEM.allocateTemplate([CInt.component_id].staticArray);
scope (exit) gEM.freeTemplate(tmpl);
EntityID id1 = gEM.addEntity(tmpl).id;
EntityTemplate* tmpl2 = gEM.allocateTemplate([CInt.component_id, CLong.component_id].staticArray);
scope (exit) gEM.freeTemplate(tmpl2);
EntityID id2 = gEM.addEntity(tmpl2).id;
gEM.begin();
Entity* entity1 = gEM.getEntity(id1);
Entity* entity2 = gEM.getEntity(id2);
assert(*entity1.getComponent!CInt == 1);
assert(*entity2.getComponent!CInt == 1);
gEM.callEntitiesFunction!TestSystem(&func2);
assert(*entity1.getComponent!CInt == 9);
assert(*entity2.getComponent!CInt == 9);
gEM.callEntitiesFunction!TestSystem(&func1);
assert(*entity1.getComponent!CInt == 13);
assert(*entity2.getComponent!CInt == 13);
gEM.end();
} }