70 lines
2.1 KiB
Odin
70 lines
2.1 KiB
Odin
#+private
|
|
package ecs
|
|
|
|
import "base:intrinsics"
|
|
import "core:log"
|
|
|
|
@(private = "file")
|
|
EntitySet :: map[EntityID]struct{}
|
|
|
|
SystemBase :: struct {
|
|
entities: EntitySet
|
|
}
|
|
|
|
SystemManager :: struct {
|
|
signatures: map[typeid]Signature,
|
|
systems: map[typeid]^SystemBase
|
|
}
|
|
|
|
system_base_init :: proc(system_base: ^SystemBase) {
|
|
system_base.entities = make(EntitySet, context.allocator)
|
|
}
|
|
|
|
system_manager_init :: proc(system_manager: ^SystemManager) {
|
|
system_manager.signatures = make(map[typeid]Signature, context.allocator)
|
|
system_manager.systems = make(map[typeid]^SystemBase, context.allocator)
|
|
}
|
|
|
|
system_manager_register_system :: proc(system_manager: ^SystemManager, $System: typeid) -> ^System {
|
|
log.assertf(System not_in system_manager.systems, "Registering system more than once")
|
|
log.assertf(intrinsics.type_has_field(System, "entities"), "Registering non system type")
|
|
|
|
system := new(System, context.allocator)
|
|
system_base_init(system)
|
|
|
|
system_manager.systems[System] = system
|
|
|
|
return system
|
|
}
|
|
|
|
system_manager_set_signature :: proc(system_manager: ^SystemManager, $System: typeid, signature: Signature) {
|
|
log.assertf(System in system_manager.systems, "System used before registered")
|
|
system_manager.signatures[System] = signature
|
|
}
|
|
|
|
system_manager_destroy_entity :: proc(system_manager: ^SystemManager, entity_id: EntityID) {
|
|
for _, system in system_manager.systems {
|
|
delete_key(&system.entities, entity_id)
|
|
}
|
|
}
|
|
|
|
system_manager_change_entity_signature :: proc(system_manager: ^SystemManager, entity_id: EntityID, entity_signature: Signature) {
|
|
for type, system in system_manager.systems {
|
|
system_signature := system_manager.signatures[type]
|
|
if (entity_signature & system_signature) == system_signature {
|
|
system.entities[entity_id] = {}
|
|
} else {
|
|
delete_key(&system.entities, entity_id)
|
|
}
|
|
}
|
|
}
|
|
|
|
system_manager_delete :: proc(system_manager: ^SystemManager) {
|
|
for _, system in system_manager.systems {
|
|
delete(system.entities)
|
|
free(system)
|
|
}
|
|
|
|
delete(system_manager.systems)
|
|
delete(system_manager.signatures)
|
|
}
|