@dcl/ecs
Version:
Decentraland ECS
101 lines (100 loc) • 3.84 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.removeEntityWithChildren = exports.getComponentEntityTree = void 0;
const components = __importStar(require("../../components"));
function* genEntityTree(entity, entities) {
// This avoid infinite loop when there is a cyclic parenting
if (!entities.has(entity))
return;
entities.delete(entity);
for (const [_entity, value] of entities) {
if (value.parent === entity) {
yield* genEntityTree(_entity, entities);
}
}
yield entity;
}
/**
* Get an iterator of entities that follow a tree structure for a component
* @public
* @param engine - the engine running the entities
* @param entity - the root entity of the tree
* @param component - the parenting component to filter by
* @returns An iterator of an array as [entity, entity2, ...]
*
* Example:
* ```ts
* const TreeComponent = engine.defineComponent('custom::TreeComponent', {
* label: Schemas.String,
* parent: Schemas.Entity
* })
*
* for (const entity of getComponentEntityTree(engine, entity, TreeComponent)) {
* // entity in the tree
* }
* ```
*/
function getComponentEntityTree(engine, entity, component) {
const entities = new Map(engine.getEntitiesWith(component));
return genEntityTree(entity, entities);
}
exports.getComponentEntityTree = getComponentEntityTree;
// I swear by all the gods that this is being tested on test/sdk/network/sync-engines.spec.ts
/* istanbul ignore next */
function removeNetworkEntityChildrens(engine, parent) {
const NetworkParent = components.NetworkParent(engine);
const NetworkEntity = components.NetworkEntity(engine);
// Remove parent
engine.removeEntity(parent);
// Remove childs
const network = NetworkEntity.getOrNull(parent);
if (network) {
for (const [entity, parent] of engine.getEntitiesWith(NetworkParent)) {
if (parent.entityId === network.entityId && parent.networkId === network.networkId) {
removeNetworkEntityChildrens(engine, entity);
}
}
}
return;
}
/**
* Remove all components of each entity in the tree made with Transform parenting
* @param engine - the engine running the entities
* @param firstEntity - the root entity of the tree
* @public
*/
function removeEntityWithChildren(engine, entity) {
const Transform = components.Transform(engine);
const NetworkEntity = components.NetworkEntity(engine);
/* istanbul ignore if */
if (NetworkEntity.has(entity)) {
return removeNetworkEntityChildrens(engine, entity);
}
for (const ent of getComponentEntityTree(engine, entity, Transform)) {
engine.removeEntity(ent);
}
}
exports.removeEntityWithChildren = removeEntityWithChildren;