UNPKG

@openhps/core

Version:

Open Hybrid Positioning System - Core component

246 lines 9.24 kB
"use strict"; var ReferenceSpace_1; Object.defineProperty(exports, "__esModule", { value: true }); exports.ReferenceSpace = void 0; const tslib_1 = require("tslib"); const DataObject_1 = require("../DataObject"); const decorators_1 = require("../../decorators"); const math_1 = require("../../../utils/math"); const utils_1 = require("../../../utils"); /** * A reference space transforms absolute positions to another (global) reference space. * The following data can be transformed: * - Position coordinates * - Linear velocity * - Angular velocity * - Orientation * - Position accuracy */ let ReferenceSpace = ReferenceSpace_1 = class ReferenceSpace extends DataObject_1.DataObject { constructor(parent) { super(); this.parent = parent; this._scaleMatrix = new math_1.Matrix4(); this._transformationMatrix = new math_1.Matrix4().identity(); this._translationMatrix = new math_1.Matrix4().identity(); this._rotation = new math_1.Quaternion(); } /** * Create a reference space from another object * @param {DataObject} object Reference space */ static fromDataObject(object) { const space = new ReferenceSpace_1(); space.uid = object.uid; space.displayName = object.displayName; if (object.getPosition()) { space.translation(...object.getPosition().toVector3(utils_1.LengthUnit.METER).toArray()); if (object.getPosition().orientation) { space.rotation(object.getPosition().orientation); } } return space; } /** * Set the parent space * @param {TransformationSpace} space Parent space */ set parent(space) { if (!space) { return; } else { this.parentUID = space.uid; this._parent = space; } } /** * Get the parent space if loaded * @returns {TransformationSpace | undefined} Transformation space or undefined */ get parent() { return this._parent; } /** * Update parent reference spaces * @param {DataService} service Service to use for updating * @returns {Promise<void>} Update promise */ update(service) { return new Promise((resolve, reject) => { if (this.parentUID) { // Update parent service .findByUID(this.parentUID) .then((parent) => { this._parent = parent; if (!parent) { throw new Error(`Unable to find reference space with uid: ${this.parentUID}!`); } return this._parent.update(service); }) .then(resolve) .catch(reject); } else { resolve(); } }); } orthographic(left, right, bottom, top, near, far) { this._transformationMatrix.multiply(new math_1.Matrix4().makeOrthographic(left, right, bottom, top, near, far)); return this; } /** * Transform perspective * @param {number} left Farthest left on the x-axis * @param {number} right Farthest right on the x-axis * @param {number} bottom Farthest down on the y-axis * @param {number} top Farthest up on the y-axis * @param {number} near Distance to the near clipping plane along the -Z axis * @param {number} far Distance to the far clipping plane along the -Z axis * @returns {ReferenceSpace} Reference space instance */ perspective(left, right, bottom, top, near, far) { this._transformationMatrix.multiply(new math_1.Matrix4().makePerspective(left, right, bottom, top, near, far)); return this; } reset() { this._transformationMatrix.identity(); this._scaleMatrix = new math_1.Matrix4(); this._rotation = new math_1.Quaternion(); return this; } referenceUnit(unit) { this._unit = unit; return this; } translation(dX, dY, dZ = 0) { this._translationMatrix.multiply(new math_1.Matrix4().makeTranslation(dX, dY, dZ)); this._transformationMatrix.multiply(this._translationMatrix); return this; } scale(kX, kY, kZ = 1.0) { this._scaleMatrix = new math_1.Matrix4().makeScale(kX, kY, kZ); this._transformationMatrix.multiply(this._scaleMatrix); return this; } rotation(r) { if (r instanceof math_1.Quaternion) { this._rotation = r.clone(); this._transformationMatrix.multiply(this._rotation.toRotationMatrix()); } else if (r instanceof math_1.Euler) { this._rotation = math_1.Quaternion.fromEuler(r); this._transformationMatrix.multiply(this._rotation.toRotationMatrix()); } else if (r instanceof math_1.AxisAngle) { this._rotation = math_1.Quaternion.fromAxisAngle(r); this._transformationMatrix.multiply(this._rotation.toRotationMatrix()); } else { this._rotation = math_1.Quaternion.fromEuler(r); this._transformationMatrix.multiply(this._rotation.toRotationMatrix()); } return this; } /** * Transform a position * @param {AbsolutePosition} position Position to transform * @param {SpaceTransformationOptions} [options] Transformation options * @returns {AbsolutePosition} Transformed position */ transform(position, options) { const config = options || {}; // Clone the position const newPosition = this._parent ? this._parent.transform(position, options) : position.clone(); // Transform the position to the length unit if (this._unit) { newPosition.fromVector(newPosition.toVector3(this._unit)); newPosition.setAccuracy(newPosition.accuracy.to(this._unit)); } const transformationMatrix = config.inverse ? this.transformationMatrix.clone().invert() : this.transformationMatrix; const rotation = config.inverse ? this.rotationQuaternion.clone().invert() : this.rotationQuaternion; const scale = config.inverse ? this._scaleMatrix.clone().invert() : this.scaleMatrix; // Transform the point using the transformation matrix newPosition.fromVector(newPosition.toVector3().applyMatrix4(transformationMatrix)); // Transform the orientation (rotation) if (newPosition.orientation) { // Rotate the quaterion newPosition.orientation.multiply(rotation); } if (newPosition.linearVelocity) { // Transform the linear velocity (rotation and scale) newPosition.linearVelocity.applyMatrix4(scale).applyMatrix4(math_1.Matrix4.rotationFromQuaternion(rotation)); } newPosition.setAccuracy(new math_1.Vector3(newPosition.accuracy.valueOf(), 0, 0).applyMatrix4(scale).x, newPosition.accuracy.unit); newPosition.referenceSpaceUID = this.uid; return newPosition; } get transformationMatrix() { return this._transformationMatrix; } set transformationMatrix(matrix) { this._transformationMatrix = matrix; } /** * Get the transformation matrix for scaling * @returns {Matrix4} Transformation matrix */ get scaleMatrix() { return this._scaleMatrix; } set scaleMatrix(matrix) { this._scaleMatrix = matrix; } get rotationQuaternion() { return this._rotation; } set rotationQuaternion(quaternion) { this._rotation = quaternion; } get translationMatrix() { return this._translationMatrix; } set translationMatrix(matrix) { this._translationMatrix = matrix; } }; exports.ReferenceSpace = ReferenceSpace; tslib_1.__decorate([ (0, decorators_1.SerializableMember)({ name: 'translationMatrix', }), tslib_1.__metadata("design:type", math_1.Matrix4) ], ReferenceSpace.prototype, "_translationMatrix", void 0); tslib_1.__decorate([ (0, decorators_1.SerializableMember)({ name: 'transformationMatrix', }), tslib_1.__metadata("design:type", math_1.Matrix4) ], ReferenceSpace.prototype, "_transformationMatrix", void 0); tslib_1.__decorate([ (0, decorators_1.SerializableMember)({ name: 'scaleMatrix', }), tslib_1.__metadata("design:type", math_1.Matrix4) ], ReferenceSpace.prototype, "_scaleMatrix", void 0); tslib_1.__decorate([ (0, decorators_1.SerializableMember)({ name: 'rotation', }), tslib_1.__metadata("design:type", math_1.Quaternion) ], ReferenceSpace.prototype, "_rotation", void 0); tslib_1.__decorate([ (0, decorators_1.SerializableMember)({ name: 'unit', }), tslib_1.__metadata("design:type", utils_1.LengthUnit) ], ReferenceSpace.prototype, "_unit", void 0); exports.ReferenceSpace = ReferenceSpace = ReferenceSpace_1 = tslib_1.__decorate([ (0, decorators_1.SerializableObject)(), tslib_1.__metadata("design:paramtypes", [Object]) ], ReferenceSpace); //# sourceMappingURL=ReferenceSpace.js.map