123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129 |
- #ifndef CORE_COMPONENTS_H
- #define CORE_COMPONENTS_H
- #include "core/HashMap.h"
- #include "core/List.h"
- #define isInvalidKeySize(key) ((key) == 0)
- #define equalSize(a, b) ((a) == (b))
- #define hashSize(key) (key)
- LIST(size_t, Size)
- HASHMAP(size_t, size_t, Size)
- typedef size_t Entity;
- #define COMPONENTS(T, N) \
- typedef struct { \
- HashMapSize entityToIndex; \
- ListSize indexToEntity; \
- List##N components; \
- } Components##N; \
- \
- typedef struct { \
- Entity entity; \
- T* component; \
- } ComponentNode##N; \
- \
- typedef struct { \
- const Entity* indexToEntity; \
- const Entity* indexToEntityEnd; \
- T* component; \
- T* componentEnd; \
- ComponentNode##N node; \
- } ComponentIterator##N; \
- \
- void initComponents##N(Components##N* c); \
- void destroyComponents##N(Components##N* c); \
- T* getOrAddComponent##N(Components##N* c, Entity e); \
- T* searchComponent##N(Components##N* c, Entity e); \
- bool removeComponent##N(Components##N* c, Entity e); \
- void initComponentIterator##N(ComponentIterator##N* ci, Components##N* c); \
- bool hasNextComponentNode##N(ComponentIterator##N* ci); \
- ComponentNode##N* nextComponentNode##N(ComponentIterator##N* ci); \
- T* getComponentsStart##N(Components##N* c); \
- T* getComponentsEnd##N(Components##N* c);
- #define COMPONENTS_SOURCE(T, N) \
- void initComponents##N(Components##N* c) { \
- initHashMapSize(&c->entityToIndex); \
- initListSize(&c->indexToEntity); \
- initList##N(&c->components); \
- } \
- \
- void destroyComponents##N(Components##N* c) { \
- destroyHashMapSize(&c->entityToIndex); \
- destroyListSize(&c->indexToEntity); \
- destroyList##N(&c->components); \
- } \
- \
- T* getOrAddComponent##N(Components##N* c, Entity e) { \
- void* component = searchComponent##N(c, e); \
- if(component != nullptr) { \
- return component; \
- } \
- size_t index = c->components.length; \
- *putHashMapKeySize(&c->entityToIndex, e) = index; \
- addListDataSize(&c->indexToEntity, e); \
- return addEmptyListData##N(&c->components); \
- } \
- \
- T* searchComponent##N(Components##N* c, Entity e) { \
- size_t* index = searchHashMapKeySize(&c->entityToIndex, e); \
- if(index == nullptr) { \
- return nullptr; \
- } \
- return getListIndex##N(&c->components, *index); \
- } \
- \
- bool removeComponent##N(Components##N* c, Entity e) { \
- size_t* indexP = searchHashMapKeySize(&c->entityToIndex, e); \
- if(indexP == nullptr) { \
- return false; \
- } \
- size_t lastIndex = c->components.length - 1; \
- size_t index = *indexP; \
- removeHashMapKeySize(&c->entityToIndex, e); \
- removeListIndexBySwap##N(&c->components, index); \
- if(index == lastIndex) { \
- removeListIndexBySwapSize(&c->indexToEntity, index); \
- return true; \
- } \
- Entity other = *getListIndexSize(&c->indexToEntity, lastIndex); \
- removeListIndexBySwapSize(&c->indexToEntity, index); \
- *putHashMapKeySize(&c->entityToIndex, other) = index; \
- return true; \
- } \
- \
- void initComponentIterator##N(ComponentIterator##N* ci, \
- Components##N* c) { \
- ci->indexToEntity = getListStartSize(&c->indexToEntity); \
- ci->indexToEntityEnd = getListEndSize(&c->indexToEntity); \
- ci->component = getListStart##N(&c->components); \
- ci->componentEnd = getListEnd##N(&c->components); \
- ci->node = (ComponentNode##N){0}; \
- } \
- \
- bool hasNextComponentNode##N(ComponentIterator##N* ci) { \
- return ci->indexToEntity != ci->indexToEntityEnd; \
- } \
- \
- ComponentNode##N* nextComponentNode##N(ComponentIterator##N* ci) { \
- ci->node.component = ci->component; \
- ci->node.entity = *ci->indexToEntity; \
- ci->indexToEntity++; \
- ci->component++; \
- return &ci->node; \
- } \
- \
- T* getComponentsStart##N(Components##N* c) { \
- return getListStart##N(&c->components); \
- } \
- \
- T* getComponentsEnd##N(Components##N* c) { \
- return getListEnd##N(&c->components); \
- } \
- LIST_SOURCE(size_t, Size) \
- HASHMAP_SOURCE(size_t, size_t, Size)
- #endif
|