summaryrefslogtreecommitdiff
path: root/src/ecs.cpp
diff options
context:
space:
mode:
authorJonathan Bradley <jcb@pikum.xyz>2024-01-12 08:14:18 -0500
committerJonathan Bradley <jcb@pikum.xyz>2024-01-12 08:14:18 -0500
commit76b1133db103e6544cec6c9b0d290723b93fd8e0 (patch)
tree573f677df7fd21bb735e346f3f43f1f4f87047b5 /src/ecs.cpp
parentcce568a7f56861d6249d7445f51d0ed27c560a5c (diff)
ECS now lives on a struct
Diffstat (limited to 'src/ecs.cpp')
-rw-r--r--src/ecs.cpp136
1 files changed, 75 insertions, 61 deletions
diff --git a/src/ecs.cpp b/src/ecs.cpp
index c627642..d087e45 100644
--- a/src/ecs.cpp
+++ b/src/ecs.cpp
@@ -15,7 +15,22 @@
#include <BulletCollision/CollisionShapes/btConvexHullShape.h>
#include <glm/gtc/type_ptr.hpp>
-constexpr PkeHandleItemIndex_T maxBucketItemCount = 256;
+constexpr struct {
+ const PkeHandleItemIndex_T generics = 256;
+ const PkeHandleItemIndex_T entityPtrs = 256;
+ const PkeHandleItemIndex_T grBinds = 64;
+ const PkeHandleItemIndex_T instances = 256;
+} bcSizes;
+
+struct ECS {
+ MemBucket *bkt = nullptr;
+ struct ECSBucketContainers {
+ BucketContainer<Entity_Base, PkeHandle, 4> generics{};
+ BucketContainer<Entity_Base *, EntityHandle, 4> entityPtrs{};
+ BucketContainer<CompGrBinds, GrBindsHandle, 4> grBinds{};
+ BucketContainer<CompInstance, InstanceHandle, 4> instances{};
+ } bc;
+} ecs;
/*
* Entities that have been marked for removal by calling ECS_MarkForRemoval
@@ -23,14 +38,12 @@ constexpr PkeHandleItemIndex_T maxBucketItemCount = 256;
* Used to build the other "removal" lists.
*/
DynArray<Entity_Base *> entitiesMarkedForRemoval{16};
-
/*
* Public list of entities that will be removed next tick
*
* Entity or child of entity that had ECS_MarkForRemoval called
*/
DynArray<Entity_Base *> EntitiesToBeRemoved{16}; // public
-
/*
* The entities being removed this tick
*
@@ -38,43 +51,44 @@ DynArray<Entity_Base *> EntitiesToBeRemoved{16}; // public
*/
DynArray<Entity_Base *> entitiesYetToBeRemoved{0, nullptr};
+/*
+ * Entities that have more instances registered than their current
+ * grBinds GPU buffer has space for.
+ *
+ * These need to be resized THIS TICK
+ */
DynArray<Entity_Base *> EntitiesWithExcessInstances{16};
-BucketContainer<Entity_Base, PkeHandle> Entities_GenericsBC{};
-BucketContainer<Entity_Base *, EntityHandle> Entities_BucketContainer{};
-BucketContainer<CompGrBinds, GrBindsHandle> Comp_GrBinds_BucketContainer{};
-BucketContainer<CompInstance, InstanceHandle> Comp_Instance_BucketContainer{};
-
void ECS_GetEntity_Inner(EntityHandle entHandle, Entity_Base*& ent) {
- assert(ValidateHandle(entHandle, Entities_BucketContainer.pkeHandle, Entities_BucketContainer.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
- ent = Entities_BucketContainer.buckets[entHandle.bucketIndex][entHandle.itemIndex];
+ assert(ValidateHandle(entHandle, ecs.bc.entityPtrs.pkeHandle, ecs.bc.entityPtrs.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
+ ent = ecs.bc.entityPtrs.buckets[entHandle.bucketIndex][entHandle.itemIndex];
}
void ECS_Init() {
- Buckets_Init(Entities_GenericsBC, maxBucketItemCount);
- Buckets_Init(Entities_BucketContainer, maxBucketItemCount);
- Buckets_Init(Comp_GrBinds_BucketContainer, maxBucketItemCount);
- Buckets_Init(Comp_Instance_BucketContainer, maxBucketItemCount);
+ Buckets_Init(ecs.bc.generics, bcSizes.generics);
+ Buckets_Init(ecs.bc.entityPtrs, bcSizes.entityPtrs);
+ Buckets_Init(ecs.bc.grBinds, bcSizes.grBinds);
+ Buckets_Init(ecs.bc.instances, bcSizes.instances);
}
Entity_Base *ECS_CreateGenericEntity() {
- PkeHandle newHandle{Buckets_NewHandle(Entities_GenericsBC)};
- return &Entities_GenericsBC.buckets[newHandle.bucketIndex][newHandle.itemIndex];
+ PkeHandle newHandle{Buckets_NewHandle(ecs.bc.generics)};
+ return &ecs.bc.generics.buckets[newHandle.bucketIndex][newHandle.itemIndex];
}
EntityHandle ECS_CreateEntity(Entity_Base *entity, Entity_Base *parentEntity) {
assert(entity != nullptr);
assert(entity->handle == EntityHandle_MAX && "Entity already created!");
- EntityHandle entityHandle{Buckets_NewHandle(Entities_BucketContainer)};
+ EntityHandle entityHandle{Buckets_NewHandle(ecs.bc.entityPtrs)};
entity->handle = entityHandle;
if (parentEntity) entity->parentHandle = parentEntity->handle;
- Entities_BucketContainer.buckets[entityHandle.bucketIndex][entityHandle.itemIndex] = entity;
+ ecs.bc.entityPtrs.buckets[entityHandle.bucketIndex][entityHandle.itemIndex] = entity;
return entityHandle;
}
Entity_Base *ECS_GetEntity(EntityHandle handle) {
- ValidateHandle(handle, Entities_BucketContainer.pkeHandle, Entities_BucketContainer.limits.itemIndex);
- return Entities_BucketContainer.buckets[handle.bucketIndex][handle.itemIndex];
+ ValidateHandle(handle, ecs.bc.entityPtrs.pkeHandle, ecs.bc.entityPtrs.limits.itemIndex);
+ return ecs.bc.entityPtrs.buckets[handle.bucketIndex][handle.itemIndex];
}
void ECS_MarkForRemoval(Entity_Base *entity) {
@@ -91,10 +105,10 @@ void ECS_Tick_Early(double delta) {
if (entitiesMarkedForRemoval.Count() == 0) return;
// this has the potential to be slow as balls
- for (long b = 0; b <= Entities_BucketContainer.pkeHandle.bucketIndex; ++b) {
- uint64_t entCount = b == Entities_BucketContainer.pkeHandle.bucketIndex ? Entities_BucketContainer.pkeHandle.itemIndex : maxBucketItemCount;
+ for (long b = 0; b <= ecs.bc.entityPtrs.pkeHandle.bucketIndex; ++b) {
+ uint64_t entCount = b == ecs.bc.entityPtrs.pkeHandle.bucketIndex ? ecs.bc.entityPtrs.pkeHandle.itemIndex : ecs.bc.entityPtrs.limits.itemIndex;
for (long e = 0; e < entCount; ++e) {
- Entity_Base *ent = Entities_BucketContainer.buckets[b][e];
+ Entity_Base *ent = ecs.bc.entityPtrs.buckets[b][e];
if (ent->handle == EntityHandle_MAX) continue;
if (ent->isMarkedForRemoval) {
entitiesYetToBeRemoved.Push(ent);
@@ -130,9 +144,9 @@ void ECS_Tick(double delta) {
DynArray<updateGrBindsAfter> *updateGrBindsPtr = Pke_New<DynArray<updateGrBindsAfter>>(pkeSettings.mem.bkt);
DynArray<updateGrBindsAfter> &updateGrBinds = *updateGrBindsPtr;
- for (long b = 0; b <= Comp_Instance_BucketContainer.pkeHandle.bucketIndex; ++b) {
- auto &bkt = Comp_Instance_BucketContainer.buckets[b];
- long count = Comp_Instance_BucketContainer.pkeHandle.bucketIndex == b ? Comp_Instance_BucketContainer.pkeHandle.itemIndex : maxBucketItemCount;
+ for (long b = 0; b <= ecs.bc.instances.pkeHandle.bucketIndex; ++b) {
+ auto &bkt = ecs.bc.instances.buckets[b];
+ long count = ecs.bc.instances.pkeHandle.bucketIndex == b ? ecs.bc.instances.pkeHandle.itemIndex : ecs.bc.instances.limits.itemIndex;
for (uint32_t i = 0; i < count; ++i) {
auto &inst = bkt[i];
if (inst.entHandle == EntityHandle_MAX)
@@ -181,9 +195,9 @@ void ECS_Tick(double delta) {
}
if (entityRemovalCount > 0 || updateGrBinds.Count() > 0) {
- for (PkeHandleBucketIndex_T b = 0; b <= Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex; ++b) {
- auto &bkt = Comp_GrBinds_BucketContainer.buckets[b];
- long count = Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex == b ? Comp_GrBinds_BucketContainer.pkeHandle.itemIndex : Comp_GrBinds_BucketContainer.limits.itemIndex;
+ for (PkeHandleBucketIndex_T b = 0; b <= ecs.bc.grBinds.pkeHandle.bucketIndex; ++b) {
+ auto &bkt = ecs.bc.grBinds.buckets[b];
+ long count = ecs.bc.grBinds.pkeHandle.bucketIndex == b ? ecs.bc.grBinds.pkeHandle.itemIndex : ecs.bc.grBinds.limits.itemIndex;
for (PkeHandleItemIndex_T i = 0; i < count; ++i) {
auto &grBinds = bkt[i];
if (grBinds.entHandle == EntityHandle_MAX) {
@@ -228,9 +242,9 @@ void ECS_Tick_Late(double delta) {
DynArray<InstanceBufferCopy> *bufferUpdatesPtr = Pke_New<DynArray<InstanceBufferCopy>>(pkeSettings.mem.bkt);
new (bufferUpdatesPtr) DynArray<InstanceBufferCopy>(0, pkeSettings.mem.bkt);
DynArray<InstanceBufferCopy> &bufferUpdates = *bufferUpdatesPtr;
- for (long b = 0; b <= Comp_Instance_BucketContainer.pkeHandle.bucketIndex; ++b) {
- auto &bkt = Comp_Instance_BucketContainer.buckets[b];
- long count = Comp_Instance_BucketContainer.pkeHandle.bucketIndex == b ? Comp_Instance_BucketContainer.pkeHandle.itemIndex : maxBucketItemCount;
+ for (long b = 0; b <= ecs.bc.instances.pkeHandle.bucketIndex; ++b) {
+ auto &bkt = ecs.bc.instances.buckets[b];
+ long count = ecs.bc.instances.pkeHandle.bucketIndex == b ? ecs.bc.instances.pkeHandle.itemIndex : ecs.bc.instances.limits.itemIndex;
for (uint32_t i = 0; i < count; ++i) {
auto &inst = bkt[i];
if (inst.isNeedingUpdated == false)
@@ -238,7 +252,7 @@ void ECS_Tick_Late(double delta) {
if (inst.entHandle == EntityHandle_MAX)
continue;
- auto &grBinds = Comp_GrBinds_BucketContainer.buckets[inst.grBindsHandle.bucketIndex][inst.grBindsHandle.itemIndex];
+ auto &grBinds = ecs.bc.grBinds.buckets[inst.grBindsHandle.bucketIndex][inst.grBindsHandle.itemIndex];
InstanceBufferCopy *bfrUpdate = nullptr;
for (long u = 0; u < bufferUpdates.Count(); ++u) {
@@ -376,8 +390,8 @@ void ECS_HandleCollision(CompInstance *lhsInst, CompInstance *rhsInst) {
CompGrBinds *ECS_CreateGrBinds(Entity_Base *entity) {
assert(entity != nullptr && entity != CAFE_BABE(Entity_Base));
- GrBindsHandle grBindsHandle{Buckets_NewHandle(Comp_GrBinds_BucketContainer)};
- auto *comp = &Comp_GrBinds_BucketContainer.buckets[grBindsHandle.bucketIndex][grBindsHandle.itemIndex];
+ GrBindsHandle grBindsHandle{Buckets_NewHandle(ecs.bc.grBinds)};
+ auto *comp = &ecs.bc.grBinds.buckets[grBindsHandle.bucketIndex][grBindsHandle.itemIndex];
comp = new (comp) CompGrBinds{};
comp->entHandle = entity->handle;
comp->grBindsHandle = grBindsHandle;
@@ -387,14 +401,14 @@ CompGrBinds *ECS_CreateGrBinds(Entity_Base *entity) {
CompGrBinds *ECS_GetGrBinds(GrBindsHandle grBindsHandle) {
if (grBindsHandle == GrBindsHandle_MAX) return nullptr;
- assert(ValidateHandle(grBindsHandle, Comp_GrBinds_BucketContainer.pkeHandle, Comp_GrBinds_BucketContainer.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
- return &Comp_GrBinds_BucketContainer.buckets[grBindsHandle.bucketIndex][grBindsHandle.itemIndex];
+ assert(ValidateHandle(grBindsHandle, ecs.bc.grBinds.pkeHandle, ecs.bc.grBinds.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
+ return &ecs.bc.grBinds.buckets[grBindsHandle.bucketIndex][grBindsHandle.itemIndex];
}
void ECS_GetGrBinds(Entity_Base *entity, PkeArray<CompGrBinds *> &arr) {
- for (PkeHandleBucketIndex_T b = 0; b <= Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex; ++b) {
- auto &bkt = Comp_GrBinds_BucketContainer.buckets[b];
- long itemCount = Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex == b ? Comp_GrBinds_BucketContainer.pkeHandle.itemIndex : Comp_GrBinds_BucketContainer.limits.itemIndex;
+ for (PkeHandleBucketIndex_T b = 0; b <= ecs.bc.grBinds.pkeHandle.bucketIndex; ++b) {
+ auto &bkt = ecs.bc.grBinds.buckets[b];
+ long itemCount = ecs.bc.grBinds.pkeHandle.bucketIndex == b ? ecs.bc.grBinds.pkeHandle.itemIndex : ecs.bc.grBinds.limits.itemIndex;
for (PkeHandleItemIndex_T i = 0; i < itemCount; ++i) {
auto &grBinds = bkt[i];
if (grBinds.entHandle == entity->handle) {
@@ -405,25 +419,25 @@ void ECS_GetGrBinds(Entity_Base *entity, PkeArray<CompGrBinds *> &arr) {
}
uint64_t ECS_GetGrBinds_BucketCount() {
- return Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex + 1;
+ return ecs.bc.grBinds.pkeHandle.bucketIndex + 1;
}
CompGrBinds *ECS_GetGrBinds(uint64_t bucketIndex, uint64_t &itemCount) {
- if (bucketIndex == Comp_GrBinds_BucketContainer.pkeHandle.bucketIndex) {
- itemCount = Comp_GrBinds_BucketContainer.pkeHandle.itemIndex;
+ if (bucketIndex == ecs.bc.grBinds.pkeHandle.bucketIndex) {
+ itemCount = ecs.bc.grBinds.pkeHandle.itemIndex;
} else {
- itemCount = maxBucketItemCount;
+ itemCount = ecs.bc.grBinds.limits.itemIndex;
}
- return Comp_GrBinds_BucketContainer.buckets[bucketIndex];
+ return ecs.bc.grBinds.buckets[bucketIndex];
}
CompInstance *ECS_CreateInstance(Entity_Base *entity, CompGrBinds *entityTypeGrBinds) {
assert(entity != nullptr && entity != CAFE_BABE(Entity_Base));
assert(entityTypeGrBinds != nullptr && entityTypeGrBinds != CAFE_BABE(CompGrBinds));
- InstanceHandle instanceHandle{Buckets_NewHandle(Comp_Instance_BucketContainer)};
+ InstanceHandle instanceHandle{Buckets_NewHandle(ecs.bc.instances)};
- auto *instBkt = Comp_Instance_BucketContainer.buckets[instanceHandle.bucketIndex];
+ auto *instBkt = ecs.bc.instances.buckets[instanceHandle.bucketIndex];
auto *comp = &instBkt[instanceHandle.itemIndex];
new (comp) CompInstance{};
comp->entHandle = entity->handle;
@@ -442,16 +456,16 @@ CompInstance *ECS_CreateInstance(Entity_Base *entity, CompGrBinds *entityTypeGrB
CompInstance *ECS_GetInstance(InstanceHandle instanceHandle ) {
if (instanceHandle == InstanceHandle_MAX) return nullptr;
- assert(ValidateHandle(instanceHandle, Comp_Instance_BucketContainer.pkeHandle, Comp_Instance_BucketContainer.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
- auto *inst = &Comp_Instance_BucketContainer.buckets[instanceHandle.bucketIndex][instanceHandle.itemIndex];
+ assert(ValidateHandle(instanceHandle, ecs.bc.instances.pkeHandle, ecs.bc.instances.limits.itemIndex) == PKE_HANDLE_VALIDATION_VALID);
+ auto *inst = &ecs.bc.instances.buckets[instanceHandle.bucketIndex][instanceHandle.itemIndex];
return inst;
}
void ECS_GetInstances(Entity_Base *entity, PkeArray<CompInstance *> &arr) {
- for (PkeHandleBucketIndex_T b = 0; b <= Comp_Instance_BucketContainer.pkeHandle.bucketIndex; ++b) {
- auto &bkt = Comp_Instance_BucketContainer.buckets[b];
- long itemCount = Comp_Instance_BucketContainer.pkeHandle.bucketIndex == b ? Comp_Instance_BucketContainer.pkeHandle.itemIndex : Comp_Instance_BucketContainer.limits.itemIndex;
+ for (PkeHandleBucketIndex_T b = 0; b <= ecs.bc.instances.pkeHandle.bucketIndex; ++b) {
+ auto &bkt = ecs.bc.instances.buckets[b];
+ long itemCount = ecs.bc.instances.pkeHandle.bucketIndex == b ? ecs.bc.instances.pkeHandle.itemIndex : ecs.bc.instances.limits.itemIndex;
for (PkeHandleItemIndex_T i = 0; i < itemCount; ++i) {
auto &inst = bkt[i];
if (inst.entHandle == entity->handle) {
@@ -477,16 +491,16 @@ void ECS_UpdateInstance(CompInstance *instance, const InstPos &instPos, bool ove
}
uint64_t ECS_GetInstances_BucketCount() {
- return Comp_Instance_BucketContainer.pkeHandle.bucketIndex + 1;
+ return ecs.bc.instances.pkeHandle.bucketIndex + 1;
}
CompInstance *ECS_GetInstances(uint64_t bucketIndex, uint64_t &itemCount) {
- if (bucketIndex == Comp_Instance_BucketContainer.pkeHandle.bucketIndex) {
- itemCount = Comp_Instance_BucketContainer.pkeHandle.itemIndex;
+ if (bucketIndex == ecs.bc.instances.pkeHandle.bucketIndex) {
+ itemCount = ecs.bc.instances.pkeHandle.itemIndex;
} else {
- itemCount = maxBucketItemCount;
+ itemCount = ecs.bc.instances.limits.itemIndex;
}
- return Comp_Instance_BucketContainer.buckets[bucketIndex];
+ return ecs.bc.instances.buckets[bucketIndex];
}
void ECS_Teardown() {
@@ -494,8 +508,8 @@ void ECS_Teardown() {
entitiesYetToBeRemoved.~DynArray();
EntitiesToBeRemoved.~DynArray();
entitiesMarkedForRemoval.~DynArray();
- Buckets_Destroy(Comp_Instance_BucketContainer);
- Buckets_Destroy(Comp_GrBinds_BucketContainer);
- Buckets_Destroy(Entities_BucketContainer);
- Buckets_Destroy(Entities_GenericsBC);
+ Buckets_Destroy(ecs.bc.instances);
+ Buckets_Destroy(ecs.bc.grBinds);
+ Buckets_Destroy(ecs.bc.entityPtrs);
+ Buckets_Destroy(ecs.bc.generics);
}