@polygonjs/polygonjs
Version:
node-based WebGL 3D engine https://polygonjs.com
201 lines (200 loc) • 6.33 kB
JavaScript
"use strict";
import { TypedBaseManagerNode } from "./_Base";
import { NodeContext } from "../../poly/NodeContext";
import { NodeParamsConfig } from "../utils/params/ParamsConfig";
import { ROOT_NAME } from "../../scene/utils/ObjectsController";
import { Scene } from "three";
import { RootAudioController, RootAudioParamConfig } from "./utils/Scene/Audio";
import { SceneAutoUpdateParamConfig, SceneAutoUpdateController } from "./utils/Scene/AutoUpdate";
import { SceneBackgroundParamConfig, SceneBackgroundController } from "./utils/Scene/Background";
import { SceneEnvParamConfig, SceneEnvController } from "./utils/Scene/Env";
import { SceneFogParamConfig, SceneFogController } from "./utils/Scene/Fog";
import { RootLoadProgressParamConfig, RootLoadProgressController } from "./utils/Scene/LoadProgress";
import { SceneMaterialOverrideParamConfig, SceneMaterialOverrideController } from "./utils/Scene/MaterialOverride";
import { RootMainCameraController, RootMainCameraParamConfig } from "./utils/Scene/RootMainCamera";
export const ROOT_NODE_NAME = "RootNode";
class ObjectsManagerParamsConfig extends RootLoadProgressParamConfig(
RootAudioParamConfig(
SceneMaterialOverrideParamConfig(
SceneEnvParamConfig(
SceneFogParamConfig(
RootMainCameraParamConfig(SceneBackgroundParamConfig(SceneAutoUpdateParamConfig(NodeParamsConfig)))
)
)
)
)
) {
}
const ParamsConfig = new ObjectsManagerParamsConfig();
export class RootManagerNode extends TypedBaseManagerNode {
constructor() {
super(...arguments);
this.paramsConfig = ParamsConfig;
this._object = this._createScene();
this._queuedNodesById = /* @__PURE__ */ new Map();
// private _expected_geo_nodes: PolyDictionary<GeoObjNode> = {};
// private _process_queue_start: number = -1;
this.audioController = new RootAudioController(this);
this.sceneAutoUpdateController = new SceneAutoUpdateController(this);
this.sceneBackgroundController = new SceneBackgroundController(this);
this.sceneEnvController = new SceneEnvController(this);
this.sceneFogController = new SceneFogController(this);
this.loadProgress = new RootLoadProgressController(this);
this.sceneMaterialOverrideController = new SceneMaterialOverrideController(
this
);
this.mainCameraController = new RootMainCameraController(this);
this._childrenControllerContext = NodeContext.OBJ;
}
static type() {
return "root";
}
cook() {
this.cookController.endCook();
}
initializeNode() {
this.params.onParamsCreated("init controllers", () => {
this.sceneEnvController.addHooks();
this.sceneBackgroundController.addHooks();
});
this.lifecycle.onChildAdd(this._onChildAdd.bind(this));
this.lifecycle.onChildRemove(this._onChildRemove.bind(this));
}
_createScene() {
const scene = new Scene();
scene.name = ROOT_NAME;
scene.matrixAutoUpdate = true;
return scene;
}
get object() {
return this._object;
}
createNode(nodeClass, options) {
return super.createNode(nodeClass, options);
}
children() {
return super.children();
}
nodesByType(type) {
return super.nodesByType(type);
}
// multiple_display_flags_allowed() {
// return true;
// }
_updateScene() {
this.sceneAutoUpdateController.update();
this.sceneBackgroundController.update();
this.sceneEnvController.update();
this.sceneFogController.update();
this.sceneMaterialOverrideController.update();
}
_addToQueue(node) {
const id = node.graphNodeId();
if (!this._queuedNodesById.has(id)) {
this._queuedNodesById.set(id, node);
}
return node;
}
processQueue() {
this._updateScene();
const queuedNodesByPath = /* @__PURE__ */ new Map();
const paths = [];
this._queuedNodesById.forEach((node, id) => {
const fullPath = `_____${node.renderOrder}__${node.path()}`;
paths.push(fullPath);
queuedNodesByPath.set(fullPath, node);
});
this._queuedNodesById.clear();
for (const path_id of paths) {
const node = queuedNodesByPath.get(path_id);
if (node) {
queuedNodesByPath.delete(path_id);
this._addToScene(node);
}
}
}
_updateObject(node) {
if (!this.scene().loadingController.autoUpdating()) {
return this._addToQueue(node);
} else {
if (node.isDisplayed() && !node.cookController.isCooking()) {
node.compute();
}
return this._addToScene(node);
}
}
//
//
// OBJ PARENTING
//
//
getParentForNode(node) {
if (node.attachableToHierarchy()) {
const node_input = node.io.inputs.input(0);
if (node_input) {
return node_input.childrenGroup();
} else {
return this._object;
}
} else {
return null;
}
}
_addToScene(node) {
if (node.attachableToHierarchy()) {
const parentObject = this.getParentForNode(node);
if (parentObject) {
if (node.usedInScene()) {
if (node.childrenDisplayController) {
node.childrenDisplayController.requestDisplayNodeContainer();
} else {
node.compute();
}
node.addObjectToParent(parentObject);
} else {
node.removeObjectFromParent();
}
} else {
}
}
}
_removeFromScene(node) {
node.removeObjectFromParent();
}
areChildrenCooking() {
const children = this.children();
for (const child of children) {
if (child.cookController.isCooking() || child.isDisplayNodeCooking()) {
return true;
}
}
return false;
}
// private async expected_loading_geo_nodes_by_id() {
// const geo_nodes = this.nodesByType('geo');
// const node_by_id: PolyDictionary<GeoObjNode> = {};
// for (let geo_node of geo_nodes) {
// const isDisplayed = await geo_node.isDisplayed();
// if (isDisplayed) {
// node_by_id[geo_node.graphNodeId()] = geo_node;
// }
// }
// return node_by_id;
// }
addToParentTransform(node) {
this._updateObject(node);
}
removeFromParentTransform(node) {
this._updateObject(node);
}
_onChildAdd(node) {
if (node) {
this._updateObject(node);
}
}
_onChildRemove(node) {
if (node) {
this._removeFromScene(node);
}
}
}