示例#1
0
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)
示例#2
0
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)
示例#3
0
文件: DCMReader.py 项目: Jothy/RTQA
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
示例#5
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
示例#7
0
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
示例#8
0
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
示例#9
0
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
示例#10
0
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
示例#11
0
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)
示例#12
0
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!')
示例#13
0
    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
示例#14
0
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)
示例#15
0
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
示例#17
0
    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
示例#18
0
  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)
示例#19
0
 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)