import {describe, test, assert} from 'vitest';
import {Size} from '../../src/image/size.js';
import {Spacing} from '../../src/image/spacing.js';
import {Point3D} from '../../src/math/point.js';
import {Matrix33} from '../../src/math/matrix.js';
import {Geometry} from '../../src/image/geometry.js';
import {ResamplingFilter} from '../../src/image/resamplingFilter.js';
import {
generateWorkerMessages,
generateResampledGeometry
} from '../../src/image/resamplingThread.js';
/**
* Tests for the 'image/resamplingFilter.js' file.
*/
describe('image', () => {
/**
* Tests for {@link ResamplingFilter}.
*
* @function module:tests/image~resamplingfilter-class
*/
test('ResamplingFilter class', () => {
/* eslint-disable @stylistic/js/array-element-newline */
const resamplingFilter = new ResamplingFilter();
const imgSize0 = new Size([3, 3, 2]);
const imgSpacing0 = new Spacing([1, 2, 3]);
const imgOrigins0 = [
new Point3D(0, 0, 0),
new Point3D(0, 0, 3)
];
const imgOrientation0 = new Matrix33([
1, 0, 0,
0, 1, 0,
0, 0, 1
]);
const imgGeometry0 = new Geometry(
imgOrigins0,
imgSize0,
imgSpacing0,
imgOrientation0
);
const imgBuffer0 = new Uint8Array([
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 1, 1,
0, 1, 1,
]);
// Basic 90° X-Axis Rotation
// --------------------------
const targetOrientation0 = new Matrix33([
1, 0, 0,
0, 0, -1,
0, 1, 0
]);
const resampledGeometry0 = generateResampledGeometry(
imgGeometry0,
targetOrientation0
);
const imgEvent0 = generateWorkerMessages(
imgBuffer0,
imgGeometry0,
resampledGeometry0,
0,
false,
'0'
);
const runReturn0 = resamplingFilter.run(imgEvent0[0]);
const expectedSize0 = new Size([3, 2, 3]);
const expectedSpacing0 = new Spacing([1, 3, 2]);
const expectedOrigins0 = [
new Point3D(0, 6, 0),
new Point3D(0, 4, 0),
new Point3D(0, 2, 0),
];
const expectedGeometry0 = new Geometry(
expectedOrigins0,
expectedSize0,
expectedSpacing0,
targetOrientation0
);
const expectedBuffer0 = new Uint8Array([
0, 1, 1,
0, 1, 1,
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 0, 0,
]);
const buffersMatch0 =
expectedBuffer0.map((value, index) => {
return value === runReturn0.targetImageBuffer[index];
}).reduce((a, b) => {
return a && b;
});
const geometriesMatch0 =
expectedGeometry0.equals(resampledGeometry0);
assert.equal(
buffersMatch0,
1,
'Expected 90° X-axis rotation resampled buffer to match expected buffer'
);
assert.ok(
geometriesMatch0,
'Expected 90° X-axis rotation resampled \
geometry to match expected geometry'
);
// Basic 90° Y-Axis Rotation
// --------------------------
const targetOrientation1 = new Matrix33([
0, 0, 1,
0, 1, 0,
-1, 0, 0
]);
const resampledGeometry1 = generateResampledGeometry(
imgGeometry0,
targetOrientation1
);
const imgEvent1 = generateWorkerMessages(
imgBuffer0,
imgGeometry0,
resampledGeometry1,
0,
false,
'1'
);
const runReturn1 = resamplingFilter.run(imgEvent1[0]);
const expectedSize1 = new Size([2, 3, 3]);
const expectedSpacing1 = new Spacing([3, 2, 1]);
const expectedOrigins1 = [
new Point3D(0, 0, 6),
new Point3D(1, 0, 6),
new Point3D(2, 0, 6),
];
const expectedGeometry1 = new Geometry(
expectedOrigins1,
expectedSize1,
expectedSpacing1,
targetOrientation1
);
const expectedBuffer1 = new Uint8Array([
0, 0,
0, 0,
0, 0,
0, 0,
1, 1,
1, 1,
0, 0,
1, 1,
1, 1,
]);
const buffersMatch1 =
expectedBuffer1.map((value, index) => {
return value === runReturn1.targetImageBuffer[index];
}).reduce((a, b) => {
return a && b;
});
const geometriesMatch1 =
expectedGeometry1.equals(resampledGeometry1);
assert.equal(
buffersMatch1,
1,
'Expected 90° Y-axis rotation resampled buffer to match expected buffer'
);
assert.ok(
geometriesMatch1,
'Expected 90° Y-axis rotation resampled \
geometry to match expected geometry'
);
// Basic 90° Z-Axis Rotation
// --------------------------
const targetOrientation2 = new Matrix33([
0, -1, 0,
1, 0, 0,
0, 0, 1
]);
const resampledGeometry2 = generateResampledGeometry(
imgGeometry0,
targetOrientation2
);
const imgEvent2 = generateWorkerMessages(
imgBuffer0,
imgGeometry0,
resampledGeometry2,
0,
false,
'2'
);
const runReturn2 = resamplingFilter.run(imgEvent2[0]);
const expectedSize2 = new Size([3, 3, 2]);
const expectedSpacing2 = new Spacing([2, 1, 3]);
const expectedOrigins2 = [
new Point3D(3, 0, 0),
new Point3D(3, 0, 3),
];
const expectedGeometry2 = new Geometry(
expectedOrigins2,
expectedSize2,
expectedSpacing2,
targetOrientation2
);
const expectedBuffer2 = new Uint8Array([
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 0, 0,
]);
const buffersMatch2 =
expectedBuffer2.map((value, index) => {
return value === runReturn2.targetImageBuffer[index];
}).reduce((a, b) => {
return a && b;
});
const geometriesMatch2 =
expectedGeometry2.equals(resampledGeometry2);
assert.equal(
buffersMatch2,
1,
'Expected 90° Z-axis rotation resampled buffer to match expected buffer'
);
assert.ok(
geometriesMatch2,
'Expected 90° Z-axis rotation resampled \
geometry to match expected geometry'
);
// Basic 90° 4D Rotation
// --------------------------
const imgSize3 = new Size([3, 3, 2, 2]);
const imgSpacing3 = new Spacing([1, 2, 3, 1]);
const imgOrigins3 = [
new Point3D(0, 0, 0),
new Point3D(0, 0, 3)
];
const imgOrientation3 = new Matrix33([
1, 0, 0,
0, 1, 0,
0, 0, 1
]);
const imgGeometry3 = new Geometry(
imgOrigins3,
imgSize3,
imgSpacing3,
imgOrientation3
);
const imgBuffer3 = new Uint8Array([
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 0, 0,
]);
const targetOrientation3 = new Matrix33([
0, -1, 0,
1, 0, 0,
0, 0, 1
]);
const resampledGeometry3 = generateResampledGeometry(
imgGeometry3,
targetOrientation3
);
const imgEvent3 = generateWorkerMessages(
imgBuffer3,
imgGeometry3,
resampledGeometry3,
false
);
const runReturn3a = resamplingFilter.run(imgEvent3[0]);
const runReturn3b = resamplingFilter.run(imgEvent3[1]);
const expectedSize3 = new Size([3, 3, 2, 2]);
const expectedSpacing3 = new Spacing([2, 1, 3, 1]);
const expectedOrigins3 = [
new Point3D(3, 0, 0),
new Point3D(3, 0, 3),
];
const expectedGeometry3 = new Geometry(
expectedOrigins3,
expectedSize3,
expectedSpacing3,
targetOrientation3
);
const expectedBuffer3a = new Uint8Array([
0, 1, 1,
0, 1, 1,
0, 0, 0,
0, 1, 1,
0, 1, 1,
0, 0, 0
]);
const expectedBuffer3b = new Uint8Array([
1, 1, 0,
1, 1, 0,
0, 0, 0,
1, 1, 0,
1, 1, 0,
0, 0, 0
]);
const buffersMatch3a =
expectedBuffer3a.map((value, index) => {
return value === runReturn3a.targetImageBuffer[index];
}).reduce((a, b) => {
return a && b;
});
const buffersMatch3b =
expectedBuffer3b.map((value, index) => {
return value === runReturn3b.targetImageBuffer[index];
}).reduce((a, b) => {
return a && b;
});
const geometriesMatch3 =
expectedGeometry3.equals(resampledGeometry3);
assert.equal(
buffersMatch3a,
1,
'Expected 90° 4D resampled buffer for frame 1 to match expected buffer'
);
assert.equal(
buffersMatch3b,
1,
'Expected 90° 4D resampled buffer for frame 2 to match expected buffer'
);
assert.ok(
geometriesMatch3,
'Expected 90° 4D resampled geometry to match expected geometry'
);
/* eslint-enable @stylistic/js/array-element-newline */
});
});