diff --git a/packages/ecs/src/ecs.js b/packages/ecs/src/ecs.js index 4eb392c..78cc64a 100644 --- a/packages/ecs/src/ecs.js +++ b/packages/ecs/src/ecs.js @@ -18,12 +18,7 @@ export default class Ecs { constructor(Components) { for (const i in Components) { - const comp = new Components[i](); - comp.setDirty = (entity) => { - comp.$$dirty = true; - this.dirty.add(entity); - }; - this.Components[i] = comp; + this.Components[i] = this.trackDirtyEntities(Components[i]); } } @@ -146,25 +141,24 @@ export default class Ecs { } destroyMany(entities) { - const map = {}; + const destroying = {}; for (let i = 0; i < entities.length; i++) { const entity = entities[i]; if (!this.$$entities[entity]) { throw new Error(`can't destroy non-existent entity ${entity}`); } for (let j = 0; j < this.$$entities[entity].length; j++) { - const key = this.$$entities[entity][j]; - if (!map[key]) { - map[key] = []; + const component = this.$$entities[entity][j]; + if (!destroying[component]) { + destroying[component] = []; } - map[key].push(entity); + destroying[component].push(entity); } this.$$pool.push(entity); delete this.$$entities[entity]; - this.dirty.delete(entity); } - for (const i in map) { - this.Components[i].destroyMany(map[i]); + for (const i in destroying) { + this.Components[i].destroyMany(destroying[i]); } for (let i = 0; i < this.$$systems.length; i++) { this.$$systems[i].deindex(entities); @@ -189,14 +183,13 @@ export default class Ecs { entity = entities[i]; } if (onlyDirty && !this.dirty.has(entity)) { - // eslint-disable-next-line no-continue continue; } view.setBigUint64(cursor, BigInt(entity), true); cursor += 8; const components = this.$$entities[entity]; view.setUint16(cursor, components.length, true); - const componentLengthIndex = cursor; + const componentsWrittenIndex = cursor; cursor += 2; if (0 === components.length) { continue; @@ -215,7 +208,7 @@ export default class Ecs { instance.serializer.encode(source, view, cursor); cursor += instance.schema.sizeOf(source); } - view.setUint16(componentLengthIndex, componentsWritten, true); + view.setUint16(componentsWrittenIndex, componentsWritten, true); } } @@ -256,6 +249,13 @@ export default class Ecs { } } + setClean() { + for (const i in this.Components) { + this.Components[i].setClean(); + } + this.dirty.clear(); + } + sizeOf(entities, onlyDirty) { let size = 0; if (0 === entities.length) { @@ -294,16 +294,9 @@ export default class Ecs { } } - tickClean() { - for (const i in this.Components) { - this.Components[i].setClean(); - } - this.dirty.clear(); - } - tickFinalize() { this.tickDestruction(); - this.tickClean(); + this.setClean(); } tickDestruction() { @@ -320,4 +313,13 @@ export default class Ecs { } } + trackDirtyEntities(Component) { + const component = new Component(); + component.setDirty = (entity) => { + component.$$dirty = true; + this.dirty.add(entity); + }; + return component; + } + }