@kitware/vtk.js 28.12.3 → 28.12.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Imaging/Core/ImageReslice.js +21 -50
- package/macros2.js +5 -0
- package/package.json +1 -1
|
@@ -29,7 +29,7 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
29
29
|
const superClass = {
|
|
30
30
|
...publicAPI
|
|
31
31
|
};
|
|
32
|
-
|
|
32
|
+
const indexMatrix = mat4.identity(new Float64Array(16));
|
|
33
33
|
let optimizedTransform = null;
|
|
34
34
|
function getImageResliceSlabTrap(tmpPtr, inComponents, sampleCount, f) {
|
|
35
35
|
const n = sampleCount - 1;
|
|
@@ -218,7 +218,7 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
218
218
|
let interpolationMode = model.interpolationMode;
|
|
219
219
|
model.usePermuteExecute = false;
|
|
220
220
|
if (model.optimization) {
|
|
221
|
-
if (model.slabSliceSpacingFraction === 1.0 && model.interpolator.isSeparable() && publicAPI.isPermutationMatrix(indexMatrix)) {
|
|
221
|
+
if (optimizedTransform == null && model.slabSliceSpacingFraction === 1.0 && model.interpolator.isSeparable() && publicAPI.isPermutationMatrix(indexMatrix)) {
|
|
222
222
|
model.usePermuteExecute = true;
|
|
223
223
|
if (publicAPI.canUseNearestNeighbor(indexMatrix, outWholeExt)) {
|
|
224
224
|
interpolationMode = InterpolationMode.NEAREST;
|
|
@@ -286,7 +286,7 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
286
286
|
const rescaleScalars = model.scalarShift !== 0.0 || model.scalarScale !== 1.0;
|
|
287
287
|
|
|
288
288
|
// is nearest neighbor optimization possible?
|
|
289
|
-
const optimizeNearest = interpolationMode === InterpolationMode.NEAREST && borderMode === ImageBorderMode.CLAMP && !(perspective || convertScalars != null || rescaleScalars) && inputScalarType === outScalars.getDataType() && fullSize === inScalars.getNumberOfTuples() && model.border === true && nsamples <= 1;
|
|
289
|
+
const optimizeNearest = interpolationMode === InterpolationMode.NEAREST && borderMode === ImageBorderMode.CLAMP && !(optimizedTransform != null || perspective || convertScalars != null || rescaleScalars) && inputScalarType === outScalars.getDataType() && fullSize === inScalars.getNumberOfTuples() && model.border === true && nsamples <= 1;
|
|
290
290
|
|
|
291
291
|
// get pixel information
|
|
292
292
|
const scalarType = outScalars.getDataType();
|
|
@@ -306,11 +306,6 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
306
306
|
origin[i] = newmat[4 * 3 + i];
|
|
307
307
|
}
|
|
308
308
|
|
|
309
|
-
// get the input origin and spacing for conversion purposes
|
|
310
|
-
model.interpolator.getOrigin();
|
|
311
|
-
const inSpacing = model.interpolator.getSpacing();
|
|
312
|
-
[1.0 / inSpacing[0], 1.0 / inSpacing[1], 1.0 / inSpacing[2]];
|
|
313
|
-
|
|
314
309
|
// allocate an output row of type double
|
|
315
310
|
let floatPtr = null;
|
|
316
311
|
if (!optimizeNearest) {
|
|
@@ -409,6 +404,16 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
409
404
|
inPoint[1] *= f;
|
|
410
405
|
inPoint[2] *= f;
|
|
411
406
|
}
|
|
407
|
+
if (optimizedTransform !== null) {
|
|
408
|
+
// get the input origin and spacing for conversion purposes
|
|
409
|
+
const inOrigin = model.interpolator.getOrigin();
|
|
410
|
+
const inSpacing = model.interpolator.getSpacing();
|
|
411
|
+
const inInvSpacing = [1.0 / inSpacing[0], 1.0 / inSpacing[1], 1.0 / inSpacing[2]];
|
|
412
|
+
|
|
413
|
+
// apply the AbstractTransform if there is one
|
|
414
|
+
// TBD: handle inDirection
|
|
415
|
+
publicAPI.applyTransform(optimizedTransform, inPoint, inOrigin, inInvSpacing);
|
|
416
|
+
}
|
|
412
417
|
if (model.interpolator.checkBoundsIJK(inPoint)) {
|
|
413
418
|
// do the interpolation
|
|
414
419
|
isInBounds = 1;
|
|
@@ -541,63 +546,29 @@ function vtkImageReslice(publicAPI, model) {
|
|
|
541
546
|
* @returns
|
|
542
547
|
*/
|
|
543
548
|
publicAPI.getIndexMatrix = (input, output) => {
|
|
544
|
-
// first verify that we have to update the matrix
|
|
545
|
-
if (indexMatrix === null) {
|
|
546
|
-
indexMatrix = mat4.identity(new Float64Array(16));
|
|
547
|
-
}
|
|
548
|
-
const inOrigin = input.getOrigin();
|
|
549
|
-
const inSpacing = input.getSpacing();
|
|
550
|
-
const inDirection = input.getDirection();
|
|
551
|
-
const outOrigin = output.getOrigin();
|
|
552
|
-
const outSpacing = output.getSpacing();
|
|
553
549
|
const transform = mat4.identity(new Float64Array(16));
|
|
554
|
-
|
|
555
|
-
const outMatrix = mat4.identity(new Float64Array(16));
|
|
550
|
+
optimizedTransform = null;
|
|
556
551
|
if (model.resliceAxes) {
|
|
557
552
|
mat4.copy(transform, model.resliceAxes);
|
|
558
553
|
}
|
|
559
554
|
if (model.resliceTransform) {
|
|
560
555
|
if (model.resliceTransform.isA('vtkHomogeneousTransform')) {
|
|
561
|
-
// transform->PostMultiply();
|
|
562
|
-
// transform->Concatenate(
|
|
563
|
-
// mat4.multiply(transform, transform, model.resliceTransform.getMatrix());
|
|
564
556
|
mat4.multiply(transform, model.resliceTransform.getMatrix(), transform);
|
|
565
557
|
} else {
|
|
566
558
|
// TODO
|
|
567
559
|
vtkWarningMacro('Non homogeneous transform have not yet been ported');
|
|
568
560
|
}
|
|
569
561
|
}
|
|
570
|
-
if (!vtkMath.isIdentity3x3(inDirection)) {
|
|
571
|
-
const imageTransform = vtkMatrixBuilder.buildFromRadian().translate(inOrigin[0], inOrigin[1], inOrigin[2]).multiply3x3(inDirection).translate(-inOrigin[0], -inOrigin[1], -inOrigin[2]);
|
|
572
|
-
mat4.multiply(transform, imageTransform.getMatrix(), transform);
|
|
573
|
-
}
|
|
574
|
-
|
|
575
|
-
// check to see if we have an identity matrix
|
|
576
|
-
let isIdentity = vtkMath.isIdentity(transform);
|
|
577
562
|
|
|
578
563
|
// the outMatrix takes OutputData indices to OutputData coordinates,
|
|
564
|
+
const outMatrix = output.getIndexToWorld();
|
|
565
|
+
mat4.multiply(transform, transform, outMatrix);
|
|
566
|
+
|
|
579
567
|
// the inMatrix takes InputData coordinates to InputData indices
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
inMatrix[4 * i + i] = 1.0 / inSpacing[i];
|
|
585
|
-
inMatrix[4 * 3 + i] = -inOrigin[i] / inSpacing[i];
|
|
586
|
-
outMatrix[4 * i + i] = outSpacing[i];
|
|
587
|
-
outMatrix[4 * 3 + i] = outOrigin[i];
|
|
588
|
-
}
|
|
589
|
-
if (!isIdentity) {
|
|
590
|
-
// transform.PreMultiply();
|
|
591
|
-
// transform.Concatenate(outMatrix);
|
|
592
|
-
mat4.multiply(transform, transform, outMatrix);
|
|
593
|
-
|
|
594
|
-
// the optimizedTransform requires data coords, not
|
|
595
|
-
// index coords, as its input
|
|
596
|
-
{
|
|
597
|
-
// transform->PostMultiply();
|
|
598
|
-
// transform->Concatenate(inMatrix);
|
|
599
|
-
mat4.multiply(transform, inMatrix, transform);
|
|
600
|
-
}
|
|
568
|
+
// the optimizedTransform requires data coords, not index coords, as its input
|
|
569
|
+
if (optimizedTransform == null) {
|
|
570
|
+
const inMatrix = input.getWorldToIndex();
|
|
571
|
+
mat4.multiply(transform, inMatrix, transform);
|
|
601
572
|
}
|
|
602
573
|
mat4.copy(indexMatrix, transform);
|
|
603
574
|
return indexMatrix;
|
package/macros2.js
CHANGED
|
@@ -154,6 +154,9 @@ function safeArrays(model) {
|
|
|
154
154
|
}
|
|
155
155
|
});
|
|
156
156
|
}
|
|
157
|
+
function isTypedArray(value) {
|
|
158
|
+
return Object.values(TYPED_ARRAYS).some(ctor => value instanceof ctor);
|
|
159
|
+
}
|
|
157
160
|
|
|
158
161
|
// ----------------------------------------------------------------------------
|
|
159
162
|
// shallow equals
|
|
@@ -346,6 +349,8 @@ function obj() {
|
|
|
346
349
|
jsonArchive[keyName] = jsonArchive[keyName].getState();
|
|
347
350
|
} else if (Array.isArray(jsonArchive[keyName])) {
|
|
348
351
|
jsonArchive[keyName] = jsonArchive[keyName].map(getStateArrayMapFunc);
|
|
352
|
+
} else if (isTypedArray(jsonArchive[keyName])) {
|
|
353
|
+
jsonArchive[keyName] = Array.from(jsonArchive[keyName]);
|
|
349
354
|
}
|
|
350
355
|
});
|
|
351
356
|
|