UNPKG

@polygonjs/polygonjs

Version:

node-based WebGL 3D engine https://polygonjs.com

114 lines (113 loc) 3.72 kB
"use strict"; import { SolverIterationStamp } from "./utils/SolverIterationStamp"; import { NetworkNodeType } from "./../../poly/NodeContext"; import { SubnetSopNodeLike, SopSubnetChildrenDisplayController } from "./utils/subnet/SopSubnetChildrenDisplayController"; import { InputCloneMode } from "../../poly/InputCloneMode"; import { NodeParamsConfig, ParamConfig } from "../utils/params/ParamsConfig"; import { DisplayNodeController } from "../utils/DisplayNodeController"; class SolverSopParamsConfig extends NodeParamsConfig { constructor() { super(...arguments); /** @param number of times the nodes inside this node will process the input */ this.iterations = ParamConfig.INTEGER(2, { range: [0, 5], rangeLocked: [true, false] }); /** @param Currently, when the child nodes are updated, the solver node does not know that it should recook. Clicking this button forces it to recompute */ this.reload = ParamConfig.BUTTON(null, { callback: (node) => { SolverSopNode.PARAM_CALLBACK_reload(node); } }); } } const ParamsConfig = new SolverSopParamsConfig(); export class SolverSopNode extends SubnetSopNodeLike { constructor() { super(...arguments); this.paramsConfig = ParamsConfig; this.childrenDisplayController = new SopSubnetChildrenDisplayController(this, { dependsOnDisplayNode: false }); this.displayNodeController = new DisplayNodeController( this, { onDisplayNodeRemove: () => { }, onDisplayNodeSet: () => { }, onDisplayNodeUpdate: () => { } }, { dependsOnDisplayNode: false } ); } static type() { return NetworkNodeType.SOLVER; } initializeNode() { this.io.inputs.setCount(0, 4); this.io.inputs.initInputsClonedState(InputCloneMode.NEVER); } iterationStamp() { return this._iterationStamp = this._iterationStamp || this._createStampNode(); } _createStampNode() { const stampNode = new SolverIterationStamp(this.scene()); stampNode.setForbiddenTriggerNodes(this); return stampNode; } previousFrameCoreGroup() { return this._previousFrameCoreGroup; } async cook(inputCoreGroups) { this._reset(); if (this.pv.iterations == 0) { this.setCoreGroup(inputCoreGroups[0]); return; } await this._computeSolverMultipleTimes(this.pv.iterations); } _reset() { this._previousFrameCoreGroup = void 0; if (this.iterationStamp().iteration() == 0) { this.iterationStamp().setIteration(-1); } } async _computeSolverMultipleTimes(iterationsCount) { for (let i = 0; i < iterationsCount; i++) { this.iterationStamp().setIteration(i); await this.computeSolver(i == iterationsCount - 1); } } async computeSolver(isLastIteration) { const childOutputNode = this.childrenDisplayController.outputNode(); let coreContent; if (childOutputNode) { const container = await childOutputNode.compute(); coreContent = container.coreContent(); if (coreContent) { this._previousFrameCoreGroup = coreContent; } else { if (childOutputNode.states.error.active()) { this.states.error.set(childOutputNode.states.error.message()); } else { this._previousFrameCoreGroup = void 0; } } } else { this.states.error.set("no output node found inside subnet"); } if (isLastIteration) { if (coreContent) { this.setCoreGroup(coreContent); } else { this.setObjects([]); } } } static PARAM_CALLBACK_reload(node) { node.param_callback_reload(); } param_callback_reload() { this.p.iterations.setDirty(); } }