def write_dicom(pixel_array, filename): file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {}, file_meta=file_meta, preamble="\0" * 128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename)
def write_dicom(pixel_array, index, filename): ## This code block was taken from the output of a MATLAB secondary ## capture. I do not know what the long dotted UIDs mean, but ## this code works. target_dir = '/'.join(filename.split('/')[:-1]) print(target_dir) mkdir_p(target_dir) file_meta = Dataset() ds = FileDataset(filename, {},file_meta = file_meta) ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.InstanceNumber = index #ds.PhotometricInterpretation = bytes("MONOCHROME2", "UTF-8") ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 #ds.SmallestImagePixelValue = bytes('\\x00\\x00', 'UTF-8') #ds.LargestImagePixelValue = bytes('\\xff\\xff', 'UTF-8') ds.Columns = pixel_array.shape[1] ds.Rows = pixel_array.shape[0] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename)
def WriteDCMFile(pixel_array,filename): file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'RT Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {},file_meta = file_meta,preamble="\0"*128) ds.Modality = 'RTIMAGE' ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'RT Image Storage' ds.SecondaryCaptureDeviceManufacturer = 'Varian Medical Systems' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.ImagePlanePixelSpacing=[0.392,0.392] ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 # ds.SmallestImagePixelValue = '\\x00\\x00' # ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns =1024# pixel_array.shape[0] ds.Rows =764# pixel_array.shape[1] ds.RescaleSlope=1.0 ds.RescaleIntercept=1.0 # if type(pixel_array) != np.uint16: # pixel_array =np.uint16(pixel_array) ds.PixelData = pixel_array ds.save_as(filename,write_like_original=True) return
def write_dicom(pixel_array, filename): file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684' file_meta.MediaStorageSOPInstanceUID += '411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {}, file_meta=file_meta, preamble=b"\0"*128) ds.Modality = 'MR' ds.ContentDate = str(date.today()).replace('-', '') ds.ContentTime = str(time()) ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.1243139774123601752342712' ds.StudyInstanceUID += '87472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421' ds.SeriesInstanceUID += '859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385' ds.SOPInstanceUID += '720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 3.3.5' # Options ds.InstitutionName = "Imperial College London" ds.RepetitionTime = 300 # These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.Columns = pixel_array.shape[1] ds.Rows = pixel_array.shape[0] ds.PixelData = pixel_array.tostring() ds.save_as(filename) return 0
def WriteDICOM_slice(self, pixel_array,filename, itemnumber=0, PhotometricInterpretation="MONOCHROME2"): from dicom.dataset import Dataset, FileDataset import numpy as np import datetime, time """ INPUTS: pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. filename: string name for the output file. """ ## This code block was taken from the output of a MATLAB secondary ## capture. I do not know what the long dotted UIDs mean, but ## this code works. file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {},file_meta = file_meta,preamble="\0"*128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 if PhotometricInterpretation=="MONOCHROME2": ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' elif PhotometricInterpretation=="RGB": ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' pixel_array = pixel_array[0] print pixel_array.shape ds.Columns = pixel_array.shape[0] ds.ItemNumber = str(itemnumber) ds.InstanceNumber = str(itemnumber) ds.SliceLocation = str(itemnumber) ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return filename
def saveDicomFile(filename, patientName, patientId, gender, birthday, imageArray, transpose=False): meta = Dataset() SOPClassUID = "1.2.840.10008.5.1.4.1.1.2" # sop class UID dla obrazow CT meta.MediaStorageSOPClassUID = SOPClassUID # Wygenerowany unikalny UID date = datetime.datetime.now().strftime('%Y%m%d') # Obecny czas time = datetime.datetime.now().strftime('%H%M%S.%f') # Obecny czas randomUId = SOPClassUID + "." + date + time # Wygenerowany unikalny UID meta.MediaStorageSOPInstanceUID = randomUId # Wygenerowany unikalny UID meta.ImplementationClassUID = randomUId + "." + "1" # Wygenerowany unikalny UID dataSet = FileDataset(filename, {}, file_meta=meta, preamble=b"\0" * 128) # Utworzenie obiektu DICOM dataSet.PatientName = patientName # Imie pacjenta dataSet.PatientID = patientId # Id pacjenta dataSet.PatientBirthDate = birthday # Data urodzenia pacjenta dataSet.PatientSex = gender # Plec pacjenta dataSet.is_little_endian = True dataSet.is_implicit_VR = True dataSet.ContentDate = date # Czas utworzenia pliku (YYYY:MM:DD) dataSet.StudyDate = date # Czas ostatniego otworzenia obrazu (YYYY-MM-DD) dataSet.StudyTime = time # Czas ostatniego otworzenia obrazu (HH:MM:SS) dataSet.ContentTime = time # Czas utworzenia pliku (HH:MM:SS) dataSet.StudyInstanceUID = randomUId + "." + "2" # Wygenerowany unikalny UID dataSet.SeriesInstanceUID = randomUId + "." + "3" # Wygenerowany unikalny UID dataSet.SOPInstanceUID = randomUId + "." + "4" # Wygenerowany unikalny UID dataSet.SOPClassUID = "CT." + date + time # Wygenerowany unikalny UID dataSet.SamplesPerPixel = 1 # Liczba kanałów. 1 - dla skali szarosci dataSet.PhotometricInterpretation = "MONOCHROME2" # MONOCHROE - obraz jest w skali szarości, 2 - maksymalna wartosc wskazuje kolor bialy dataSet.PixelRepresentation = 0 # 0 - wartosci sa tylko dodatnie (unsigned) 1 - wartosci sa tez ujemne dataSet.HighBit = 15 # Najważniejszy bit w pliku z obrazem dataSet.BitsStored = 16 # Liczba bitow na jedna wartosc w obrazie dataSet.BitsAllocated = 16 # Liczba bitow na jedna wartosc ktora jest zaalokowana dla obrazu dataSet.SmallestImagePixelValue = b'\\x00\\x00' # Wskazanie minimalnej wartosci dla kanalu dataSet.LargestImagePixelValue = b'\\xff\\xff' # Wskazanie maksymalnej wartosci dla kanalu dataSet.Rows = imageArray.shape[1] # Liczba wierszy dataSet.Columns = imageArray.shape[0] # Liczba kolumn if imageArray.dtype != np.uint16: # Sprawdzenie czy wartosci sa w przedziale [0,255] imageArray = skimage.img_as_uint( imageArray) # Zamiana na wartosci w przedziale [0,255] if transpose == True: # Zamiana wierszy i kolumn (opcjonalne) dataSet.Rows = imageArray.shape[0] dataSet.Columns = imageArray.shape[1] dataSet.PixelData = imageArray.tostring() # Zapisanie obrazu dataSet.save_as(filename) # Zapisanie pliku na dysku
def write_dicom(pixel_array, filename): """ INPUTS: pixel_array: 2D or 3D numpy ndarray. filename: string name for the output file. """ file_meta = Dataset() file_meta.MediaStorageSOPClassUID = '1.1' file_meta.MediaStorageSOPInstanceUID = '1.2' file_meta.ImplementationClassUID = '1.3' ds = FileDataset(filename, {}, file_meta=file_meta, preamble=b'\x00' * 128) ds.Modality = 'PET' # imaging modality name ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) # milliseconds since the epoch ds.StudyInstanceUID = '1.3' ds.SeriesInstanceUID = '1.3' ds.SOPInstanceUID = '1.3' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 3.7.5' # Patient-related data ds.PatientName = 'Wawrzyniec L. Dobrucki' ds.PatientID = 'M12345' ds.PatientSex = 'M' ds.PatientBirthDate = '12/12/12' ds.SeriesNumber = 5 ds.SeriesDescription = 'test image' ds.SliceThickness = '0.5' # slice thickness in mm ds.PixelSpacing = '0.5' # pixel spacing or size in mm # These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 # unsigned (default) ds.HighBit = 15 ds.BitsStored = 16 # default ds.BitsAllocated = 16 # default ds.NumberOfFrames = 216 # number of frames for 3D files # ds.SmallestImagePixelValue = '\\x00\\x00' # ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return
def writeDicom(pixel_array, filename): """ Source: https://codedump.io/share/qCDN4fOKcTAS/1/create-pydicom-file-from-numpy-array INPUTS: pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. filename: string name for the output file. """ ## This code block was taken from the output of a MATLAB secondary ## capture. I do not know what the long dotted UIDs mean, but ## this code works. file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {}, file_meta=file_meta, preamble=b'\x00' * 128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return
def write_dicom(pixel_array,filename): """ INPUTS: pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. filename: string name for the output file. """ ## Metadata is captured from Osirix file_meta = Dataset() file_meta.MediaStorageSOPClassUID = '1.2.840.10008.5.1.4.1.1.4' file_meta.MediaStorageSOPInstanceUID = '1.2.276.0.7230010.3.1.4.680961.1356.1477424584.260802' file_meta.ImplementationClassUID = '1.2.276.0.7230010.3.0.3.6.0' ds = FileDataset(filename, {},file_meta = file_meta,preamble="\0"*128) ds.Modality = 'MR' ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.2.840.113619.2.40.20410.4.1101731106.1478904046.976759' ds.SeriesInstanceUID = '1.2.840.113619.2.40.20410.4.1101731106.1478904045.846068' ds.SOPInstanceUID = '1.2.840.113619.2.40.20410.4.1101731106.1478904123.170427' ds.SOPClassUID = '1.2.840.10008.5.1.4.1.1.4' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ds.SliceThickness = 2.4 ds.SpacingBetweenSlices = 2.4 ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 1 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return
def write_dicom(pixel_array,index,filename): """ INPUTS: pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. filename: string name for the output file. """ ## This code block was taken from the output of a MATLAB secondary ## capture. I do not know what the long dotted UIDs mean, but ## this code works. file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.2.3.4.5.6.7.8.9.00'+str(index) file_meta.ImplementationClassUID = '1.2.3.4.5.6.7.8.9.0' ds = FileDataset(filename, {},file_meta = file_meta,preamble="\0"*128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.2.3.4.5.6.7.8.9' ds.SeriesInstanceUID = '1.2.3.4.5.6.7.8.9.00' ds.SOPInstanceUID = file_meta.MediaStorageSOPInstanceUID ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3 by Linkingmed' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return
def _write_numpy_2_dicom(pixel_array, dcmfilename): filename = dcmfilename[dcmfilename.index('-') + 1:dcmfilename.index('.mhd')] print(filename) for i in range(pixel_array.shape[0]): file_meta = Dataset() file_meta.MediaStorageSOPClassUID = '1.2.840.10008.5.1.4.1.1.2' # CT Image Storage file_meta.MediaStorageSOPInstanceUID = "1.2.3" # !! Need valid UID here for real work file_meta.ImplementationClassUID = "1.2.3.4" # !!! Need valid UIDs here ds = FileDataset(dcmfilename, {}, file_meta=file_meta, preamble="\0" * 128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) # milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' ds.Columns = pixel_array.shape[1] ds.Rows = pixel_array.shape[2] ds.PixelData = pixel_array[i].tostring() dcm = "{0}{1}-{2}.dcm".format(output_path, filename, i) print("dcm filename = %s,shape = %s" % (dcm, pixel_array[0].shape)) ds.save_as(dcm)
def process_mrs_ge(pfile_dir): # Make a top-level instance and hide in top left corner, get filepath # root = Tkinter.Tk() # root.geometry('0x0+0+0') # root.attributes("-topmost", 1) # pfile_dir = tkFileDialog.askdirectory(parent=root) # root.attributes("-topmost", 0) # root.destroy() print('Working...') root_dir = os.path.abspath(os.path.join(pfile_dir, os.pardir)) pat_name = os.path.split(os.path.dirname(pfile_dir))[1] filelist = glob.glob(pfile_dir + '/*.7') filelist.extend(glob.glob(pfile_dir + '/*.anon')) for fname in filelist: try: print('') print(fname) fbin = open(fname, 'rb') sw_ver = int( str(struct.unpack('f', fbin.read(4))[0]).split('.')[0]) print('software version: ' + str(sw_ver)) s = fbin.read() if s.find('PROBE-P') > 0: seqtype = 'PRESS' elif s.find('PROBE-S') > 0: seqtype = 'STEAM' else: print('WARNING: acquisition type not recognised!') if sw_ver < 26: fbin.seek(82) pt_sz = struct.unpack('<h', fbin.read(2))[0] fbin.seek(1468) hdr_sz = struct.unpack('<i', fbin.read(4))[0] if sw_ver == 15: fbin.seek(144580) # FOR REV 15 elif sw_ver == 16: fbin.seek(144628) # FOR REV 16 elif sw_ver > 19: fbin.seek(148404) # FOR REV 20 & 24 te = struct.unpack('<i', fbin.read(4))[0] if sw_ver == 15: fbin.seek(144572) # FOR REV 15 elif sw_ver == 16: fbin.seek(144620) # FOR REV 16 elif sw_ver > 19 and sw_ver < 26: fbin.seek(148396) # FOR REV 20 & 24 tr = struct.unpack('<i', fbin.read(4))[0] fbin.seek(148712) exam_no = struct.unpack('<i', fbin.read(4))[0] fbin.seek(148724) series_no = struct.unpack('<i', fbin.read(4))[0] fbin.seek(424) c_freq = struct.unpack('<i', fbin.read(4))[0] fbin.seek(200) st_rcv = struct.unpack('<h', fbin.read(2))[0] fbin.seek(202) en_rcv = struct.unpack('<h', fbin.read(2))[0] fbin.seek(70) nechoes = struct.unpack('<h', fbin.read(2))[0] fbin.seek(72) navs = struct.unpack('<h', fbin.read(2))[0] fbin.seek(74) nframes = struct.unpack('<h', fbin.read(2))[0] n_rcv = (en_rcv - st_rcv) + 1 # pfile=headers.Pfile.from_file(fname) # frm_sz=pfile.acq_x_res*2*pt_sz # echo_size=frm_sz*pfile.acq_y_Res # slice_size=echo_size*nechoes # data_sz=pfile.acq_x_res*2*(pfile.acq_y_Res-1) fbin.seek(102) acq_x_res = struct.unpack('<h', fbin.read(2))[0] fbin.seek(104) acq_y_Res = struct.unpack('<h', fbin.read(2))[0] fbin.seek(216) bandwidth = struct.unpack('<f', fbin.read(4))[0] # if sw_ver == 15: # fbin.seek(948) # FOR REV 15 # elif sw_ver == 16: # fbin.seek(948) # FOR REV 16 # elif sw_ver > 19: # fbin.seek(948) # FOR REV 20 & 24 fbin.seek(232) ws_nsa = struct.unpack('<f', fbin.read(4))[0] elif sw_ver == 26: fbin.seek(158) pt_sz = struct.unpack('<h', fbin.read(2))[0] fbin.seek(4) hdr_sz = struct.unpack('<i', fbin.read(4))[0] fbin.seek(199244) # FOR REV 26 te = struct.unpack('<i', fbin.read(4))[0] fbin.seek(199236) # FOR REV 26 tr = struct.unpack('<i', fbin.read(4))[0] fbin.seek(196428) exam_no = struct.unpack('<i', fbin.read(4))[0] fbin.seek(194068) series_no = struct.unpack('<i', fbin.read(4))[0] fbin.seek(504) c_freq = struct.unpack('<i', fbin.read(4))[0] fbin.seek(264) st_rcv = struct.unpack('<h', fbin.read(2))[0] fbin.seek(266) en_rcv = struct.unpack('<h', fbin.read(2))[0] fbin.seek(146) nechoes = struct.unpack('<h', fbin.read(2))[0] fbin.seek(148) navs = struct.unpack('<h', fbin.read(2))[0] fbin.seek(2520) nframes = struct.unpack('<h', fbin.read(2))[0] n_rcv = (en_rcv - st_rcv) + 1 # pfile=headers.Pfile.from_file(fname) # frm_sz=pfile.acq_x_res*2*pt_sz # echo_size=frm_sz*pfile.acq_y_Res # slice_size=echo_size*nechoes # data_sz=pfile.acq_x_res*2*(pfile.acq_y_Res-1) fbin.seek(156) acq_x_res = struct.unpack('<h', fbin.read(2))[0] fbin.seek(180) acq_y_Res = struct.unpack('<h', fbin.read(2))[0] fbin.seek(280) bandwidth = struct.unpack('<f', fbin.read(4))[0] fbin.seek(296) ws_nsa = struct.unpack('<f', fbin.read(4))[0] ws_avgs = int(ws_nsa) / int(navs) frm_sz = acq_x_res * 2 * pt_sz echo_size = frm_sz * acq_y_Res slice_size = echo_size * nechoes data_sz = acq_x_res * 2 * (acq_y_Res - 1) #off_raw is the offset in bytes to the start of the raw data off_raw = hdr_sz + frm_sz w_avgs = acq_y_Res - 1 - ws_avgs print('Number of water ref frames : ' + str(w_avgs)) print('Number of data frames : ' + str(ws_avgs)) fbin.seek(off_raw) raw_data = np.zeros(data_sz) frame_data = np.zeros(shape=(int(acq_y_Res - 1), int(acq_x_res), int(n_rcv)), dtype=np.int64) frame_data = frame_data.view(np.complex64) rot_frame_data = np.zeros(shape=(int(acq_y_Res - 1), int(acq_x_res), int(n_rcv)), dtype=np.float64) rot_frame_data = rot_frame_data.view(np.complex64) fid_norm = np.zeros(shape=(int(acq_y_Res - 1), int(acq_x_res), int(n_rcv)), dtype=np.float64) fid_norm = fid_norm.view(np.complex64) summed_signal = np.zeros(shape=(int(acq_y_Res - 1) * int(acq_x_res)), dtype=np.float64) summed_signal = summed_signal.view(np.complex64) for receiver in range(0, n_rcv): fbin.seek(off_raw + (slice_size * receiver)) for element in range(0, data_sz): raw_data[element] = struct.unpack('<i', fbin.read(4))[0] for frm in range(0, int(acq_y_Res - 1)): row_off = frm * acq_x_res * 2 for pt in range(0, int(acq_x_res)): frame_data[frm, pt, receiver] = raw_data[ (2 * pt) + row_off] + 1j * raw_data[(2 * pt) + 1 + row_off] fbin.close() amp = np.zeros(n_rcv, dtype=np.int64) amp = amp.view(np.complex64) amp = frame_data[0, 5, :] ang = np.zeros(n_rcv) fid_w = np.zeros(n_rcv) for n in range(0, n_rcv): ang[n] = cmath.phase(list(frame_data[0, 5, :])[n]) # print(ang) ph_dif = ang - ang[0] for receiver in range(0, n_rcv): rot_frame_data[:, :, receiver] = frame_data[:, :, receiver] * np.exp( -1j * ph_dif[receiver]) for receiver in range(0, n_rcv): fid_w[receiver] = abs(amp[receiver]) / np.sqrt( sum(abs(amp * amp))) # fid_w[receiver]=abs(amp[receiver])/sum(abs(amp)) # fid_w=np.max(np.abs(frame_data[1,:,:]),axis=0)/np.sqrt(np.sum(np.max(np.abs(frame_data[1,:,:]),axis=0)*np.max(np.abs(frame_data[1,:,:]),axis=0))) # fid_w=np.abs(np.max(frame_data[0,:,:],axis=0))/(np.sum(np.abs(np.max(frame_data[0,:,:],axis=0)))) fid_norm[:, :, receiver] = rot_frame_data[:, :, receiver] * fid_w[receiver] summed_signal = np.sum(fid_norm, axis=2) #fbin.close() #raw_data=raw_data.astype(np.int64) print('coil weightings:') print(fid_w) output_data_ws = [] for pt in range(w_avgs * int(acq_x_res), np.size(summed_signal)): output_data_ws.append( np.float64(np.imag(summed_signal.flatten()[pt]))) output_data_ws.append( np.float64(np.real(summed_signal.flatten()[pt]))) output_data_w = [] for pt in range(0, w_avgs * int(acq_x_res)): output_data_w.append( np.float64(np.imag(summed_signal.flatten()[pt]))) output_data_w.append( np.float64(np.real(summed_signal.flatten()[pt]))) file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'MRSpectroscopyStorage' file_meta.MediaStorageSOPInstanceUID = dicom.UID.generate_uid() file_meta.ImplementationClassUID = dicom.UID.generate_uid() ds_ws = FileDataset(fname + '_dcm', {}, file_meta=file_meta, preamble="\0" * 128) ds_ws.Modality = 'MR' ds_ws.ContentDate = str(datetime.date.today()).replace('-', '') ds_ws.ContentTime = str(time.time()) #milliseconds since the epoch ds_ws.StudyInstanceUID = dicom.UID.generate_uid() ds_ws.SeriesInstanceUID = dicom.UID.generate_uid() ds_ws.SOPInstanceUID = dicom.UID.generate_uid() ds_ws.SOPClassUID = 'MRSpectroscopyStorage' ds_ws.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ds_ws.VolumeLocalizationTechnique = seqtype ds_ws.RepetitionTime = tr / 1000 ## These are the necessary imaging components of the FileDataset object. ds_ws.Columns = 1 ds_ws.Rows = 1 ds_ws.DataPointColumns = int(acq_x_res) ds_ws.SpectroscopyAcquisitionDataColumns = ds_ws.DataPointColumns ds_ws.DataPointRows = ws_avgs ds_ws.SpectroscopyData = output_data_ws ds_ws.ImageType = ['ORIGINAL', 'PRIMARY', 'SPECTROSCOPY', 'NONE'] ds_ws.SpectralWidth = bandwidth ds_ws.SeriesNumber = series_no ds_ws.ProtocolName = fname.split('\\')[-1].split( '.')[0] + '_SVS_TR' + str(int(tr / 1000)) + '_TE' + str( int(te / 1000)) c_freq2 = c_freq / 10000000.0 ds_ws.TransmitterFrequency = c_freq2 ds_ws.EffectiveEchoTime = te / 1000 ds_ws.EchoTime = te / 1000 ds_ws.WaterReferencedPhaseCorrection = 'N' if w_avgs > 0: file_meta_w = Dataset() file_meta_w.MediaStorageSOPClassUID = 'MRSpectroscopyStorage' file_meta_w.MediaStorageSOPInstanceUID = dicom.UID.generate_uid( ) file_meta_w.ImplementationClassUID = dicom.UID.generate_uid() ds_w = FileDataset(fname + '_dcm', {}, file_meta=file_meta, preamble="\0" * 128) ds_w.Modality = 'MR' ds_w.ContentDate = str(datetime.date.today()).replace('-', '') ds_w.ContentTime = str( time.time()) #milliseconds since the epoch ds_w.StudyInstanceUID = dicom.UID.generate_uid() ds_w.SeriesInstanceUID = dicom.UID.generate_uid() ds_w.SOPInstanceUID = dicom.UID.generate_uid() ds_w.SOPClassUID = 'MRSpectroscopyStorage' ds_w.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ds_w.VolumeLocalizationTechnique = seqtype ## These are the necessary imaging components of the FileDataset object. ds_w.Columns = 1 ds_w.Rows = 1 ds_w.DataPointColumns = int(acq_x_res) ds_w.SpectroscopyAcquisitionDataColumns = ds_w.DataPointColumns ds_w.DataPointRows = w_avgs ds_w.SpectroscopyData = output_data_w ds_w.ImageType = [ 'ORIGINAL', 'PRIMARY', 'SPECTROSCOPY', 'NONE' ] ds_w.SpectralWidth = bandwidth ds_w.SeriesNumber = series_no ds_w.ProtocolName = fname.split('\\')[-1].split( '.')[0] + '_SVS_TR' + str(int(tr / 1000)) + '_TE' + str( int(te / 1000)) c_freq2 = c_freq / 10000000.0 ds_w.TransmitterFrequency = c_freq2 ds_w.EffectiveEchoTime = te / 1000 ds_w.EchoTime = te / 1000 ds_w.RepetitionTime = tr / 1000 ds_w.WaterReferencedPhaseCorrection = 'N' if not os.path.exists( str(root_dir) + '/' + str(pat_name) + '_PREPROC_LCM'): os.makedirs( str(root_dir) + '/' + str(pat_name) + '_PREPROC_LCM') # if not os.path.exists(str(root_dir)+'/'+str(pat_name)+'_LCM_Results'): # os.makedirs(str(root_dir)+'/'+str(pat_name)+'_LCM_Results') ds_ws.save_as( str(root_dir) + '/' + str(pat_name) + '_PREPROC_LCM/' + str(ds_ws.ProtocolName)) if w_avgs > 0: ds_w.save_as( str(root_dir) + '/' + str(pat_name) + '_PREPROC_LCM/' + str(ds_w.ProtocolName) + '_WATER') except AttributeError: print('...') except IOError: print 'no such file' print('DONE!')
def create_dicom(self): """ Generates and returns Dicom RTSTRUCT object, which holds all VOIs. :returns: a Dicom RTSTRUCT object holding any VOIs. """ if _dicom_loaded is False: raise ModuleNotLoadedError("Dicom") meta = Dataset() meta.MediaStorageSOPClassUID = '1.2.840.10008.5.1.4.1.1.481.3' # RT Structure Set Storage SOP Class # see https://github.com/darcymason/pydicom/blob/master/pydicom/_uid_dict.py meta.MediaStorageSOPInstanceUID = "1.2.3" meta.ImplementationClassUID = "1.2.3.4" meta.TransferSyntaxUID = UID.ImplicitVRLittleEndian # Implicit VR Little Endian - Default Transfer Syntax ds = FileDataset("file", {}, file_meta=meta, preamble=b"\0" * 128) if self.cube is not None: ds.PatientsName = self.cube.patient_name else: ds.PatientsName = "" ds.PatientID = "123456" ds.PatientsSex = '0' ds.PatientsBirthDate = '19010101' ds.SpecificCharacterSet = 'ISO_IR 100' ds.AccessionNumber = '' ds.is_little_endian = True ds.is_implicit_VR = True ds.SOPClassUID = '1.2.840.10008.5.1.4.1.1.481.3' # RT Structure Set Storage SOP Class ds.SOPInstanceUID = '1.2.3' # !!!!!!!!!! ds.StudyInstanceUID = '1.2.3' # !!!!!!!!!! ds.SeriesInstanceUID = '1.2.3' # !!!!!!!!!! ds.FrameofReferenceUID = '1.2.3' # !!!!!!!!! ds.SeriesDate = '19010101' # !!!!!!!! ds.ContentDate = '19010101' # !!!!!! ds.StudyDate = '19010101' # !!!!!!! ds.SeriesTime = '000000' # !!!!!!!!! ds.StudyTime = '000000' # !!!!!!!!!! ds.ContentTime = '000000' # !!!!!!!!! ds.StructureSetLabel = 'pyTRiP plan' ds.StructureSetDate = '19010101' ds.StructureSetTime = '000000' ds.StructureSetName = 'ROI' ds.Modality = 'RTSTRUCT' roi_label_list = [] roi_data_list = [] roi_structure_roi_list = [] # to get DICOM which can be loaded in Eclipse we need to store information about UIDs of all slices in CT # first we check if DICOM cube is loaded if self.cube is not None: rt_ref_series_data = Dataset() rt_ref_series_data.SeriesInstanceUID = '1.2.3.4.5' rt_ref_series_data.ContourImageSequence = Sequence([]) # each CT slice corresponds to one DICOM file for slice_dicom in self.cube.create_dicom(): slice_dataset = Dataset() slice_dataset.ReferencedSOPClassUID = '1.2.840.10008.5.1.4.1.1.2' # CT Image Storage SOP Class slice_dataset.ReferencedSOPInstanceUID = slice_dicom.SOPInstanceUID # most important - slice UID rt_ref_series_data.ContourImageSequence.append(slice_dataset) rt_ref_study_seq_data = Dataset() rt_ref_study_seq_data.ReferencedSOPClassUID = '1.2.840.10008.3.1.2.3.2' # Study Component Management Class rt_ref_study_seq_data.ReferencedSOPInstanceUID = '1.2.3.4.5' rt_ref_study_seq_data.RTReferencedSeriesSequence = Sequence([rt_ref_series_data]) rt_ref_frame_study_data = Dataset() rt_ref_frame_study_data.RTReferencedStudySequence = Sequence([rt_ref_study_seq_data]) rt_ref_frame_study_data.FrameOfReferenceUID = '1.2.3.4.5' ds.ReferencedFrameOfReferenceSequence = Sequence([rt_ref_frame_study_data]) for i in range(self.number_of_vois()): roi_label = self.vois[i].create_dicom_label() roi_label.ObservationNumber = str(i + 1) roi_label.ReferencedROINumber = str(i + 1) roi_label.RefdROINumber = str(i + 1) roi_contours = self.vois[i].create_dicom_contour_data(i) roi_contours.RefdROINumber = str(i + 1) roi_contours.ReferencedROINumber = str(i + 1) roi_structure_roi = self.vois[i].create_dicom_structure_roi() roi_structure_roi.ROINumber = str(i + 1) roi_structure_roi_list.append(roi_structure_roi) roi_label_list.append(roi_label) roi_data_list.append(roi_contours) ds.RTROIObservations = Sequence(roi_label_list) ds.ROIContours = Sequence(roi_data_list) ds.StructureSetROIs = Sequence(roi_structure_roi_list) return ds
def write_dicom(arguments, pixel_array, meta_arr=[]): """ Function to create completely new DICOM file. :param arguments: Dictionary containing input parameters. :param pixel_array: 2D or 3D numpy array containing pixel values. :param meta_arr: An array contaning parsed meta data. :return: """ #TODO:Check the possibility to use UID generator instead hardcoded ones. file_meta = Dataset() # The Secondary Capture (SC) Image Information Object Definition (IOD) specifies images that are converted from # a non-DICOM format to a modality independent DICOM format. file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' # Since we don't want to store any additional info in the header, we set it to x00 ds = FileDataset(arguments['out_file'], {}, file_meta=file_meta, preamble=b'0' * 128) # Type of equipment that originally acquired the data. ds.Modality = 'WSD' # Setting the date and time ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) # milliseconds since the epoch # Keep scrolling :) ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' # Manufacturer ds.SecondaryCaptureDeviceManufctur = 'NCBJ' # These are the necessary imaging components of the FileDataset object. # Number of color channels. ds.SamplesPerPixel = 1 # It defines what does every color channel hold ds.PhotometricInterpretation = "MONOCHROME2" # ds.PixelRepresentation = 0 ds.HighBit = 15 # Here meta-data is put into the Data Set. It can override hardcoded values, but parameters providided as program # arguments will be inserted no matter what is in the meta-data file. ds = write_meta(meta_arr, ds) # How many bits are allocated to store pixel info ds.BitsAllocated = arguments['bytes_per_pix'] * 8 # How many bits are used to store pixel info ds.BitsStored = arguments['bytes_per_pix'] * 8 # Whether signed or unsigned numbers are used if arguments['is_signed']: ds.PixelRepresentation = 1 else: ds.PixelRepresentation = 0 # Read from data the dimensions. if len(pixel_array.shape) == 3: ds.NumberOfFrames = pixel_array.shape[0] ds.Columns = pixel_array.shape[1] ds.Rows = pixel_array.shape[2] else: ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] try: err_str = '[ERROR] The file could not be created because of: ' data_type = recognize_type(arguments['bytes_per_pix'], arguments['is_signed'], arguments['is_float']) if pixel_array.dtype != data_type: pixel_array = pixel_array.astype(data_type) ds.PixelData = pixel_array.tostring() ds.save_as(arguments['out_file'].replace('.dcm', '') + '.dcm') print('[INFO] Writing to DICOM file is complete!') except ValueError as ve: print(err_str + 'ValueError ' + str(ve)) sys.exit(1) except FileExistsError as fe: print(err_str + 'FileExistsError ' + str(fe)) sys.exit(1) except Exception as e: print(err_str + str(e)) sys.exit(1)
def write_dicom(pixel_array, filename, series_number, fdf_info, series_description, project, subject, session): """Write a dicom from a pixel_array (numpy). :param pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. :param filename: string name for the output file. :param ds_ori: original pydicom object of the pixel_array :param series_number: number of the series being processed :param series_description: series description for Osirix display :param project: XNAT Project ID :param subject: XNAT Subject label :param session: XNAT Session label """ # Variables pixel_array = np.rot90(pixel_array) pixel_array = np.rot90(pixel_array) pixel_array = np.rot90(pixel_array) # less than zero # pixel_array[pixel_array < 0] = 0 now = datetime.datetime.now() date = '%d%02d%02d' % (now.year, now.month, now.day) sop_id = '1.2.840.10008.5.1.4.1.1.4.%s' % date ti = str(time.time()) uid = sop_id + ti # Other tags to set sop_uid = sop_id + str(now).replace('-', '')\ .replace(':', '')\ .replace('.', '')\ .replace(' ', '') # Number of frames size = pixel_array.shape nb_frames = None if len(size) == 3: nb_frames = size[2] elif len(size) == 4: nb_frames = size[2]*size[3] # Create the ds object file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = sop_id file_meta.ImplementationClassUID = '1.2.840.10008.5.1.4.1.1.4' ds = FileDataset(filename, {}, file_meta=file_meta, preamble="\0"*128) ds.SeriesDate = '%d%02d%02d' % (now.year, now.month, now.day) ds.ContentDate = '%d%02d%02d' % (now.year, now.month, now.day) ds.ContentTime = str(time.time()) # milliseconds since the epoch ds.StudyInstanceUID = uid ds.SeriesInstanceUID = uid # Other tags to set ds.SOPInstanceUID = sop_uid[:-1] ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' # These are the necessary imaging components of the FileDataset object. ds.Modality = 'MR' ds.ConversionType = 'WSD' ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.Columns = pixel_array.shape[0] ds.Rows = pixel_array.shape[1] ds.ProtocolName = '%s 9.4T' % series_description ds.StudyDescription = project ds.PatientsName = subject ds.PatientID = session ds.SeriesDescription = series_description ds.SeriesNumber = 1 ds.SmallestImagePixelValue = pixel_array.min() ds.LargestImagePixelValue = pixel_array.max() ds.AcquisitionNumber = 1 ds.SamplesperPixel = 1 ds.PixelSpacing = '%s\%s' % (fdf_info['spacing'][0], fdf_info['spacing'][1]) ds.SpacingBetweenSlices = float(fdf_info['spacing'][2]) ds.ImageOrientation = '\\'.join(fdf_info['orientation']) ds.PatientPosition = '\\'.join(fdf_info['origin']) if nb_frames: ds.NumberOfFrames = nb_frames # Organise the array: if len(size) == 3: pixel_array2 = np.zeros((size[0]*size[2], size[1])) for i in range(size[2]): pixel_array2[size[0]*i:size[0]*(i+1), :] = pixel_array[:, :, i] elif len(size) > 3: pixel_array2 = np.zeros((size[0]*size[2]*size[3], size[1])) for i in range(size[2]): for j in range(size[3]): pixel_array2[size[0]*j+i*size[3]*size[0]: size[0]*(j+1)+i*size[3]*size[0], :] = pixel_array[:, :, i, j] else: pixel_array2 = pixel_array # Set the Image pixel array if pixel_array2.dtype != np.uint16: pixel_array2 = pixel_array2.astype(np.uint16) print pixel_array2.max() print pixel_array2.min() ds.PixelData = pixel_array2.tostring() # Save the image ds.save_as(filename)
def WriteDICOM_slice(self, pixel_array, filename, itemnumber=0, PhotometricInterpretation="MONOCHROME2"): from dicom.dataset import Dataset, FileDataset import numpy as np import datetime, time """ INPUTS: pixel_array: 2D numpy ndarray. If pixel_array is larger than 2D, errors. filename: string name for the output file. """ ## This code block was taken from the output of a MATLAB secondary ## capture. I do not know what the long dotted UIDs mean, but ## this code works. file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' ds = FileDataset(filename, {}, file_meta=file_meta, preamble="\0" * 128) ds.Modality = 'WSD' ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'Secondary Capture Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 if PhotometricInterpretation == "MONOCHROME2": ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' elif PhotometricInterpretation == "RGB": ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' pixel_array = pixel_array[0] print pixel_array.shape ds.Columns = pixel_array.shape[0] ds.ItemNumber = str(itemnumber) ds.InstanceNumber = str(itemnumber) ds.SliceLocation = str(itemnumber) ds.Rows = pixel_array.shape[1] if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() ds.save_as(filename) return filename
def encode(self, input_image, text, output_file): print("using file: " + input_image) print("analysis result is: " + text) # first we need to setup some meta data # Populate required values for file meta information file_meta = Dataset() file_meta.MediaStorageSOPClassUID = '1.2.840.10008.5.1.4.1.1.2' # CT Image Storage .... check here: http://dicom.nema.org/dicom/2013/output/chtml/part04/sect_B.5.html file_meta.MediaStorageSOPInstanceUID = "1.2.3" # !! Need valid UID here for real work file_meta.ImplementationClassUID = "1.2.3.4" # !!! Need valid UIDs here # Create the FileDataset instance (initially no data elements, but file_meta supplied) ds = FileDataset(output_file, {}, file_meta=file_meta, preamble=b"\0" * 128) # Add the data elements -- not trying to set all required here. Check DICOM standard # ds.PatientName = "John Smith2" ds.add_new(Tag(0x10,0x10), "PN", "John 99") # this is the tag for patient's name ds.PatientID = "123456" # Set the transfer syntax ds.is_little_endian = True ds.is_implicit_VR = True # Set creation date/time dt = datetime.datetime.now() ds.ContentDate = dt.strftime('%Y%m%d') timeStr = dt.strftime('%H%M%S.%f') # long format with micro seconds ds.ContentTime = timeStr # imge file data # read this http://stackoverflow.com/questions/14350675/create-pydicom-file-from-numpy-array # img=mpimg.imread(input_image) img = cv2.imread(input_image, 0) # we read the image monochrome print(img.shape) plt.imshow(img) print(img.shape[0]) ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = bytes((0,)) ds.LargestImagePixelValue = bytes((255,)) img = img.astype(np.uint16) print(np.amin(img)) print(np.amax(img)) ds.PixelData = img.tostring() ds.Rows = img.shape[0] ds.Columns = img.shape[1] print("Writing test file", output_file) ds.save_as(output_file) print("File saved.") return
def writeDicomFiles(self, filename): for i in range(1,len(self.PA)): #Image 0 is a null image for default display and will not be written out fileName = filename + str(i) + ".dcm" # print ("printing dicom file " + fileName) # Populate required values for file meta information file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' # Create the FileDataset instance (initially no data elements, but file_meta supplied) ds = FileDataset(fileName, {}, file_meta=file_meta, preamble="\0"*128) ds.Modality = 'MR' ds.ContentDate = str(datetime.date.today()).replace('-','') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'MR Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' #Add MRI data elements ds.bValue= self.bValue[i] ds.Columns=self.Columns[i] ds.FoVX=self.FoVX[i] ds.FoVY=self.FoVY[i] ds.ImageOrientationPatient=self.ImagePosition[i].tolist() ds.InstitutionName=self.InstitutionName[i] ds.PixelBandwidth= self.PixelBandwidth[i] ds.PixelSpacing =[self.PixelSpacingY[i],self.PixelSpacingX[i]] ds.Rows= self.Rows[i] ds.PatientName = self.PatientName[i] ds.PatientID = "123456" ds.ProtocolName=self.ProtocolName[i] ds.RepetitionTime = self.TR[i] ds.SeriesDescription=self.SeriesDescription[i] ds.EchoTime = self.TE[i] ds.FlipAngle= self.FA[i] ds.InversionTime=self.TI[i] ds.ImageOrientationPatient[3:6]=self.ColumnDirection[i].tolist() ds.ImageOrientationPatient[:3]=self.RowDirection[i].tolist() ds.MagneticFieldStrength = self.MagneticFieldStrength[i] ds.Manufacturer = self.Manufacturer[i] pixel_array=np.transpose(self.PA[i]) #numpy pixel array if self.DataType[i].lower() == "phase" : pixel_array=(pixel_array+np.pi) *10000 # phase data -pi to pi is converted to 0 to 10000pi #print "Adjusting phase to 16 bit integer" if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() # image byte data # Set the transfer syntax ds.is_little_endian = True ds.is_implicit_VR = True ds.save_as(fileName)
def writeDicomFiles(self, filename): for i in range( 1, len(self.PA) ): #Image 0 is a null image for default display and will not be written out fileName = filename + str(i) + ".dcm" # print ("printing dicom file " + fileName) # Populate required values for file meta information file_meta = Dataset() file_meta.MediaStorageSOPClassUID = 'Secondary Capture Image Storage' file_meta.MediaStorageSOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' file_meta.ImplementationClassUID = '1.3.6.1.4.1.9590.100.1.0.100.4.0' # Create the FileDataset instance (initially no data elements, but file_meta supplied) ds = FileDataset(fileName, {}, file_meta=file_meta, preamble="\0" * 128) ds.Modality = 'MR' ds.ContentDate = str(datetime.date.today()).replace('-', '') ds.ContentTime = str(time.time()) #milliseconds since the epoch ds.StudyInstanceUID = '1.3.6.1.4.1.9590.100.1.1.124313977412360175234271287472804872093' ds.SeriesInstanceUID = '1.3.6.1.4.1.9590.100.1.1.369231118011061003403421859172643143649' ds.SOPInstanceUID = '1.3.6.1.4.1.9590.100.1.1.111165684411017669021768385720736873780' ds.SOPClassUID = 'MR Image Storage' ds.SecondaryCaptureDeviceManufctur = 'Python 2.7.3' ## These are the necessary imaging components of the FileDataset object. ds.SamplesPerPixel = 1 ds.PhotometricInterpretation = "MONOCHROME2" ds.PixelRepresentation = 0 ds.HighBit = 15 ds.BitsStored = 16 ds.BitsAllocated = 16 ds.SmallestImagePixelValue = '\\x00\\x00' ds.LargestImagePixelValue = '\\xff\\xff' #Add MRI data elements ds.bValue = self.bValue[i] ds.Columns = self.Columns[i] ds.FoVX = self.FoVX[i] ds.FoVY = self.FoVY[i] ds.ImageOrientationPatient = self.ImagePosition[i].tolist() ds.InstitutionName = self.InstitutionName[i] ds.PixelBandwidth = self.PixelBandwidth[i] ds.PixelSpacing = [self.PixelSpacingY[i], self.PixelSpacingX[i]] ds.Rows = self.Rows[i] ds.PatientName = self.PatientName[i] ds.PatientID = "123456" ds.ProtocolName = self.ProtocolName[i] ds.RepetitionTime = self.TR[i] ds.SeriesDescription = self.SeriesDescription[i] ds.EchoTime = self.TE[i] ds.FlipAngle = self.FA[i] ds.InversionTime = self.TI[i] ds.ImageOrientationPatient[3:6] = self.ColumnDirection[i].tolist() ds.ImageOrientationPatient[:3] = self.RowDirection[i].tolist() ds.MagneticFieldStrength = self.MagneticFieldStrength[i] ds.Manufacturer = self.Manufacturer[i] pixel_array = np.transpose(self.PA[i]) #numpy pixel array if self.DataType[i].lower() == "phase": pixel_array = ( pixel_array + np.pi ) * 10000 # phase data -pi to pi is converted to 0 to 10000pi #print "Adjusting phase to 16 bit integer" if pixel_array.dtype != np.uint16: pixel_array = pixel_array.astype(np.uint16) ds.PixelData = pixel_array.tostring() # image byte data # Set the transfer syntax ds.is_little_endian = True ds.is_implicit_VR = True ds.save_as(fileName)