UNPKG

@polygonjs/polygonjs

Version:

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

146 lines (145 loc) 4.85 kB
"use strict"; import { BaseSopOperation } from "./_Base"; import { Vector3 } from "three"; import { InputCloneMode } from "../../../engine/poly/InputCloneMode"; import { Matrix4 } from "three"; import { TypeAssert } from "../../poly/Assert"; import { Plane } from "three"; import { pointsFromObject } from "../../../core/geometry/entities/point/CorePointUtils"; export var ShearMode = /* @__PURE__ */ ((ShearMode2) => { ShearMode2["MATRIX"] = "matrix"; ShearMode2["AXIS"] = "axis"; return ShearMode2; })(ShearMode || {}); export const SHEAR_MODES = ["matrix" /* MATRIX */, "axis" /* AXIS */]; export var ShearCenterMode = /* @__PURE__ */ ((ShearCenterMode2) => { ShearCenterMode2["BBOX_CENTER"] = "bbox center"; ShearCenterMode2["BBOX_CENTER_OFFSET"] = "bbox center offset"; ShearCenterMode2["CUSTOM"] = "custom"; return ShearCenterMode2; })(ShearCenterMode || {}); export const SHEAR_CENTER_MODES = [ "bbox center" /* BBOX_CENTER */, "bbox center offset" /* BBOX_CENTER_OFFSET */, "custom" /* CUSTOM */ ]; const _points = []; export class ShearSopOperation extends BaseSopOperation { constructor() { super(...arguments); this._m4 = new Matrix4(); this._axisNormalized = new Vector3(); this._center = new Vector3(); this._pointPos = new Vector3(); this._axisPlane = new Plane(); this._pointOnPlane = new Vector3(); this._delta = new Vector3(); this._deltaNormalized = new Vector3(); this._offset = new Vector3(); } static type() { return "shear"; } cook(input_contents, params) { const objects = input_contents[0].threejsObjects(); this._applyShear(objects, params); return input_contents[0]; } _applyShear(objects, params) { const mode = SHEAR_MODES[params.mode]; switch (mode) { case "matrix" /* MATRIX */: { return this._applyMatrixShear(objects, params); } case "axis" /* AXIS */: { return this._applyAxisShear(objects, params); } } TypeAssert.unreachable(mode); } _applyMatrixShear(objects, params) { this._m4.makeShear(params.xy, params.xz, params.yx, params.yz, params.zx, params.zy); for (let object of objects) { const mesh = object; const geometry = mesh.geometry; if (geometry) { geometry.applyMatrix4(this._m4); } } } _applyAxisShear(objects, params) { this._axisNormalized.copy(params.axis); this._axisNormalized.normalize(); for (let object of objects) { const mesh = object; const geometry = mesh.geometry; if (geometry) { this._getAxisModeCenter(geometry, params); this._axisPlane.setFromNormalAndCoplanarPoint(params.planeAxis, this._center); pointsFromObject(object, _points); for (const point of _points) { point.position(this._pointPos); this._axisPlane.projectPoint(this._pointPos, this._pointOnPlane); this._delta.copy(this._pointOnPlane).sub(this._pointPos); const distToPlane = this._delta.length(); this._deltaNormalized.copy(this._delta).normalize(); this._offset.copy(this._axisNormalized).multiplyScalar(params.axisAmount * distToPlane); if (this._delta.dot(params.planeAxis) > 0) { this._offset.multiplyScalar(-1); } this._pointPos.add(this._offset); point.setPosition(this._pointPos); } } } } _getAxisModeCenter(geometry, params) { const mode = SHEAR_CENTER_MODES[params.centerMode]; switch (mode) { case "bbox center" /* BBOX_CENTER */: { return this._getAxisModeCenterBbox(geometry, params); } case "bbox center offset" /* BBOX_CENTER_OFFSET */: { return this._getAxisModeCenterBboxOffset(geometry, params); } case "custom" /* CUSTOM */: { return this._getAxisModeCenterCustom(params); } } TypeAssert.unreachable(mode); } _getAxisModeCenterBbox(geometry, params) { geometry.computeBoundingBox(); const box = geometry.boundingBox; if (box) { box.getCenter(this._center); } else { this._center.set(0, 0, 0); } } _getAxisModeCenterBboxOffset(geometry, params) { this._getAxisModeCenterBbox(geometry, params); this._center.add(params.centerOffset); } _getAxisModeCenterCustom(params) { return this._center.copy(params.center); } } ShearSopOperation.DEFAULT_PARAMS = { mode: SHEAR_MODES.indexOf("axis" /* AXIS */), // matrix mode xy: 0, xz: 0, yx: 0, yz: 0, zx: 0, zy: 0, // axis mode centerMode: SHEAR_CENTER_MODES.indexOf("bbox center" /* BBOX_CENTER */), centerOffset: new Vector3(0, 0, 0), center: new Vector3(0, 0, 0), planeAxis: new Vector3(0, 0, 1), axis: new Vector3(0, 1, 0), axisAmount: 0 }; ShearSopOperation.INPUT_CLONED_STATE = InputCloneMode.FROM_NODE;