@polygonjs/polygonjs
Version:
node-based WebGL 3D engine https://polygonjs.com
80 lines (74 loc) • 2.53 kB
text/typescript
import {ObjectType} from './../../../core/geometry/Constant';
import {BaseSopOperation} from './_Base';
import {CoreGroup} from '../../../core/geometry/Group';
import {Vector3, BoxGeometry, Box3} from 'three';
import {CoreTransform} from '../../../core/Transform';
import {InputCloneMode} from '../../../engine/poly/InputCloneMode';
import {DefaultOperationParams} from '../../../core/operations/_Base';
const tmpBox = new Box3();
const tmpSize = new Vector3();
const tmpCenter = new Vector3();
interface BoxSopParams extends DefaultOperationParams {
sizes: Vector3;
size: number;
divisions: Vector3;
center: Vector3;
}
function _roundDivision(division: number) {
return Math.max(1, Math.floor(division));
}
// const _size = new Vector3();
// const _center = new Vector3();
export class BoxSopOperation extends BaseSopOperation {
static override readonly DEFAULT_PARAMS: BoxSopParams = {
sizes: new Vector3(1, 1, 1),
size: 1,
divisions: new Vector3(1, 1, 1),
center: new Vector3(0, 0, 0),
};
static override readonly INPUT_CLONED_STATE = InputCloneMode.NEVER;
static override type(): Readonly<'box'> {
return 'box';
}
private _coreTransform = new CoreTransform();
override cook(inputCoreGroups: CoreGroup[], params: BoxSopParams) {
const inputCoreGroup = inputCoreGroups[0];
const geometry = inputCoreGroup ? this._cookWithInput(inputCoreGroup, params) : this._cookWithoutInput(params);
const object = BaseSopOperation.createObject(geometry, ObjectType.MESH);
if (this._node) {
object.name = this._node.name();
}
return this.createCoreGroupFromObjects([object]);
}
private _cookWithoutInput(params: BoxSopParams) {
const {divisions, size, sizes} = params;
const geometry = new BoxGeometry(
size * sizes.x,
size * sizes.y,
size * sizes.z,
_roundDivision(divisions.x),
_roundDivision(divisions.y),
_roundDivision(divisions.z)
);
geometry.translate(params.center.x, params.center.y, params.center.z);
geometry.computeVertexNormals();
return geometry;
}
private _cookWithInput(coreGroup: CoreGroup, params: BoxSopParams) {
coreGroup.boundingBox(tmpBox);
tmpBox.getSize(tmpSize);
tmpBox.getCenter(tmpCenter);
const divisions = params.divisions;
const geometry = new BoxGeometry(
tmpSize.x,
tmpSize.y,
tmpSize.z,
_roundDivision(divisions.x),
_roundDivision(divisions.y),
_roundDivision(divisions.z)
);
const matrix = this._coreTransform.translationMatrix(tmpCenter);
geometry.applyMatrix4(matrix);
return geometry;
}
}