@cornerstonejs/adapters 2.11.7 → 2.12.1
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/dist/esm/adapters/Cornerstone/Segmentation_4X.d.ts +45 -3
- package/dist/esm/adapters/Cornerstone/Segmentation_4X.js +35 -2
- package/dist/esm/adapters/Cornerstone3D/Segmentation/generateToolState.d.ts +17 -2
- package/dist/esm/adapters/Cornerstone3D/Segmentation/generateToolState.js +15 -2
- package/dist/esm/adapters/Cornerstone3D/Segmentation/index.d.ts +2 -2
- package/dist/esm/adapters/Cornerstone3D/Segmentation/index.js +1 -1
- package/dist/esm/adapters/Cornerstone3D/Segmentation/labelmapImagesFromBuffer.d.ts +13 -0
- package/dist/esm/adapters/Cornerstone3D/Segmentation/labelmapImagesFromBuffer.js +198 -0
- package/package.json +4 -4
|
@@ -1,3 +1,48 @@
|
|
|
1
|
+
export function generateSegmentation(images: object[], inputLabelmaps3D: any | any[], userOptions?: any): Blob;
|
|
2
|
+
export function fillSegmentation(segmentation: any, inputLabelmaps3D: any, userOptions?: {}): object;
|
|
3
|
+
export function _getLabelmapsFromReferencedFrameIndicies(labelmap3D: any, referencedFrameIndicies: any): any[];
|
|
4
|
+
export function _createSegFromImages(images: any[], isMultiframe: boolean, options: any): any;
|
|
5
|
+
export function generateToolState(referencedImageIds: string[], arrayBuffer: ArrayBuffer, metadataProvider: any, options: obj): [];
|
|
6
|
+
export function findReferenceSourceImageId(multiframe: any, frameSegment: Int, imageIds: string[], metadataProvider: any, tolerance: Float, sopUIDImageIdIndexMap: any): string;
|
|
7
|
+
export function checkSEGsOverlapping(pixelData: any, multiframe: any, imageIds: any, validOrientations: any, metadataProvider: any, tolerance: any, TypedArrayConstructor: any, sopUIDImageIdIndexMap: any): boolean;
|
|
8
|
+
export function insertOverlappingPixelDataPlanar(segmentsOnFrame: any, segmentsOnFrameArray: any, labelmapBufferArray: any, pixelData: any, multiframe: any, imageIds: any, validOrientations: any, metadataProvider: any, tolerance: any, TypedArrayConstructor: any, segmentsPixelIndices: any, sopUIDImageIdIndexMap: any): void;
|
|
9
|
+
export function insertPixelDataPlanar(segmentsOnFrame: any, segmentsOnFrameArray: any, labelmapBufferArray: any, pixelData: any, multiframe: any, imageIds: any, validOrientations: any, metadataProvider: any, tolerance: any, TypedArrayConstructor: any, segmentsPixelIndices: any, sopUIDImageIdIndexMap: any, imageIdMaps: any, eventTarget: any, triggerEvent: any): Promise<any>;
|
|
10
|
+
export function unpackPixelData(multiframe: any, options: any): Uint8Array;
|
|
11
|
+
export function getUnpackedChunks(data: any, maxBytesPerChunk: any): any[];
|
|
12
|
+
export function getImageIdOfSourceImageBySourceImageSequence(SourceImageSequence: any, sopUIDImageIdIndexMap: any): string;
|
|
13
|
+
export function getImageIdOfSourceImagebyGeometry(ReferencedSeriesInstanceUID: string, FrameOfReferenceUID: string, PerFrameFunctionalGroup: any, imageIds: string[], metadataProvider: any, tolerance: Float): string;
|
|
14
|
+
export function getImageIdOfReferencedFrame(sopInstanceUid: string, frameNumber: number, sopUIDImageIdIndexMap: any): string;
|
|
15
|
+
export function getValidOrientations(iop: any): any;
|
|
16
|
+
export function alignPixelDataWithSourceData(pixelData2D: Ndarray, iop: any, orientations: any, tolerance: any): Ndarray;
|
|
17
|
+
export function getSegmentMetadata(multiframe: any, seriesInstanceUid: any): {
|
|
18
|
+
seriesInstanceUid: any;
|
|
19
|
+
data: any[];
|
|
20
|
+
};
|
|
21
|
+
export function readFromUnpackedChunks(chunks: ArrayBuffer[], offset: number, length: number): Uint8Array;
|
|
22
|
+
export function getUnpackedOffsetAndLength(chunks: any, offset: any, length: any): {
|
|
23
|
+
start: {
|
|
24
|
+
chunkIndex: number;
|
|
25
|
+
offset: any;
|
|
26
|
+
};
|
|
27
|
+
end: {
|
|
28
|
+
chunkIndex: number;
|
|
29
|
+
offset: any;
|
|
30
|
+
};
|
|
31
|
+
};
|
|
32
|
+
export function calculateCentroid(imageIdIndexBufferIndex: any, multiframe: any, metadataProvider: any, imageIds: any): {
|
|
33
|
+
image: {
|
|
34
|
+
x: number;
|
|
35
|
+
y: number;
|
|
36
|
+
z: number;
|
|
37
|
+
};
|
|
38
|
+
world: {
|
|
39
|
+
x: number;
|
|
40
|
+
y: number;
|
|
41
|
+
z: number;
|
|
42
|
+
};
|
|
43
|
+
count: number;
|
|
44
|
+
};
|
|
45
|
+
export function getSegmentIndex(multiframe: any, frame: any): any;
|
|
1
46
|
export default Segmentation;
|
|
2
47
|
export type BrushData = {
|
|
3
48
|
toolState: any;
|
|
@@ -8,6 +53,3 @@ declare namespace Segmentation {
|
|
|
8
53
|
export { generateToolState };
|
|
9
54
|
export { fillSegmentation };
|
|
10
55
|
}
|
|
11
|
-
export function fillSegmentation(segmentation: any, inputLabelmaps3D: any, userOptions?: {}): object;
|
|
12
|
-
export function generateSegmentation(images: object[], inputLabelmaps3D: any | any[], userOptions?: any): Blob;
|
|
13
|
-
export function generateToolState(referencedImageIds: string[], arrayBuffer: ArrayBuffer, metadataProvider: any, options: obj): [];
|
|
@@ -180,7 +180,9 @@ function _createSegFromImages(images, isMultiframe, options) {
|
|
|
180
180
|
*/
|
|
181
181
|
function generateToolState(_x, _x2, _x3, _x4) {
|
|
182
182
|
return _generateToolState.apply(this, arguments);
|
|
183
|
-
}
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
// function insertPixelDataPerpendicular(
|
|
184
186
|
// segmentsOnFrame,
|
|
185
187
|
// labelmapBuffer,
|
|
186
188
|
// pixelData,
|
|
@@ -195,23 +197,30 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
195
197
|
// Rows,
|
|
196
198
|
// Columns
|
|
197
199
|
// } = multiframe;
|
|
200
|
+
|
|
198
201
|
// const firstImagePlaneModule = metadataProvider.get(
|
|
199
202
|
// "imagePlaneModule",
|
|
200
203
|
// imageIds[0]
|
|
201
204
|
// );
|
|
205
|
+
|
|
202
206
|
// const lastImagePlaneModule = metadataProvider.get(
|
|
203
207
|
// "imagePlaneModule",
|
|
204
208
|
// imageIds[imageIds.length - 1]
|
|
205
209
|
// );
|
|
210
|
+
|
|
206
211
|
// console.log(firstImagePlaneModule);
|
|
207
212
|
// console.log(lastImagePlaneModule);
|
|
213
|
+
|
|
208
214
|
// const corners = [
|
|
209
215
|
// ...getCorners(firstImagePlaneModule),
|
|
210
216
|
// ...getCorners(lastImagePlaneModule)
|
|
211
217
|
// ];
|
|
218
|
+
|
|
212
219
|
// console.log(`corners:`);
|
|
213
220
|
// console.log(corners);
|
|
221
|
+
|
|
214
222
|
// const indexToWorld = mat4.create();
|
|
223
|
+
|
|
215
224
|
// const ippFirstFrame = firstImagePlaneModule.imagePositionPatient;
|
|
216
225
|
// const rowCosines = Array.isArray(firstImagePlaneModule.rowCosines)
|
|
217
226
|
// ? [...firstImagePlaneModule.rowCosines]
|
|
@@ -220,6 +229,7 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
220
229
|
// firstImagePlaneModule.rowCosines.y,
|
|
221
230
|
// firstImagePlaneModule.rowCosines.z
|
|
222
231
|
// ];
|
|
232
|
+
|
|
223
233
|
// const columnCosines = Array.isArray(firstImagePlaneModule.columnCosines)
|
|
224
234
|
// ? [...firstImagePlaneModule.columnCosines]
|
|
225
235
|
// : [
|
|
@@ -227,7 +237,9 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
227
237
|
// firstImagePlaneModule.columnCosines.y,
|
|
228
238
|
// firstImagePlaneModule.columnCosines.z
|
|
229
239
|
// ];
|
|
240
|
+
|
|
230
241
|
// const { pixelSpacing } = firstImagePlaneModule;
|
|
242
|
+
|
|
231
243
|
// mat4.set(
|
|
232
244
|
// indexToWorld,
|
|
233
245
|
// // Column 1
|
|
@@ -251,36 +263,50 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
251
263
|
// 0,
|
|
252
264
|
// 1
|
|
253
265
|
// );
|
|
266
|
+
|
|
254
267
|
// // TODO -> Get origin and (x,y,z) increments to build a translation matrix:
|
|
255
268
|
// // TODO -> Equation C.7.6.2.1-1
|
|
269
|
+
|
|
256
270
|
// // | cx*di rx* Xx 0 | |x|
|
|
257
271
|
// // | cy*di ry Xy 0 | |y|
|
|
258
272
|
// // | cz*di rz Xz 0 | |z|
|
|
259
273
|
// // | tx ty tz 1 | |1|
|
|
274
|
+
|
|
260
275
|
// // const [
|
|
261
276
|
// // 0, 0 , 0 , 0,
|
|
262
277
|
// // 0, 0 , 0 , 0,
|
|
263
278
|
// // 0, 0 , 0 , 0,
|
|
264
279
|
// // ipp[0], ipp[1] , ipp[2] , 1,
|
|
265
280
|
// // ]
|
|
281
|
+
|
|
266
282
|
// // Each frame:
|
|
283
|
+
|
|
267
284
|
// // Find which corner the first voxel lines up with (one of 8 corners.)
|
|
285
|
+
|
|
268
286
|
// // Find how i,j,k orient with respect to source volume.
|
|
269
287
|
// // Go through each frame, find location in source to start, and whether to increment +/ix,+/-y,+/-z
|
|
270
288
|
// // through each voxel.
|
|
289
|
+
|
|
271
290
|
// // [1,0,0,0,1,0]
|
|
291
|
+
|
|
272
292
|
// // const [
|
|
293
|
+
|
|
273
294
|
// // ]
|
|
295
|
+
|
|
274
296
|
// // Invert transformation matrix to get worldToIndex
|
|
297
|
+
|
|
275
298
|
// // Apply world to index on each point to fill up the matrix.
|
|
299
|
+
|
|
276
300
|
// // const sharedImageOrientationPatient = SharedFunctionalGroupsSequence.PlaneOrientationSequence
|
|
277
301
|
// // ? SharedFunctionalGroupsSequence.PlaneOrientationSequence
|
|
278
302
|
// // .ImageOrientationPatient
|
|
279
303
|
// // : undefined;
|
|
280
304
|
// // const sliceLength = Columns * Rows;
|
|
281
305
|
// }
|
|
306
|
+
|
|
282
307
|
// function getCorners(imagePlaneModule) {
|
|
283
308
|
// // console.log(imagePlaneModule);
|
|
309
|
+
|
|
284
310
|
// const {
|
|
285
311
|
// rows,
|
|
286
312
|
// columns,
|
|
@@ -290,18 +316,22 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
290
316
|
// rowPixelSpacing,
|
|
291
317
|
// columnPixelSpacing
|
|
292
318
|
// } = imagePlaneModule;
|
|
319
|
+
|
|
293
320
|
// const rowLength = columns * columnPixelSpacing;
|
|
294
321
|
// const columnLength = rows * rowPixelSpacing;
|
|
322
|
+
|
|
295
323
|
// const entireRowVector = [
|
|
296
324
|
// rowLength * columnCosines[0],
|
|
297
325
|
// rowLength * columnCosines[1],
|
|
298
326
|
// rowLength * columnCosines[2]
|
|
299
327
|
// ];
|
|
328
|
+
|
|
300
329
|
// const entireColumnVector = [
|
|
301
330
|
// columnLength * rowCosines[0],
|
|
302
331
|
// columnLength * rowCosines[1],
|
|
303
332
|
// columnLength * rowCosines[2]
|
|
304
333
|
// ];
|
|
334
|
+
|
|
305
335
|
// const topLeft = [ipp[0], ipp[1], ipp[2]];
|
|
306
336
|
// const topRight = [
|
|
307
337
|
// topLeft[0] + entireRowVector[0],
|
|
@@ -313,13 +343,16 @@ function generateToolState(_x, _x2, _x3, _x4) {
|
|
|
313
343
|
// topLeft[1] + entireColumnVector[1],
|
|
314
344
|
// topLeft[2] + entireColumnVector[2]
|
|
315
345
|
// ];
|
|
346
|
+
|
|
316
347
|
// const bottomRight = [
|
|
317
348
|
// bottomLeft[0] + entireRowVector[0],
|
|
318
349
|
// bottomLeft[1] + entireRowVector[1],
|
|
319
350
|
// bottomLeft[2] + entireRowVector[2]
|
|
320
351
|
// ];
|
|
352
|
+
|
|
321
353
|
// return [topLeft, topRight, bottomLeft, bottomRight];
|
|
322
354
|
// }
|
|
355
|
+
|
|
323
356
|
/**
|
|
324
357
|
* Find the reference frame of the segmentation frame in the source data.
|
|
325
358
|
*
|
|
@@ -1149,4 +1182,4 @@ var Segmentation = {
|
|
|
1149
1182
|
fillSegmentation: fillSegmentation
|
|
1150
1183
|
};
|
|
1151
1184
|
|
|
1152
|
-
export { Segmentation as default, fillSegmentation, generateSegmentation, generateToolState };
|
|
1185
|
+
export { _createSegFromImages, _getLabelmapsFromReferencedFrameIndicies, alignPixelDataWithSourceData, calculateCentroid, checkSEGsOverlapping, Segmentation as default, fillSegmentation, findReferenceSourceImageId, generateSegmentation, generateToolState, getImageIdOfReferencedFrame, getImageIdOfSourceImageBySourceImageSequence, getImageIdOfSourceImagebyGeometry, getSegmentIndex, getSegmentMetadata, getUnpackedChunks, getUnpackedOffsetAndLength, getValidOrientations, insertOverlappingPixelDataPlanar, insertPixelDataPlanar, readFromUnpackedChunks, unpackPixelData };
|
|
@@ -1,2 +1,17 @@
|
|
|
1
|
-
declare function generateToolState(imageIds: any, arrayBuffer: any, metadataProvider: any, skipOverlapping?: boolean, tolerance?: number): any;
|
|
2
|
-
|
|
1
|
+
declare function generateToolState(imageIds: any, arrayBuffer: any, metadataProvider: any, skipOverlapping?: boolean, tolerance?: number, cs3dVersion?: number): any;
|
|
2
|
+
declare function createFromDICOMSegBuffer(referencedImageIds: any, arrayBuffer: any, { metadataProvider, skipOverlapping, tolerance }: {
|
|
3
|
+
metadataProvider: any;
|
|
4
|
+
skipOverlapping?: boolean;
|
|
5
|
+
tolerance?: number;
|
|
6
|
+
}): Promise<{
|
|
7
|
+
labelMapImages: any[][];
|
|
8
|
+
segMetadata: {
|
|
9
|
+
seriesInstanceUid: any;
|
|
10
|
+
data: any[];
|
|
11
|
+
};
|
|
12
|
+
segmentsOnFrame: any[];
|
|
13
|
+
segmentsOnFrameArray: any[];
|
|
14
|
+
centroids: Map<any, any>;
|
|
15
|
+
overlappingSegments: any;
|
|
16
|
+
}>;
|
|
17
|
+
export { generateToolState, createFromDICOMSegBuffer };
|
|
@@ -1,9 +1,22 @@
|
|
|
1
1
|
import { generateToolState as generateToolState$1 } from '../../Cornerstone/Segmentation.js';
|
|
2
|
+
import { createLabelmapsFromBufferInternal } from './labelmapImagesFromBuffer.js';
|
|
2
3
|
|
|
3
4
|
function generateToolState(imageIds, arrayBuffer, metadataProvider) {
|
|
4
5
|
var skipOverlapping = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : false;
|
|
5
6
|
var tolerance = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : 1e-3;
|
|
6
|
-
|
|
7
|
+
var cs3dVersion = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : 4;
|
|
8
|
+
return generateToolState$1(imageIds, arrayBuffer, metadataProvider, skipOverlapping, tolerance, cs3dVersion);
|
|
9
|
+
}
|
|
10
|
+
function createFromDICOMSegBuffer(referencedImageIds, arrayBuffer, _ref) {
|
|
11
|
+
var metadataProvider = _ref.metadataProvider,
|
|
12
|
+
_ref$skipOverlapping = _ref.skipOverlapping,
|
|
13
|
+
skipOverlapping = _ref$skipOverlapping === void 0 ? false : _ref$skipOverlapping,
|
|
14
|
+
_ref$tolerance = _ref.tolerance,
|
|
15
|
+
tolerance = _ref$tolerance === void 0 ? 1e-3 : _ref$tolerance;
|
|
16
|
+
return createLabelmapsFromBufferInternal(referencedImageIds, arrayBuffer, metadataProvider, {
|
|
17
|
+
skipOverlapping: skipOverlapping,
|
|
18
|
+
tolerance: tolerance
|
|
19
|
+
});
|
|
7
20
|
}
|
|
8
21
|
|
|
9
|
-
export { generateToolState };
|
|
22
|
+
export { createFromDICOMSegBuffer, generateToolState };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { generateSegmentation } from "./generateSegmentation";
|
|
2
2
|
import { generateLabelMaps2DFrom3D } from "./generateLabelMaps2DFrom3D";
|
|
3
|
-
import { generateToolState } from "./generateToolState";
|
|
4
|
-
export { generateLabelMaps2DFrom3D, generateSegmentation, generateToolState };
|
|
3
|
+
import { generateToolState, createFromDICOMSegBuffer } from "./generateToolState";
|
|
4
|
+
export { generateLabelMaps2DFrom3D, generateSegmentation, generateToolState, createFromDICOMSegBuffer };
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
export { generateSegmentation } from './generateSegmentation.js';
|
|
2
2
|
export { generateLabelMaps2DFrom3D } from './generateLabelMaps2DFrom3D.js';
|
|
3
|
-
export { generateToolState } from './generateToolState.js';
|
|
3
|
+
export { createFromDICOMSegBuffer, generateToolState } from './generateToolState.js';
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
declare function createLabelmapsFromBufferInternal(referencedImageIds: any, arrayBuffer: any, metadataProvider: any, options: any): Promise<{
|
|
2
|
+
labelMapImages: any[][];
|
|
3
|
+
segMetadata: {
|
|
4
|
+
seriesInstanceUid: any;
|
|
5
|
+
data: any[];
|
|
6
|
+
};
|
|
7
|
+
segmentsOnFrame: any[];
|
|
8
|
+
segmentsOnFrameArray: any[];
|
|
9
|
+
centroids: Map<any, any>;
|
|
10
|
+
overlappingSegments: any;
|
|
11
|
+
}>;
|
|
12
|
+
export declare function insertPixelDataPlanar(segmentsOnFrame: any, labelMapImages: any, pixelData: any, multiframe: any, imageIds: any, validOrientations: any, metadataProvider: any, tolerance: any, segmentsPixelIndices: any, sopUIDImageIdIndexMap: any, imageIdMaps: any): Promise<unknown>;
|
|
13
|
+
export { createLabelmapsFromBufferInternal };
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
import { asyncToGenerator as _asyncToGenerator, regeneratorRuntime as _regeneratorRuntime, toConsumableArray as _toConsumableArray } from '../../../_virtual/_rollupPluginBabelHelpers.js';
|
|
2
|
+
import { imageLoader } from '@cornerstonejs/core';
|
|
3
|
+
import { data, normalizers, utilities } from 'dcmjs';
|
|
4
|
+
import ndarray from 'ndarray';
|
|
5
|
+
import checkOrientation from '../../helpers/checkOrientation.js';
|
|
6
|
+
import { calculateCentroid, checkSEGsOverlapping, unpackPixelData, getValidOrientations, getSegmentMetadata, readFromUnpackedChunks, alignPixelDataWithSourceData, getSegmentIndex, findReferenceSourceImageId } from '../../Cornerstone/Segmentation_4X.js';
|
|
7
|
+
|
|
8
|
+
var DicomMessage = data.DicomMessage,
|
|
9
|
+
DicomMetaDictionary = data.DicomMetaDictionary;
|
|
10
|
+
var Normalizer = normalizers.Normalizer;
|
|
11
|
+
var decode = utilities.compression.decode;
|
|
12
|
+
function createLabelmapsFromBufferInternal(_x, _x2, _x3, _x4) {
|
|
13
|
+
return _createLabelmapsFromBufferInternal.apply(this, arguments);
|
|
14
|
+
}
|
|
15
|
+
function _createLabelmapsFromBufferInternal() {
|
|
16
|
+
_createLabelmapsFromBufferInternal = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime().mark(function _callee(referencedImageIds, arrayBuffer, metadataProvider, options) {
|
|
17
|
+
var _options$skipOverlapp, skipOverlapping, _options$tolerance, tolerance, _options$TypedArrayCo, TypedArrayConstructor, _options$maxBytesPerC, maxBytesPerChunk, dicomData, dataset, multiframe, imagePlaneModule, generalSeriesModule, SeriesInstanceUID, ImageOrientationPatient, validOrientations, segMetadata, TransferSyntaxUID, pixelData, pixelDataChunks, rleEncodedFrames, orientation, sopUIDImageIdIndexMap, overlapping, insertFunction, segmentsOnFrameArray, segmentsOnFrame, imageIdMaps, labelMapImages, i, referenceImageId, labelMapImage, segmentsPixelIndices, overlappingSegments, centroidXYZ;
|
|
18
|
+
return _regeneratorRuntime().wrap(function _callee$(_context) {
|
|
19
|
+
while (1) switch (_context.prev = _context.next) {
|
|
20
|
+
case 0:
|
|
21
|
+
_options$skipOverlapp = options.skipOverlapping, skipOverlapping = _options$skipOverlapp === void 0 ? false : _options$skipOverlapp, _options$tolerance = options.tolerance, tolerance = _options$tolerance === void 0 ? 1e-3 : _options$tolerance, _options$TypedArrayCo = options.TypedArrayConstructor, TypedArrayConstructor = _options$TypedArrayCo === void 0 ? Uint8Array : _options$TypedArrayCo, _options$maxBytesPerC = options.maxBytesPerChunk, maxBytesPerChunk = _options$maxBytesPerC === void 0 ? 199000000 : _options$maxBytesPerC;
|
|
22
|
+
dicomData = DicomMessage.readFile(arrayBuffer);
|
|
23
|
+
dataset = DicomMetaDictionary.naturalizeDataset(dicomData.dict);
|
|
24
|
+
dataset._meta = DicomMetaDictionary.namifyDataset(dicomData.meta);
|
|
25
|
+
multiframe = Normalizer.normalizeToDataset([dataset]);
|
|
26
|
+
imagePlaneModule = metadataProvider.get("imagePlaneModule", referencedImageIds[0]);
|
|
27
|
+
generalSeriesModule = metadataProvider.get("generalSeriesModule", referencedImageIds[0]);
|
|
28
|
+
SeriesInstanceUID = generalSeriesModule.seriesInstanceUID;
|
|
29
|
+
if (!imagePlaneModule) {
|
|
30
|
+
console.warn("Insufficient metadata, imagePlaneModule missing.");
|
|
31
|
+
}
|
|
32
|
+
ImageOrientationPatient = Array.isArray(imagePlaneModule.rowCosines) ? [].concat(_toConsumableArray(imagePlaneModule.rowCosines), _toConsumableArray(imagePlaneModule.columnCosines)) : [imagePlaneModule.rowCosines.x, imagePlaneModule.rowCosines.y, imagePlaneModule.rowCosines.z, imagePlaneModule.columnCosines.x, imagePlaneModule.columnCosines.y, imagePlaneModule.columnCosines.z];
|
|
33
|
+
validOrientations = getValidOrientations(ImageOrientationPatient);
|
|
34
|
+
segMetadata = getSegmentMetadata(multiframe, SeriesInstanceUID);
|
|
35
|
+
TransferSyntaxUID = multiframe._meta.TransferSyntaxUID.Value[0];
|
|
36
|
+
if (!(TransferSyntaxUID === "1.2.840.10008.1.2.5")) {
|
|
37
|
+
_context.next = 22;
|
|
38
|
+
break;
|
|
39
|
+
}
|
|
40
|
+
rleEncodedFrames = Array.isArray(multiframe.PixelData) ? multiframe.PixelData : [multiframe.PixelData];
|
|
41
|
+
pixelData = decode(rleEncodedFrames, multiframe.Rows, multiframe.Columns);
|
|
42
|
+
if (!(multiframe.BitsStored === 1)) {
|
|
43
|
+
_context.next = 19;
|
|
44
|
+
break;
|
|
45
|
+
}
|
|
46
|
+
console.warn("No implementation for rle + bit packing.");
|
|
47
|
+
return _context.abrupt("return");
|
|
48
|
+
case 19:
|
|
49
|
+
pixelDataChunks = [pixelData];
|
|
50
|
+
_context.next = 25;
|
|
51
|
+
break;
|
|
52
|
+
case 22:
|
|
53
|
+
pixelDataChunks = unpackPixelData(multiframe, {
|
|
54
|
+
maxBytesPerChunk: maxBytesPerChunk
|
|
55
|
+
});
|
|
56
|
+
if (pixelDataChunks) {
|
|
57
|
+
_context.next = 25;
|
|
58
|
+
break;
|
|
59
|
+
}
|
|
60
|
+
throw new Error("Fractional segmentations are not yet supported");
|
|
61
|
+
case 25:
|
|
62
|
+
orientation = checkOrientation(multiframe, validOrientations, [imagePlaneModule.rows, imagePlaneModule.columns, referencedImageIds.length], tolerance);
|
|
63
|
+
sopUIDImageIdIndexMap = referencedImageIds.reduce(function (acc, imageId) {
|
|
64
|
+
var _metadataProvider$get = metadataProvider.get("generalImageModule", imageId),
|
|
65
|
+
sopInstanceUID = _metadataProvider$get.sopInstanceUID;
|
|
66
|
+
acc[sopInstanceUID] = imageId;
|
|
67
|
+
return acc;
|
|
68
|
+
}, {});
|
|
69
|
+
overlapping = false;
|
|
70
|
+
if (!skipOverlapping) {
|
|
71
|
+
overlapping = checkSEGsOverlapping(pixelDataChunks, multiframe, referencedImageIds, validOrientations, metadataProvider, tolerance, TypedArrayConstructor, sopUIDImageIdIndexMap);
|
|
72
|
+
}
|
|
73
|
+
_context.t0 = orientation;
|
|
74
|
+
_context.next = _context.t0 === "Planar" ? 32 : _context.t0 === "Perpendicular" ? 38 : _context.t0 === "Oblique" ? 39 : 40;
|
|
75
|
+
break;
|
|
76
|
+
case 32:
|
|
77
|
+
if (!overlapping) {
|
|
78
|
+
_context.next = 36;
|
|
79
|
+
break;
|
|
80
|
+
}
|
|
81
|
+
throw new Error("Overlapping segmentations are not yet supported.");
|
|
82
|
+
case 36:
|
|
83
|
+
insertFunction = insertPixelDataPlanar;
|
|
84
|
+
case 37:
|
|
85
|
+
return _context.abrupt("break", 40);
|
|
86
|
+
case 38:
|
|
87
|
+
throw new Error("Segmentations orthogonal to the acquisition plane of the source data are not yet supported.");
|
|
88
|
+
case 39:
|
|
89
|
+
throw new Error("Segmentations oblique to the acquisition plane of the source data are not yet supported.");
|
|
90
|
+
case 40:
|
|
91
|
+
segmentsOnFrameArray = [];
|
|
92
|
+
segmentsOnFrameArray[0] = [];
|
|
93
|
+
segmentsOnFrame = [];
|
|
94
|
+
imageIdMaps = {
|
|
95
|
+
indices: {},
|
|
96
|
+
metadata: {}
|
|
97
|
+
};
|
|
98
|
+
labelMapImages = [];
|
|
99
|
+
for (i = 0; i < referencedImageIds.length; i++) {
|
|
100
|
+
referenceImageId = referencedImageIds[i];
|
|
101
|
+
imageIdMaps.indices[referenceImageId] = i;
|
|
102
|
+
imageIdMaps.metadata[referenceImageId] = metadataProvider.get("instance", referenceImageId);
|
|
103
|
+
labelMapImage = imageLoader.createAndCacheDerivedLabelmapImage(referenceImageId);
|
|
104
|
+
labelMapImages.push(labelMapImage);
|
|
105
|
+
}
|
|
106
|
+
segmentsPixelIndices = new Map();
|
|
107
|
+
_context.next = 49;
|
|
108
|
+
return insertFunction(segmentsOnFrame, labelMapImages, pixelDataChunks, multiframe, referencedImageIds, validOrientations, metadataProvider, tolerance, segmentsPixelIndices, sopUIDImageIdIndexMap, imageIdMaps);
|
|
109
|
+
case 49:
|
|
110
|
+
overlappingSegments = _context.sent;
|
|
111
|
+
centroidXYZ = new Map();
|
|
112
|
+
segmentsPixelIndices.forEach(function (imageIdIndexBufferIndex, segmentIndex) {
|
|
113
|
+
var centroids = calculateCentroid(imageIdIndexBufferIndex, multiframe, metadataProvider, referencedImageIds);
|
|
114
|
+
centroidXYZ.set(segmentIndex, centroids);
|
|
115
|
+
});
|
|
116
|
+
return _context.abrupt("return", {
|
|
117
|
+
labelMapImages: [labelMapImages],
|
|
118
|
+
segMetadata: segMetadata,
|
|
119
|
+
segmentsOnFrame: segmentsOnFrame,
|
|
120
|
+
segmentsOnFrameArray: segmentsOnFrameArray,
|
|
121
|
+
centroids: centroidXYZ,
|
|
122
|
+
overlappingSegments: overlappingSegments
|
|
123
|
+
});
|
|
124
|
+
case 53:
|
|
125
|
+
case "end":
|
|
126
|
+
return _context.stop();
|
|
127
|
+
}
|
|
128
|
+
}, _callee);
|
|
129
|
+
}));
|
|
130
|
+
return _createLabelmapsFromBufferInternal.apply(this, arguments);
|
|
131
|
+
}
|
|
132
|
+
function insertPixelDataPlanar(segmentsOnFrame, labelMapImages, pixelData, multiframe, imageIds, validOrientations, metadataProvider, tolerance, segmentsPixelIndices, sopUIDImageIdIndexMap, imageIdMaps) {
|
|
133
|
+
var SharedFunctionalGroupsSequence = multiframe.SharedFunctionalGroupsSequence,
|
|
134
|
+
PerFrameFunctionalGroupsSequence = multiframe.PerFrameFunctionalGroupsSequence,
|
|
135
|
+
Rows = multiframe.Rows,
|
|
136
|
+
Columns = multiframe.Columns;
|
|
137
|
+
var sharedImageOrientationPatient = SharedFunctionalGroupsSequence.PlaneOrientationSequence ? SharedFunctionalGroupsSequence.PlaneOrientationSequence.ImageOrientationPatient : undefined;
|
|
138
|
+
var sliceLength = Columns * Rows;
|
|
139
|
+
var groupsLen = PerFrameFunctionalGroupsSequence.length;
|
|
140
|
+
var overlapping = false;
|
|
141
|
+
return new Promise(function (resolve) {
|
|
142
|
+
for (var i = 0; i < groupsLen; ++i) {
|
|
143
|
+
var PerFrameFunctionalGroups = PerFrameFunctionalGroupsSequence[i];
|
|
144
|
+
var ImageOrientationPatientI = sharedImageOrientationPatient || PerFrameFunctionalGroups.PlaneOrientationSequence.ImageOrientationPatient;
|
|
145
|
+
var view = readFromUnpackedChunks(pixelData, i * sliceLength, sliceLength);
|
|
146
|
+
var pixelDataI2D = ndarray(view, [Rows, Columns]);
|
|
147
|
+
var alignedPixelDataI = alignPixelDataWithSourceData(pixelDataI2D, ImageOrientationPatientI, validOrientations, tolerance);
|
|
148
|
+
if (!alignedPixelDataI) {
|
|
149
|
+
throw new Error("Individual SEG frames are out of plane with respect to the first SEG frame. " + "This is not yet supported. Aborting segmentation loading.");
|
|
150
|
+
}
|
|
151
|
+
var segmentIndex = getSegmentIndex(multiframe, i);
|
|
152
|
+
if (segmentIndex === undefined) {
|
|
153
|
+
throw new Error("Could not retrieve the segment index. Aborting segmentation loading.");
|
|
154
|
+
}
|
|
155
|
+
if (!segmentsPixelIndices.has(segmentIndex)) {
|
|
156
|
+
segmentsPixelIndices.set(segmentIndex, {});
|
|
157
|
+
}
|
|
158
|
+
var imageId = findReferenceSourceImageId(multiframe, i, imageIds, metadataProvider, tolerance, sopUIDImageIdIndexMap);
|
|
159
|
+
if (!imageId) {
|
|
160
|
+
console.warn("Image not present in stack, can't import frame : " + i + ".");
|
|
161
|
+
continue;
|
|
162
|
+
}
|
|
163
|
+
var sourceImageMetadata = imageIdMaps.metadata[imageId];
|
|
164
|
+
if (Rows !== sourceImageMetadata.Rows || Columns !== sourceImageMetadata.Columns) {
|
|
165
|
+
throw new Error("Individual SEG frames have different geometry dimensions (Rows and Columns) " + "respect to the source image reference frame. This is not yet supported. " + "Aborting segmentation loading. ");
|
|
166
|
+
}
|
|
167
|
+
var imageIdIndex = imageIdMaps.indices[imageId];
|
|
168
|
+
var labelmapImage = labelMapImages[imageIdIndex];
|
|
169
|
+
var labelmap2DView = labelmapImage.getPixelData();
|
|
170
|
+
var data = alignedPixelDataI.data;
|
|
171
|
+
var indexCache = [];
|
|
172
|
+
for (var j = 0, len = alignedPixelDataI.data.length; j < len; ++j) {
|
|
173
|
+
if (data[j]) {
|
|
174
|
+
for (var x = j; x < len; ++x) {
|
|
175
|
+
if (data[x]) {
|
|
176
|
+
if (!overlapping && labelmap2DView[x] !== 0) {
|
|
177
|
+
overlapping = true;
|
|
178
|
+
}
|
|
179
|
+
labelmap2DView[x] = segmentIndex;
|
|
180
|
+
indexCache.push(x);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
if (!segmentsOnFrame[imageIdIndex]) {
|
|
184
|
+
segmentsOnFrame[imageIdIndex] = [];
|
|
185
|
+
}
|
|
186
|
+
segmentsOnFrame[imageIdIndex].push(segmentIndex);
|
|
187
|
+
break;
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
var segmentIndexObject = segmentsPixelIndices.get(segmentIndex);
|
|
191
|
+
segmentIndexObject[imageIdIndex] = indexCache;
|
|
192
|
+
segmentsPixelIndices.set(segmentIndex, segmentIndexObject);
|
|
193
|
+
}
|
|
194
|
+
resolve(overlapping);
|
|
195
|
+
});
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
export { createLabelmapsFromBufferInternal, insertPixelDataPlanar };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cornerstonejs/adapters",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.12.1",
|
|
4
4
|
"description": "Adapters for Cornerstone3D to/from formats including DICOM SR and others",
|
|
5
5
|
"module": "./dist/esm/index.js",
|
|
6
6
|
"types": "./dist/esm/index.d.ts",
|
|
@@ -84,8 +84,8 @@
|
|
|
84
84
|
"ndarray": "^1.0.19"
|
|
85
85
|
},
|
|
86
86
|
"peerDependencies": {
|
|
87
|
-
"@cornerstonejs/core": "^2.
|
|
88
|
-
"@cornerstonejs/tools": "^2.
|
|
87
|
+
"@cornerstonejs/core": "^2.12.1",
|
|
88
|
+
"@cornerstonejs/tools": "^2.12.1"
|
|
89
89
|
},
|
|
90
|
-
"gitHead": "
|
|
90
|
+
"gitHead": "0bb31a1b9c61111d2d94c100d8b5d4c699182c42"
|
|
91
91
|
}
|