103 lines
2.9 KiB
Swift
103 lines
2.9 KiB
Swift
//
|
|
// Nexus+Entity.swift
|
|
// FirebladeECS
|
|
//
|
|
// Created by Christian Treffs on 13.10.17.
|
|
//
|
|
|
|
extension Nexus {
|
|
@discardableResult
|
|
public func createEntity() -> Entity {
|
|
let entityId: EntityIdentifier = entityIdGenerator.nextId()
|
|
componentIdsByEntity[entityId] = []
|
|
delegate?.nexusEvent(EntityCreated(entityId: entityId))
|
|
return Entity(nexus: self, id: entityId)
|
|
}
|
|
|
|
@discardableResult
|
|
public func createEntity(with components: Component...) -> Entity {
|
|
let newEntity = createEntity()
|
|
assign(components: components, to: newEntity.identifier)
|
|
return newEntity
|
|
}
|
|
|
|
@discardableResult
|
|
public func createEntity(with components: some Collection<Component>) -> Entity {
|
|
let entity = createEntity()
|
|
assign(components: components, to: entity.identifier)
|
|
return entity
|
|
}
|
|
|
|
/// Number of entities in nexus.
|
|
public var numEntities: Int {
|
|
componentIdsByEntity.keys.count
|
|
}
|
|
|
|
/// Creates an iterator over all entities in the nexus.
|
|
///
|
|
/// Entity order is not guaranteed to stay the same over iterations.
|
|
public func makeEntitiesIterator() -> EntitiesIterator {
|
|
EntitiesIterator(nexus: self)
|
|
}
|
|
|
|
public func exists(entity entityId: EntityIdentifier) -> Bool {
|
|
componentIdsByEntity.keys.contains(entityId)
|
|
}
|
|
|
|
public func entity(from entityId: EntityIdentifier) -> Entity {
|
|
Entity(nexus: self, id: entityId)
|
|
}
|
|
|
|
@discardableResult
|
|
public func destroy(entity: Entity) -> Bool {
|
|
destroy(entityId: entity.identifier)
|
|
}
|
|
|
|
@discardableResult
|
|
public func destroy(entityId: EntityIdentifier) -> Bool {
|
|
guard componentIdsByEntity.keys.contains(entityId) else {
|
|
delegate?.nexusNonFatalError("EntityRemove failure: no entity \(entityId) to remove")
|
|
return false
|
|
}
|
|
|
|
if removeAll(components: entityId) {
|
|
update(familyMembership: entityId)
|
|
}
|
|
|
|
if let index = componentIdsByEntity.index(forKey: entityId) {
|
|
componentIdsByEntity.remove(at: index)
|
|
}
|
|
|
|
entityIdGenerator.markUnused(entityId: entityId)
|
|
|
|
delegate?.nexusEvent(EntityDestroyed(entityId: entityId))
|
|
return true
|
|
}
|
|
}
|
|
|
|
// MARK: - entities iterator
|
|
|
|
extension Nexus {
|
|
public struct EntitiesIterator: IteratorProtocol {
|
|
private var iterator: AnyIterator<Entity>
|
|
|
|
@usableFromInline
|
|
init(nexus: Nexus) {
|
|
var iter = nexus.componentIdsByEntity.keys.makeIterator()
|
|
iterator = AnyIterator {
|
|
guard let entityId = iter.next() else {
|
|
return nil
|
|
}
|
|
return Entity(nexus: nexus, id: entityId)
|
|
}
|
|
}
|
|
|
|
public func next() -> Entity? {
|
|
iterator.next()
|
|
}
|
|
}
|
|
}
|
|
|
|
extension Nexus.EntitiesIterator: LazySequenceProtocol {}
|
|
extension Nexus.EntitiesIterator: Sequence {}
|