1
1
import readImageDICOMFileSeries from 'itk/readImageDICOMFileSeries'
2
- import PromiseFileReader from 'promise-file-reader'
3
2
import curry from 'curry'
4
- import dicomParser from 'dicom-parser'
5
3
6
4
import setupDicomForm from './dicomForm'
7
- import "regenerator-runtime/runtime" ;
8
-
9
- const DICOM_DICTIONARY = {
10
- patientId : 'x00100020' ,
11
- patientName : 'x00100010' ,
12
- patientDateOfBirth : 'x00100030' ,
13
- patientSex : 'x00100040' ,
14
- studyID : 'x00200010' ,
15
- studyUID : 'x0020000d' ,
16
- studyDate : 'x00080020' ,
17
- studyTime : 'x00080030' ,
18
- studyAccessionNumber : 'x00080050' ,
19
- studyDescription : 'x00081030' ,
20
- seriesNumber : 'x00200011' ,
21
- seriesUid : 'x0020000e' ,
22
- seriesDate : 'x00080021' ,
23
- seriesTime : 'x00080031' ,
24
- seriesModality : 'x00080060' ,
25
- seriesDescription : 'x0008103e' ,
26
- seriesProtocolName : 'x00181030' ,
27
- seriesBodyPart : 'x00180015' ,
28
- }
29
-
30
- const parseDICOMFiles = async ( fileList ) => {
31
- var patientDict = new Map ( )
32
-
33
- const parseFile = async ( file ) => {
34
- // Read
35
- const arrayBuffer = await PromiseFileReader . readAsArrayBuffer ( file )
36
-
37
- // Parse
38
- const byteArray = new Uint8Array ( arrayBuffer )
39
- const dicomMetaData = dicomParser . parseDicom ( byteArray )
40
-
41
- // Add to patientDict
42
- const tag = DICOMPatient . primaryTag
43
- const patientId = dicomMetaData . string ( DICOM_DICTIONARY [ tag ] )
44
- var patient = patientDict . get ( patientId )
45
- if ( patient === undefined ) {
46
- console . log ( `New patient ${ patientId } ` )
47
- patient = new DICOMPatient ( )
48
- patientDict . set ( patientId , patient )
49
- }
50
- patient . parseMetaData ( dicomMetaData , file )
51
- }
52
-
53
- // Parse all files and populate patientDict
54
- const parseFiles = [ ...fileList ] . map ( parseFile )
55
- await Promise . all ( parseFiles )
56
- return patientDict
57
- }
58
-
59
- class DICOMEntity {
60
- constructor ( ) {
61
- this . checkTagsValidity ( ) // could it be a static assertion instead?
62
- }
63
-
64
- checkTagsValidity ( ) {
65
- const tags = this . constructor . tags
66
- const primaryTag = this . constructor . primaryTag
67
- console . assert (
68
- tags . includes ( primaryTag ) ,
69
- `The primary tag ${ primaryTag } is not listed in ${ tags } `
70
- )
71
- tags . forEach ( ( tag ) => {
72
- console . assert (
73
- tag in DICOM_DICTIONARY ,
74
- `The tag ${ tag } is not defined in DICOM_DICTIONARY`
75
- )
76
- } )
77
- }
78
-
79
- extractTags ( dicomMetaData ) {
80
- const tags = this . constructor . tags
81
- const primaryTag = this . constructor . primaryTag
82
- tags . forEach ( ( tag ) => {
83
- const value = dicomMetaData . string ( DICOM_DICTIONARY [ tag ] )
84
- if ( this [ tag ] === undefined ) {
85
- this [ tag ] = value
86
- } else if ( value != undefined ) {
87
- console . assert ( this [ tag ] === value , `Inconsistent value for ${ tag } property of ${ this [ primaryTag ] } ` )
88
- }
89
- } )
90
- }
91
- }
92
-
93
- class DICOMPatient extends DICOMEntity {
94
- static get primaryTag ( ) {
95
- return 'patientId'
96
- }
97
-
98
- static get tags ( ) {
99
- return [
100
- 'patientId' ,
101
- 'patientName' ,
102
- 'patientDateOfBirth' ,
103
- 'patientSex' ,
104
- ]
105
- }
106
-
107
- constructor ( ) {
108
- super ( )
109
- this . studyDict = new Map ( )
110
- }
111
-
112
- parseMetaData ( dicomMetaData , file ) {
113
- this . extractTags ( dicomMetaData )
114
-
115
-
116
- const tag = DICOMStudy . primaryTag
117
- const studyId = dicomMetaData . string ( DICOM_DICTIONARY [ tag ] )
118
- var study = this . studyDict . get ( studyId )
119
- if ( study === undefined ) {
120
- console . log ( `new study ${ studyId } ` )
121
- study = new DICOMStudy ( )
122
- this . studyDict . set ( studyId , study )
123
- }
124
- study . parseMetaData ( dicomMetaData , file )
125
- }
126
- }
127
-
128
-
129
- class DICOMStudy extends DICOMEntity {
130
- static get primaryTag ( ) {
131
- return 'studyID'
132
- }
133
-
134
- static get tags ( ) {
135
- return [
136
- 'studyID' ,
137
- 'studyUID' ,
138
- 'studyDate' ,
139
- 'studyTime' ,
140
- 'studyAccessionNumber' ,
141
- 'studyDescription' ,
142
- ]
143
- }
144
-
145
- constructor ( ) {
146
- super ( )
147
- this . serieDict = new Map ( )
148
- }
149
-
150
- parseMetaData ( dicomMetaData , file ) {
151
- this . extractTags ( dicomMetaData )
152
-
153
- const tag = DICOMSerie . primaryTag
154
- const serieNumber = dicomMetaData . string ( DICOM_DICTIONARY [ tag ] )
155
- var serie = this . serieDict . get ( serieNumber )
156
- if ( serie === undefined ) {
157
- console . log ( `new serie ${ serieNumber } ` )
158
- serie = new DICOMSerie ( )
159
- this . serieDict . set ( serieNumber , serie )
160
- }
161
- serie . parseMetaData ( dicomMetaData , file )
162
- }
163
- }
164
-
165
- class DICOMSerie extends DICOMEntity {
166
- static get primaryTag ( ) {
167
- return 'seriesNumber'
168
- }
169
-
170
- static get tags ( ) {
171
- return [
172
- 'seriesNumber' ,
173
- 'seriesUid' ,
174
- 'seriesDate' ,
175
- 'seriesTime' ,
176
- 'seriesModality' ,
177
- 'seriesDescription' ,
178
- 'seriesProtocolName' ,
179
- 'seriesBodyPart' ,
180
- ]
181
- }
182
-
183
- constructor ( ) {
184
- super ( )
185
- this . files = [ ]
186
- }
187
-
188
- parseMetaData ( dicomMetaData , file ) {
189
- this . extractTags ( dicomMetaData )
190
-
191
- this . files . push ( file )
192
- }
193
- }
5
+ import parseDicomFiles from './parseDicomFiles'
194
6
195
7
const outputFileInformation = curry ( async function outputFileInformation ( outputTextArea , event ) {
196
8
outputTextArea . textContent = "Parsing..."
@@ -200,7 +12,7 @@ const outputFileInformation = curry(async function outputFileInformation (output
200
12
const files = event . target . files || dataTransfer . files
201
13
202
14
// Parse DICOM metadata
203
- const patientDict = await parseDICOMFiles ( files )
15
+ const patientDict = await parseDicomFiles ( files )
204
16
205
17
// Select DICOM serie
206
18
outputTextArea . textContent = "Please select serie..."
0 commit comments