Skip to content

Commit

Permalink
feat(math)!: Move Quat.toMat4() to Mat4.createRotation() (#930)
Browse files Browse the repository at this point in the history
  • Loading branch information
jespertheend authored Apr 13, 2024
1 parent c9009fb commit 69e2c48
Show file tree
Hide file tree
Showing 6 changed files with 107 additions and 40 deletions.
29 changes: 29 additions & 0 deletions src/math/Mat4.js
Original file line number Diff line number Diff line change
Expand Up @@ -449,6 +449,35 @@ export class Mat4 {
]);
}

/**
* @param {import("./Quat.js").QuatParameters} args
*/
static createRotation(...args) {
const q = new Quat(...args);

// https://github.com/toji/gl-matrix/blob/6866ae93d19bbff032139941cbfe0ae68c4cdead/src/gl-matrix/mat4.js#L1186
const x2 = q.x + q.x;
const y2 = q.y + q.y;
const z2 = q.z + q.z;

const xx = q.x * x2;
const yx = q.y * x2;
const yy = q.y * y2;
const zx = q.z * x2;
const zy = q.z * y2;
const zz = q.z * z2;
const wx = q.w * x2;
const wy = q.w * y2;
const wz = q.w * z2;

return new Mat4([
[1 - yy - zz, yx + wz, zx - wy, 0],
[yx - wz, 1 - xx - zz, zy + wx, 0],
[zx + wy, zy - wx, 1 - xx - yy, 0],
[0, 0, 0, 1],
]);
}

/**
* @param {import("./Vec3.js").Vec3Parameters} args
*/
Expand Down
25 changes: 0 additions & 25 deletions src/math/Quat.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import { Mat4 } from "./Mat4.js";
import { Vec2 } from "./Vec2.js";
import { Vec3 } from "./Vec3.js";
import { Vec4 } from "./Vec4.js";
Expand Down Expand Up @@ -201,30 +200,6 @@ export class Quat {
return vec;
}

toMat4() {
// https://github.com/toji/gl-matrix/blob/6866ae93d19bbff032139941cbfe0ae68c4cdead/src/gl-matrix/mat4.js#L1186
const x2 = this.x + this.x;
const y2 = this.y + this.y;
const z2 = this.z + this.z;

const xx = this.x * x2;
const yx = this.y * x2;
const yy = this.y * y2;
const zx = this.z * x2;
const zy = this.z * y2;
const zz = this.z * z2;
const wx = this.w * x2;
const wy = this.w * y2;
const wz = this.w * z2;

return new Mat4([
[1 - yy - zz, yx + wz, zx - wy, 0],
[yx - wz, 1 - xx - zz, zy + wx, 0],
[zx + wy, zy - wx, 1 - xx - yy, 0],
[0, 0, 0, 1],
]);
}

// http://www.euclideanspace.com/maths/geometry/rotations/conversions/eulerToQuaternion/index.htm
/**
* @param {import("./Vec3.js").Vec3Parameters} args
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -626,7 +626,7 @@ export class ContentWindowEntityEditor extends ContentWindow {
} else if (this.transformationMode == "rotate") {
gizmo = this.gizmos.addGizmo(RotationGizmo);
gizmo.onDrag((e) => {
const localMatrix = e.localDelta.toMat4();
const localMatrix = Mat4.createRotation(e.localDelta);
this.dragSelectedEntities(localMatrix);
});
} else if (this.transformationMode == "scale") {
Expand Down
30 changes: 30 additions & 0 deletions test/unit/src/math/Mat4.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -205,6 +205,36 @@ Deno.test({
},
});

Deno.test({
name: "createTranslation",
fn() {
const mat = Mat4.createTranslation(1, 2, 3);
assertVecAlmostEquals(mat.getTranslation(), [1, 2, 3]);
},
});

Deno.test({
name: "createRotation",
fn() {
const quat = Quat.fromAxisAngle(0, 1, 0, Math.PI * 0.5);
const v1 = Vec3.forward.rotate(quat);

const mat = Mat4.createRotation(quat);
const v2 = new Vec3(0, 0, 1).multiply(mat);

assertVecAlmostEquals(v1, v2);
},
});

Deno.test({
name: "createScale",
fn() {
const mat = Mat4.createScale(1, 2, 3);

assertVecAlmostEquals(mat.getScale(), [1, 2, 3]);
},
});

Deno.test({
name: "multiplyMatrices",
fn() {
Expand Down
13 changes: 0 additions & 13 deletions test/unit/src/math/Quat.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,19 +17,6 @@ Deno.test({
},
});

Deno.test({
name: "toMat4()",
fn() {
const quat = Quat.fromAxisAngle(0, 1, 0, Math.PI * 0.5);
const v1 = Vec3.forward.rotate(quat);

const mat = quat.toMat4();
const v2 = new Vec3(0, 0, 1).multiply(mat);

assertVecAlmostEquals(v1, v2);
},
});

Deno.test({
name: "toString()",
fn() {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { basicTest } from "./shared.js";
import { ContentWindowEntityEditor } from "../../../../../../../studio/src/windowManagement/contentWindows/ContentWindowEntityEditor/ContentWindowEntityEditor.js";
import { assertEquals, assertInstanceOf } from "std/testing/asserts.ts";
import { Entity, Quat, TranslationGizmo, Vec3, assertQuatAlmostEquals, assertVecAlmostEquals } from "../../../../../../../src/mod.js";
import { Entity, Quat, RotationGizmo, TranslationGizmo, Vec3, assertQuatAlmostEquals, assertVecAlmostEquals } from "../../../../../../../src/mod.js";
import { stub } from "std/testing/mock.ts";

function createEntitiesForGizmoTests() {
Expand Down Expand Up @@ -203,3 +203,49 @@ Deno.test({
}
},
});

Deno.test({
name: "Dragging a rotation gizmo",
async fn() {
const { args, uninstall } = basicTest();
try {
const contentWindow = new ContentWindowEntityEditor(...args);
contentWindow.setTransformationMode("rotate");

/** @type {import("../../../../../../../src/gizmos/gizmos/RotationGizmo.js").RotationGizmoDragCallback[]} */
const onDragCbs = [];

/** @type {import("std/testing/mock.ts").Stub<import("../../../../../../../src/mod.js").GizmoManager, [...args: any[]], import("../../../../../../../src/mod.js").Gizmo>} */
const addGizmoStub = stub(contentWindow.gizmos, "addGizmo", (...args) => {
const gizmo = addGizmoStub.original.bind(contentWindow.gizmos)(...args);
if (gizmo instanceof RotationGizmo) {
stub(gizmo, "onDrag", (cb) => {
onDragCbs.push(cb);
});
}
return gizmo;
});

const { root } = createEntitiesForGizmoTests();
contentWindow.editingEntity = root;

contentWindow.selectionGroup.changeSelection({
added: [createMockEntitySelection(root)],
});

const gizmos = Array.from(contentWindow.gizmos.gizmos);
assertEquals(gizmos.length, 1);
assertInstanceOf(gizmos[0], RotationGizmo);

assertEquals(onDragCbs.length, 1);
onDragCbs[0]({
localDelta: Quat.fromAxisAngle(0, 1, 0, 0.2),
worldDelta: Quat.fromAxisAngle(0, 1, 0, 0.2),
});

assertQuatAlmostEquals(root.rot, Quat.fromAxisAngle(0, 1, 0, 0.2));
} finally {
uninstall();
}
},
});

0 comments on commit 69e2c48

Please sign in to comment.