UNPKG

@polygonjs/polygonjs

Version:

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

105 lines (104 loc) 3.46 kB
"use strict"; import { Vector3 } from "three"; import { Attribute, markAttributeAsNeedsUpdateForFrame } from "../../core/geometry/Attribute"; import { isBooleanTrue } from "../../core/Type"; import { ObjectNamedFunction1, ObjectNamedFunction2, ObjectNamedFunction5 } from "./_Base"; import { _setArrayLength } from "./_ArrayUtils"; import { dummyReadRefVal } from "./_Param"; const tmpV3 = new Vector3(); const nextV3 = new Vector3(); const STRIDE = 3; export class getGeometryPositions extends ObjectNamedFunction1 { static type() { return "getGeometryPositions"; } func(object3D, target) { const geometry = object3D.geometry; if (!geometry) { return target; } const positionAttribute = geometry.getAttribute(Attribute.POSITION); if (!positionAttribute) { return target; } const positionArray = positionAttribute.array; const pointsCount = positionArray.length / STRIDE; _setArrayLength(target, pointsCount, () => new Vector3()); for (let i = 0; i < pointsCount; i++) { const _v = target[i]; const i3 = i * STRIDE; _v.x = positionArray[i3]; _v.y = positionArray[i3 + 1]; _v.z = positionArray[i3 + 2]; } return target; } } export class getGeometryBoundingBox extends ObjectNamedFunction2 { static type() { return "getGeometryBoundingBox"; } func(object3D, forceCompute, target) { dummyReadRefVal(this.timeController.timeUniform().value); const geometry = object3D.geometry; if (!geometry) { return target; } if (!geometry.boundingBox || forceCompute) { geometry.computeBoundingBox(); } if (!geometry.boundingBox) { return target; } target.copy(geometry.boundingBox); return target; } } export class setGeometryPositions extends ObjectNamedFunction5 { static type() { return "setGeometryPositions"; } func(object3D, values, lerp, attributeNeedsUpdate, computeNormals, computeTangents) { const geometry = object3D.geometry; if (!geometry) { return; } if (!values) { return; } const positionAttribute = geometry.getAttribute(Attribute.POSITION); if (!positionAttribute) { return; } const doLerp = lerp < 1; const positionArray = positionAttribute.array; const geoPointsCount = positionArray.length / STRIDE; const valuesCount = values.length; const minCount = Math.min(geoPointsCount, valuesCount); if (doLerp) { for (let i = 0; i < minCount; i++) { const value = values[i]; const j = i * STRIDE; nextV3.copy(value); tmpV3.fromArray(positionArray, j); tmpV3.lerp(nextV3, lerp); tmpV3.toArray(positionArray, j); } } else { for (let i = 0; i < minCount; i++) { const value = values[i]; const j = i * STRIDE; value.toArray(positionArray, j); } } if (isBooleanTrue(attributeNeedsUpdate)) { markAttributeAsNeedsUpdateForFrame(positionAttribute, this.timeController.frame()); } if (positionAttribute != null && isBooleanTrue(computeNormals) && geometry.getAttribute(Attribute.NORMAL) != null) { geometry.computeVertexNormals(); } if (isBooleanTrue(computeTangents) && positionAttribute != null && geometry.getAttribute(Attribute.UV) != null && geometry.getAttribute(Attribute.NORMAL) != null && geometry.getIndex() != null) { geometry.computeTangents(); } } }