@@ -2994,11 +2994,6 @@ class VolumeImageViewer {
29942994 color : this [ _options ] . primaryColor
29952995 }
29962996
2997- // We need to bind those variables to constants for the loader function
2998- const client = this [ _options ] . client
2999- const pyramid = this [ _pyramid ] . metadata
3000- const affineInverse = this [ _affineInverse ]
3001- const container = this [ _map ] . getTargetElement ( )
30022997 const _getROIFromFeature = ( feature ) => {
30032998 const roi = this . _getROIFromFeature (
30042999 feature ,
@@ -3009,92 +3004,109 @@ class VolumeImageViewer {
30093004 const annotationGroupMetadata = metadata . AnnotationGroupSequence . find (
30103005 item => item . AnnotationGroupUID === annotationGroupUID
30113006 )
3007+ if ( annotationGroupUID == null || annotationGroupMetadata == null ) {
3008+ throw new Error (
3009+ 'Could not obtain information of annotation from ' +
3010+ `annotation group "${ annotationGroupUID } ".`
3011+ )
3012+ }
30123013
3013- const findingCategory = (
3014- annotationGroupMetadata
3015- . AnnotationPropertyCategoryCodeSequence [ 0 ]
3016- )
3017- roi . addEvaluation (
3018- new dcmjs . sr . valueTypes . CodeContentItem ( {
3019- name : new dcmjs . sr . coding . CodedConcept ( {
3020- value : '276214006' ,
3021- meaning : 'Finding category' ,
3022- schemeDesignator : 'SCT'
3023- } ) ,
3024- value : new dcmjs . sr . coding . CodedConcept ( {
3025- value : findingCategory . CodeValue ,
3026- meaning : findingCategory . CodeMeaning ,
3027- schemeDesignator : findingCategory . CodingSchemeDesignator
3028- } ) ,
3029- relationshipType : dcmjs . sr . valueTypes . RelationshipTypes . HAS_CONCEPT_MOD
3030- } )
3031- )
3032- const findingType = (
3033- annotationGroupMetadata
3034- . AnnotationPropertyTypeCodeSequence [ 0 ]
3035- )
3036- roi . addEvaluation (
3037- new dcmjs . sr . valueTypes . CodeContentItem ( {
3038- name : new dcmjs . sr . coding . CodedConcept ( {
3039- value : '121071' ,
3040- meaning : 'Finding' ,
3041- schemeDesignator : 'DCM'
3042- } ) ,
3043- value : new dcmjs . sr . coding . CodedConcept ( {
3044- value : findingType . CodeValue ,
3045- meaning : findingType . CodeMeaning ,
3046- schemeDesignator : findingType . CodingSchemeDesignator
3047- } ) ,
3048- relationshipType : dcmjs . sr . valueTypes . RelationshipTypes . HAS_CONCEPT_MOD
3049- } )
3050- )
3051-
3052- annotationGroupMetadata . MeasurementsSequence . forEach (
3053- ( measurementItem , measurementIndex ) => {
3054- const key = `measurementValue${ measurementIndex . toString ( ) } `
3055- const value = feature . get ( key )
3056- const name = measurementItem . ConceptNameCodeSequence [ 0 ]
3057- const unit = measurementItem . MeasurementUnitsCodeSequence [ 0 ]
3058-
3059- const measurement = new dcmjs . sr . valueTypes . NumContentItem ( {
3060- value : Number ( value ) ,
3014+ if ( annotationGroupMetadata . AnnotationPropertyCategoryCodeSequence != null ) {
3015+ const findingCategory = (
3016+ annotationGroupMetadata . AnnotationPropertyCategoryCodeSequence [ 0 ]
3017+ )
3018+ roi . addEvaluation (
3019+ new dcmjs . sr . valueTypes . CodeContentItem ( {
30613020 name : new dcmjs . sr . coding . CodedConcept ( {
3062- value : name . CodeValue ,
3063- meaning : name . CodeMeaning ,
3064- schemeDesignator : name . CodingSchemeDesignator
3021+ value : '276214006' ,
3022+ meaning : 'Finding category' ,
3023+ schemeDesignator : 'SCT'
30653024 } ) ,
3066- unit : new dcmjs . sr . coding . CodedConcept ( {
3067- value : unit . CodeValue ,
3068- meaning : unit . CodeMeaning ,
3069- schemeDesignator : unit . CodingSchemeDesignator
3025+ value : new dcmjs . sr . coding . CodedConcept ( {
3026+ value : findingCategory . CodeValue ,
3027+ meaning : findingCategory . CodeMeaning ,
3028+ schemeDesignator : findingCategory . CodingSchemeDesignator
30703029 } ) ,
3071- relationshipType : dcmjs . sr . valueTypes . RelationshipTypes . CONTAINS
3030+ relationshipType :
3031+ dcmjs . sr . valueTypes . RelationshipTypes . HAS_CONCEPT_MOD
30723032 } )
3073- if ( measurementItem . ReferencedImageSequence != null ) {
3074- const ref = measurementItem . ReferencedImageSequence [ 0 ]
3075- const image = new dcmjs . sr . valueTypes . ImageContentItem ( {
3033+ )
3034+ }
3035+ if ( annotationGroupMetadata . AnnotationPropertyTypeCodeSequence != null ) {
3036+ const findingType = (
3037+ annotationGroupMetadata . AnnotationPropertyTypeCodeSequence [ 0 ]
3038+ )
3039+ roi . addEvaluation (
3040+ new dcmjs . sr . valueTypes . CodeContentItem ( {
3041+ name : new dcmjs . sr . coding . CodedConcept ( {
3042+ value : '121071' ,
3043+ meaning : 'Finding' ,
3044+ schemeDesignator : 'DCM'
3045+ } ) ,
3046+ value : new dcmjs . sr . coding . CodedConcept ( {
3047+ value : findingType . CodeValue ,
3048+ meaning : findingType . CodeMeaning ,
3049+ schemeDesignator : findingType . CodingSchemeDesignator
3050+ } ) ,
3051+ relationshipType :
3052+ dcmjs . sr . valueTypes . RelationshipTypes . HAS_CONCEPT_MOD
3053+ } )
3054+ )
3055+ }
3056+
3057+ if ( annotationGroupMetadata . MeasurementsSequence != null ) {
3058+ annotationGroupMetadata . MeasurementsSequence . forEach (
3059+ ( measurementItem , measurementIndex ) => {
3060+ const key = `measurementValue${ measurementIndex . toString ( ) } `
3061+ const value = feature . get ( key )
3062+ const name = measurementItem . ConceptNameCodeSequence [ 0 ]
3063+ const unit = measurementItem . MeasurementUnitsCodeSequence [ 0 ]
3064+
3065+ const measurement = new dcmjs . sr . valueTypes . NumContentItem ( {
3066+ value : Number ( value ) ,
30763067 name : new dcmjs . sr . coding . CodedConcept ( {
3077- value : '121112' ,
3078- meaning : 'Source of Measurement' ,
3079- schemeDesignator : 'DCM'
3068+ value : name . CodeValue ,
3069+ meaning : name . CodeMeaning ,
3070+ schemeDesignator : name . CodingSchemeDesignator
30803071 } ) ,
3081- referencedSOPClassUID : ref . ReferencedSOPClassUID ,
3082- referencedSOPInstanceUID : ref . ReferencedSOPInstanceUID
3072+ unit : new dcmjs . sr . coding . CodedConcept ( {
3073+ value : unit . CodeValue ,
3074+ meaning : unit . CodeMeaning ,
3075+ schemeDesignator : unit . CodingSchemeDesignator
3076+ } ) ,
3077+ relationshipType : dcmjs . sr . valueTypes . RelationshipTypes . CONTAINS
30833078 } )
3084- if ( ref . ReferencedOpticalPathIdentifier != null ) {
3085- image . ReferencedSOPSequence [ 0 ] . ReferencedOpticalPathIdentifier = (
3086- ref . ReferencedOpticalPathIdentifier
3087- )
3079+ if ( measurementItem . ReferencedImageSequence != null ) {
3080+ const ref = measurementItem . ReferencedImageSequence [ 0 ]
3081+ const image = new dcmjs . sr . valueTypes . ImageContentItem ( {
3082+ name : new dcmjs . sr . coding . CodedConcept ( {
3083+ value : '121112' ,
3084+ meaning : 'Source of Measurement' ,
3085+ schemeDesignator : 'DCM'
3086+ } ) ,
3087+ referencedSOPClassUID : ref . ReferencedSOPClassUID ,
3088+ referencedSOPInstanceUID : ref . ReferencedSOPInstanceUID
3089+ } )
3090+ if ( ref . ReferencedOpticalPathIdentifier != null ) {
3091+ image . ReferencedSOPSequence [ 0 ] . ReferencedOpticalPathIdentifier = (
3092+ ref . ReferencedOpticalPathIdentifier
3093+ )
3094+ }
3095+ measurement . ContentSequence = [ image ]
30883096 }
3089- measurement . ContentSequence = [ image ]
3097+ roi . addMeasurement ( measurement )
30903098 }
3091- roi . addMeasurement ( measurement )
3092- }
3093- )
3099+ )
3100+ }
30943101
30953102 return roi
30963103 }
30973104
3105+ // We need to bind those variables to constants for the loader function
3106+ const client = this [ _options ] . client
3107+ const pyramid = this [ _pyramid ] . metadata
3108+ const affineInverse = this [ _affineInverse ]
3109+
30983110 metadata . AnnotationGroupSequence . forEach ( ( item , index ) => {
30993111 const annotationGroupUID = item . AnnotationGroupUID
31003112 const algorithm = item . AnnotationGroupAlgorithmIdentificationSequence [ 0 ]
@@ -3291,28 +3303,33 @@ class VolumeImageViewer {
32913303
32923304 let selectedAnnotation = null
32933305 this [ _map ] . on ( 'singleclick' , ( e ) => {
3294- if ( selectedAnnotation !== null ) {
3295- selectedAnnotation . set ( 'selected' , 0 )
3296- selectedAnnotation = null
3297- }
3298-
3299- this [ _map ] . forEachFeatureAtPixel (
3300- e . pixel ,
3301- ( feature ) => {
3302- feature . set ( 'selected' , 1 )
3303- selectedAnnotation = feature
3304- publish (
3305- container ,
3306- EVENT . ROI_SELECTED ,
3307- _getROIFromFeature ( feature )
3308- )
3309- return true
3310- } ,
3311- {
3312- hitTolerance : 1 ,
3313- layerFilter : ( layer ) => ( layer instanceof PointsLayer )
3306+ if ( e != null ) {
3307+ if ( selectedAnnotation != null ) {
3308+ selectedAnnotation . set ( 'selected' , 0 )
3309+ selectedAnnotation = null
33143310 }
3315- )
3311+ const container = this [ _map ] . getTargetElement ( )
3312+ this [ _map ] . forEachFeatureAtPixel (
3313+ e . pixel ,
3314+ ( feature ) => {
3315+ if ( feature != null ) {
3316+ feature . set ( 'selected' , 1 )
3317+ selectedAnnotation = feature
3318+ publish (
3319+ container ,
3320+ EVENT . ROI_SELECTED ,
3321+ _getROIFromFeature ( feature )
3322+ )
3323+ return true
3324+ }
3325+ return false
3326+ } ,
3327+ {
3328+ hitTolerance : 1 ,
3329+ layerFilter : ( layer ) => ( layer instanceof PointsLayer )
3330+ }
3331+ )
3332+ }
33163333 } )
33173334 }
33183335
@@ -3767,7 +3784,12 @@ class VolumeImageViewer {
37673784 colormap : segment . style . paletteColorLookupTable . data
37683785 } ) ,
37693786 useInterimTilesOnError : false ,
3770- cacheSize : this [ _options ] . tilesCacheSize
3787+ cacheSize : this [ _options ] . tilesCacheSize ,
3788+ minResolution : (
3789+ minZoomLevel > 0
3790+ ? this [ _pyramid ] . resolutions [ minZoomLevel ]
3791+ : undefined
3792+ )
37713793 } )
37723794 segment . layer . on ( 'error' , ( event ) => {
37733795 console . error ( `error rendering segment "${ segmentUID } "` , event )
0 commit comments