wmc/se3.js

140 lines
3.0 KiB
JavaScript
Raw Normal View History

// all column-major, *sigh*
export function identity() {
return [
1.0, 0.0, 0.0, 0.0,
0.0, 1.0, 0.0, 0.0,
0.0, 0.0, 1.0, 0.0,
0.0, 0.0, 0.0, 1.0
];
}
export function rotx(rad) {
const s = Math.sin(rad);
const c = Math.cos(rad);
return [
1.0, 0.0, 0.0, 0.0,
0.0, c, s, 0.0,
0.0, -s, c, 0.0,
0.0, 0.0, 0.0, 1.0,
];
}
export function roty(rad) {
const s = Math.sin(rad);
const c = Math.cos(rad);
return [
c, 0.0, -s, 0.0,
0.0, 1.0, 0.0, 0.0,
s, 0.0, c, 0.0,
0.0, 0.0, 0.0, 1.0,
];
}
export function rotz(rad) {
const s = Math.sin(rad);
const c = Math.cos(rad);
return [
c, s, 0.0, 0.0,
-s, c, 0.0, 0.0,
0.0, 0.0, 1.0, 0.0,
0.0, 0.0, 0.0, 1.0,
];
}
export function apply(mat, vect) {
const indices = [0, 1, 2, 3];
const sum = v => v.reduce((a, b) => a + b);
return [
sum(indices.map(i => mat[4*i + 0] * vect[i])),
sum(indices.map(i => mat[4*i + 1] * vect[i])),
sum(indices.map(i => mat[4*i + 2] * vect[i])),
sum(indices.map(i => mat[4*i + 3] * vect[i])),
];
}
export function rotxyz(x, y, z) {
return [rotx(x), roty(y), rotz(z)].reduce(product);
}
2022-10-18 20:49:35 +00:00
export function rotationOnly(m) {
return [
m[0], m[1], m[2], 0.0,
m[4], m[5], m[6], 0.0,
m[8], m[9], m[10], 0.0,
0, 0, 0, 1,
];
}
export function translation(x, y, z) {
return [
1.0, 0.0, 0.0, 0.0,
0.0, 1.0, 0.0, 0.0,
0.0, 0.0, 1.0, 0.0,
x, y, z, 1.0,
];
}
2022-10-18 20:49:35 +00:00
export function orientationOnly(m) {
2021-12-17 14:16:57 +00:00
return [
2022-10-18 20:49:35 +00:00
m[0], m[1], m[2], 0,
m[4], m[5], m[6], 0,
m[8], m[9], m[10], 0,
0, 0, 0, 1,
];
}
export function inverse(m) {
const t = apply(m, [0, 0, 0, 1]);
const r = orientationOnly(m);
const newR = [
m[0], m[4], m[8], 0,
m[1], m[5], m[9], 0,
m[2], m[6], m[10], 0,
2021-12-17 14:16:57 +00:00
0, 0, 0, 1,
];
2022-10-18 20:49:35 +00:00
const newT = apply(newR, t);
const out = newR;
out[12] = -newT[0];
out[13] = -newT[1];
out[14] = -newT[2];
return out;
2021-12-17 14:16:57 +00:00
}
export function product(a, b) {
const c = (i, j) => (
a[4 * 0 + i] * b[4 * j + 0] +
a[4 * 1 + i] * b[4 * j + 1] +
a[4 * 2 + i] * b[4 * j + 2] +
a[4 * 3 + i] * b[4 * j + 3]
);
return [
c(0, 0), c(1, 0), c(2, 0), c(3, 0),
c(0, 1), c(1, 1), c(2, 1), c(3, 1),
c(0, 2), c(1, 2), c(2, 2), c(3, 2),
c(0, 3), c(1, 3), c(2, 3), c(3, 3),
];
}
export function ortho(aspectRatio) {
const out = identity();
out[0] = 1 / aspectRatio;
return out;
}
export function perspective(fov, aspectRatio, near, far) {
const f = 1 / Math.tan(fov / 2);
const rangeInv = 1 / (near - far);
return [
f / aspectRatio, 0.0, 0.0, 0.0,
0.0, f, 0.0, 0.0,
0.0, 0.0, (near + far) * rangeInv, -1,
0.0, 0.0, near * far * rangeInv * 2, 0,
];
2022-10-18 20:49:35 +00:00
};