@cornerstonejs/tools 4.15.4 → 4.15.6

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.
@@ -42,6 +42,9 @@ function setActiveSegmentIndex(segmentationId, segmentIndex) {
42
42
  });
43
43
  viewportIds.forEach((viewportId) => {
44
44
  const toolGroup = getToolGroupForViewport(viewportId);
45
+ if (!toolGroup) {
46
+ return;
47
+ }
45
48
  invalidateBrushCursor(toolGroup.id);
46
49
  });
47
50
  }
@@ -331,7 +331,6 @@ class CircleROITool extends AnnotationTool {
331
331
  if (!annotations?.length) {
332
332
  return renderStatus;
333
333
  }
334
- const targetId = this.getTargetId(viewport);
335
334
  const renderingEngine = viewport.getRenderingEngine();
336
335
  const styleSpecifier = {
337
336
  toolGroupId: this.toolGroupId,
@@ -343,6 +342,7 @@ class CircleROITool extends AnnotationTool {
343
342
  const { annotationUID, data } = annotation;
344
343
  const { handles } = data;
345
344
  const { points, activeHandleIndex } = handles;
345
+ const targetId = this.getTargetId(viewport, data);
346
346
  styleSpecifier.annotationUID = annotationUID;
347
347
  const { color, lineWidth, lineDash } = this.getAnnotationStyle({
348
348
  annotation,
@@ -291,7 +291,6 @@ class CobbAngleTool extends AnnotationTool {
291
291
  if (!annotations?.length) {
292
292
  return renderStatus;
293
293
  }
294
- const targetId = this.getTargetId(viewport);
295
294
  const renderingEngine = viewport.getRenderingEngine();
296
295
  const styleSpecifier = {
297
296
  toolGroupId: this.toolGroupId,
@@ -302,6 +301,7 @@ class CobbAngleTool extends AnnotationTool {
302
301
  const annotation = annotations[i];
303
302
  const { annotationUID, data } = annotation;
304
303
  const { points, activeHandleIndex } = data.handles;
304
+ const targetId = this.getTargetId(viewport, data);
305
305
  styleSpecifier.annotationUID = annotationUID;
306
306
  const { color, lineWidth, lineDash } = this.getAnnotationStyle({
307
307
  annotation,
@@ -67,7 +67,6 @@ class DragProbeTool extends ProbeTool {
67
67
  if (!annotations?.length) {
68
68
  return renderStatus;
69
69
  }
70
- const targetId = this.getTargetId(viewport);
71
70
  const renderingEngine = viewport.getRenderingEngine();
72
71
  const styleSpecifier = {
73
72
  toolGroupId: this.toolGroupId,
@@ -79,6 +78,7 @@ class DragProbeTool extends ProbeTool {
79
78
  const data = annotation.data;
80
79
  const point = data.handles.points[0];
81
80
  const canvasCoordinates = viewport.worldToCanvas(point);
81
+ const targetId = this.getTargetId(viewport, data);
82
82
  styleSpecifier.annotationUID = annotationUID;
83
83
  const { color } = this.getAnnotationStyle({
84
84
  annotation,
@@ -380,7 +380,6 @@ class EllipticalROITool extends AnnotationTool {
380
380
  if (!annotations?.length) {
381
381
  return renderStatus;
382
382
  }
383
- const targetId = this.getTargetId(viewport);
384
383
  const renderingEngine = viewport.getRenderingEngine();
385
384
  const styleSpecifier = {
386
385
  toolGroupId: this.toolGroupId,
@@ -392,6 +391,7 @@ class EllipticalROITool extends AnnotationTool {
392
391
  const { annotationUID, data } = annotation;
393
392
  const { handles } = data;
394
393
  const { points, activeHandleIndex } = handles;
394
+ const targetId = this.getTargetId(viewport, data);
395
395
  styleSpecifier.annotationUID = annotationUID;
396
396
  const { color, lineWidth, lineDash } = this.getAnnotationStyle({
397
397
  annotation,
@@ -206,7 +206,7 @@ class PlanarFreehandROITool extends ContourSegmentationBaseTool {
206
206
  };
207
207
  this._renderStats = (annotation, viewport, enabledElement, svgDrawingHelper) => {
208
208
  const { data } = annotation;
209
- const targetId = this.getTargetId(viewport);
209
+ const targetId = this.getTargetId(viewport, data);
210
210
  const styleSpecifier = {
211
211
  toolGroupId: this.toolGroupId,
212
212
  toolName: this.getToolName(),
@@ -141,7 +141,6 @@ class ProbeTool extends AnnotationTool {
141
141
  if (!annotations?.length) {
142
142
  return renderStatus;
143
143
  }
144
- const targetId = this.getTargetId(viewport);
145
144
  const renderingEngine = viewport.getRenderingEngine();
146
145
  const styleSpecifier = {
147
146
  toolGroupId: this.toolGroupId,
@@ -154,6 +153,7 @@ class ProbeTool extends AnnotationTool {
154
153
  const data = annotation.data;
155
154
  const point = data.handles.points[0];
156
155
  const canvasCoordinates = viewport.worldToCanvas(point);
156
+ const targetId = this.getTargetId(viewport, data);
157
157
  styleSpecifier.annotationUID = annotationUID;
158
158
  const { color, lineWidth } = this.getAnnotationStyle({
159
159
  annotation,
@@ -317,7 +317,6 @@ class RectangleROITool extends AnnotationTool {
317
317
  if (!annotations?.length) {
318
318
  return renderStatus;
319
319
  }
320
- const targetId = this.getTargetId(viewport);
321
320
  const renderingEngine = viewport.getRenderingEngine();
322
321
  const styleSpecifier = {
323
322
  toolGroupId: this.toolGroupId,
@@ -329,6 +328,7 @@ class RectangleROITool extends AnnotationTool {
329
328
  const { annotationUID, data } = annotation;
330
329
  const { points, activeHandleIndex } = data.handles;
331
330
  const canvasCoordinates = points.map((p) => viewport.worldToCanvas(p));
331
+ const targetId = this.getTargetId(viewport, data);
332
332
  styleSpecifier.annotationUID = annotationUID;
333
333
  const { color, lineWidth, lineDash } = this.getAnnotationStyle({
334
334
  annotation,
@@ -2,12 +2,13 @@ import { utilities as csUtils } from '@cornerstonejs/core';
2
2
  import type { Types } from '@cornerstonejs/core';
3
3
  import ToolModes from '../../enums/ToolModes';
4
4
  import type StrategyCallbacks from '../../enums/StrategyCallbacks';
5
- import type { InteractionTypes, ToolProps, PublicToolProps } from '../../types';
5
+ import type { InteractionTypes, ToolProps, PublicToolProps, ToolConfiguration } from '../../types';
6
6
  declare abstract class BaseTool {
7
7
  static toolName: any;
8
8
  static activeCursorTool: any;
9
9
  supportedInteractionTypes: InteractionTypes[];
10
10
  configuration: Record<string, any>;
11
+ get configurationTyped(): ToolConfiguration;
11
12
  toolGroupId: string;
12
13
  mode: ToolModes;
13
14
  isPrimary: boolean;
@@ -22,6 +23,9 @@ declare abstract class BaseTool {
22
23
  };
23
24
  constructor(toolProps: PublicToolProps, defaultToolProps: ToolProps);
24
25
  static mergeDefaultProps(defaultProps?: {}, additionalProps?: any): any;
26
+ static isSpecifiedTargetId(desiredVolumeId: string): (_viewport: any, { targetId }: {
27
+ targetId: any;
28
+ }) => any;
25
29
  get toolName(): string;
26
30
  getToolName(): string;
27
31
  applyActiveStrategy(enabledElement: Types.IEnabledElement, operationData: unknown): any;
@@ -29,7 +33,9 @@ declare abstract class BaseTool {
29
33
  setConfiguration(newConfiguration: Record<string, any>): void;
30
34
  setActiveStrategy(strategyName: string): void;
31
35
  protected getTargetImageData(targetId: string): Types.IImageData | Types.CPUIImageData;
32
- protected getTargetId(viewport: Types.IViewport): string | undefined;
36
+ protected getTargetId(viewport: Types.IViewport, data?: unknown & {
37
+ cachedStats?: Record<string, unknown>;
38
+ }): string | undefined;
33
39
  undo(): void;
34
40
  redo(): void;
35
41
  static createZoomPanMemo(viewport: any): {
@@ -2,6 +2,9 @@ import { utilities as csUtils } from '@cornerstonejs/core';
2
2
  import ToolModes from '../../enums/ToolModes';
3
3
  const { DefaultHistoryMemo } = csUtils.HistoryMemo;
4
4
  class BaseTool {
5
+ get configurationTyped() {
6
+ return this.configuration;
7
+ }
5
8
  static { this.defaults = {
6
9
  configuration: {
7
10
  strategies: {},
@@ -26,6 +29,11 @@ class BaseTool {
26
29
  }
27
30
  return csUtils.deepMerge(defaultProps, additionalProps);
28
31
  }
32
+ static isSpecifiedTargetId(desiredVolumeId) {
33
+ return (_viewport, { targetId }) => {
34
+ return targetId.includes(desiredVolumeId);
35
+ };
36
+ }
29
37
  get toolName() {
30
38
  return this.getToolName();
31
39
  }
@@ -85,10 +93,18 @@ class BaseTool {
85
93
  throw new Error('getTargetIdImage: targetId must start with "imageId:" or "volumeId:"');
86
94
  }
87
95
  }
88
- getTargetId(viewport) {
89
- const targetId = viewport.getViewReferenceId?.();
90
- if (targetId) {
91
- return targetId;
96
+ getTargetId(viewport, data) {
97
+ const { isPreferredTargetId } = this.configurationTyped;
98
+ if (isPreferredTargetId && data?.cachedStats) {
99
+ for (const [targetId, cachedStat] of Object.entries(data.cachedStats)) {
100
+ if (isPreferredTargetId(viewport, { targetId, cachedStat })) {
101
+ return targetId;
102
+ }
103
+ }
104
+ }
105
+ const defaultTargetId = viewport.getViewReferenceId?.();
106
+ if (defaultTargetId) {
107
+ return defaultTargetId;
92
108
  }
93
109
  throw new Error('getTargetId: viewport must have a getViewReferenceId method');
94
110
  }
@@ -92,10 +92,12 @@ class ContourSegmentationBaseTool extends ContourBaseTool {
92
92
  const { segmentationId } = (annotation).data.segmentation;
93
93
  triggerSegmentationDataModified(segmentationId);
94
94
  const viewportIds = getViewportIdsWithSegmentation(segmentationId);
95
- const toolGroupIds = viewportIds.map((viewportId) => {
95
+ const toolGroupIds = viewportIds
96
+ .map((viewportId) => {
96
97
  const toolGroup = getToolGroupForViewport(viewportId);
97
- return toolGroup.id;
98
- });
98
+ return toolGroup?.id;
99
+ })
100
+ .filter((toolGroupId) => toolGroupId != null);
99
101
  triggerAnnotationRenderForToolGroupIds(toolGroupIds);
100
102
  }
101
103
  return renderResult;
@@ -54,16 +54,16 @@ export default class BrushStrategy {
54
54
  return initializedData;
55
55
  };
56
56
  this.configurationName = name;
57
- const cursorGeometryInitializer = initializers.find(init => init.hasOwnProperty(StrategyCallbacks.CalculateCursorGeometry));
58
- const renderCursorInitializer = initializers.find(init => init.hasOwnProperty(StrategyCallbacks.RenderCursor));
57
+ const cursorGeometryInitializer = initializers.find((init) => init.hasOwnProperty(StrategyCallbacks.CalculateCursorGeometry));
58
+ const renderCursorInitializer = initializers.find((init) => init.hasOwnProperty(StrategyCallbacks.RenderCursor));
59
59
  if (!cursorGeometryInitializer) {
60
60
  initializers.push({
61
- [StrategyCallbacks.CalculateCursorGeometry]: compositions.circularCursor.calculateCursorGeometry
61
+ [StrategyCallbacks.CalculateCursorGeometry]: compositions.circularCursor.calculateCursorGeometry,
62
62
  });
63
63
  }
64
64
  if (!renderCursorInitializer) {
65
65
  initializers.push({
66
- [StrategyCallbacks.RenderCursor]: compositions.circularCursor.renderCursor
66
+ [StrategyCallbacks.RenderCursor]: compositions.circularCursor.renderCursor,
67
67
  });
68
68
  }
69
69
  this.compositions = initializers;
@@ -89,7 +89,10 @@ export default class BrushStrategy {
89
89
  initialize(enabledElement, operationData, operationName) {
90
90
  const { viewport } = enabledElement;
91
91
  const data = getStrategyData({ operationData, viewport, strategy: this });
92
- if (!data) {
92
+ if (!data ||
93
+ !data.imageVoxelManager ||
94
+ !data.segmentationVoxelManager ||
95
+ !data.segmentationImageData) {
93
96
  return null;
94
97
  }
95
98
  const { imageVoxelManager, segmentationVoxelManager, segmentationImageData, } = data;
@@ -1,2 +1,12 @@
1
1
  import type BaseTool from '../tools/base/BaseTool';
2
+ export interface ToolConfiguration {
3
+ strategies: any;
4
+ defaultStrategy?: string;
5
+ activeStrategy?: string;
6
+ strategyOptions: any;
7
+ isPreferredTargetId?: (viewport: any, targetInfo: {
8
+ imageId: string;
9
+ cachedStat: any;
10
+ }) => boolean;
11
+ }
2
12
  export type IBaseTool = BaseTool;
@@ -2,6 +2,9 @@ import { cache, volumeLoader, utilities, ImageVolume, } from '@cornerstonejs/cor
2
2
  import { getSegmentation } from '../../stateManagement/segmentation/getSegmentation';
3
3
  function getOrCreateSegmentationVolume(segmentationId) {
4
4
  const { representationData } = getSegmentation(segmentationId);
5
+ if (!representationData.Labelmap) {
6
+ return;
7
+ }
5
8
  let { volumeId } = representationData.Labelmap;
6
9
  let segVolume;
7
10
  if (volumeId) {
@@ -1 +1 @@
1
- export declare const version = "4.15.4";
1
+ export declare const version = "4.15.6";
@@ -1 +1 @@
1
- export const version = '4.15.4';
1
+ export const version = '4.15.6';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cornerstonejs/tools",
3
- "version": "4.15.4",
3
+ "version": "4.15.6",
4
4
  "description": "Cornerstone3D Tools",
5
5
  "types": "./dist/esm/index.d.ts",
6
6
  "module": "./dist/esm/index.js",
@@ -108,7 +108,7 @@
108
108
  "canvas": "3.2.0"
109
109
  },
110
110
  "peerDependencies": {
111
- "@cornerstonejs/core": "4.15.4",
111
+ "@cornerstonejs/core": "4.15.6",
112
112
  "@kitware/vtk.js": "34.15.1",
113
113
  "@types/d3-array": "3.2.1",
114
114
  "@types/d3-interpolate": "3.0.4",
@@ -127,5 +127,5 @@
127
127
  "type": "individual",
128
128
  "url": "https://ohif.org/donate"
129
129
  },
130
- "gitHead": "1aea9ba6a06fab190274cbe46ea709031f78af13"
130
+ "gitHead": "91ce6d8dbb2cc3e2c6afe10510a5e04ad5c6ebc3"
131
131
  }