def setUp(self):
        import SampleData
        sampleDataLogic = SampleData.SampleDataLogic()
        dti = sampleDataLogic.downloadMRHead()
        self.file_name = dti.GetStorageNode().GetFileName()

        self.ritk = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
        self.ritk.SetUseOrientationFromFile(True)
        self.ritk.SetUseNativeOriginOn();
        self.ritk.SetOutputScalarTypeToNative()
        self.ritk.SetDesiredCoordinateOrientationToNative()
        self.ritk.SetArchetype(self.file_name)
        self.ritk.Update()

        self.rnrrd = slicer.vtkNRRDReader()
        self.rnrrd.SetFileName(self.file_name)
        self.rnrrd.Update()
  def loadFilesWithSeriesReader(self,imageIOName,files,name):
    """ Explicitly use the named imageIO to perform the loading
    """

    reader = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
    reader.SetArchetype(files[0]);
    for f in files:
      reader.AddFileName(slicer.util.toVTKString(f))
    reader.SetSingleFile(0);
    reader.SetOutputScalarTypeToNative()
    reader.SetDesiredCoordinateOrientationToNative()
    reader.SetUseNativeOriginOn()
    if imageIOName == "GDCM":
      reader.SetDICOMImageIOApproachToGDCM()
    elif imageIOName == "DCMTK":
      reader.SetDICOMImageIOApproachToDCMTK()
    else:
      raise Exception("Invalid imageIOName of %s" % imageIOName)
    logging.info("Loading with imageIOName: %s" % imageIOName)
    reader.Update()

    slicer.modules.reader = reader
    if reader.GetErrorCode() != vtk.vtkErrorCode.NoError:
      errorStrings = (imageIOName, vtk.vtkErrorCode.GetStringFromErrorCode(reader.GetErrorCode()))
      logging.error("Could not read scalar volume using %s approach.  Error is: %s" % errorStrings)
      return


    imageChangeInformation = vtk.vtkImageChangeInformation()
    imageChangeInformation.SetInputConnection(reader.GetOutputPort())
    imageChangeInformation.SetOutputSpacing( 1, 1, 1 )
    imageChangeInformation.SetOutputOrigin( 0, 0, 0 )
    imageChangeInformation.Update()

    name = slicer.mrmlScene.GenerateUniqueName(slicer.util.toVTKString(name))
    volumeNode = slicer.mrmlScene.AddNewNodeByClass("vtkMRMLScalarVolumeNode", name)
    volumeNode.SetAndObserveImageData(imageChangeInformation.GetOutputDataObject(0))
    slicer.vtkMRMLVolumeArchetypeStorageNode.SetMetaDataDictionaryFromReader(volumeNode, reader)
    volumeNode.SetRASToIJKMatrix(reader.GetRasToIjkMatrix())
    volumeNode.CreateDefaultDisplayNodes()

    slicer.modules.DICOMInstance.reader = reader
    slicer.modules.DICOMInstance.imageChangeInformation = imageChangeInformation

    return(volumeNode)
  def loadFilesWithSeriesReader(self,imageIOName,files,name):
    """ Explicitly use the named imageIO to perform the loading
    """

    reader = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
    reader.SetArchetype(files[0]);
    for f in files:
      reader.AddFileName(slicer.util.toVTKString(f))
    reader.SetSingleFile(0);
    reader.SetOutputScalarTypeToNative()
    reader.SetDesiredCoordinateOrientationToNative()
    reader.SetUseNativeOriginOn()
    if imageIOName == "GDCM":
      reader.SetDICOMImageIOApproachToGDCM()
    elif imageIOName == "DCMTK":
      reader.SetDICOMImageIOApproachToDCMTK()
    else:
      raise Exception("Invalid imageIOName of %s" % imageIOName)
    logging.info("Loading with imageIOName: %s" % imageIOName)
    reader.Update()

    slicer.modules.reader = reader
    if reader.GetErrorCode() != vtk.vtkErrorCode.NoError:
      errorStrings = (imageIOName, vtk.vtkErrorCode.GetStringFromErrorCode(reader.GetErrorCode()))
      logging.error("Could not read scalar volume using %s approach.  Error is: %s" % errorStrings)
      return


    imageChangeInformation = vtk.vtkImageChangeInformation()
    imageChangeInformation.SetInputConnection(reader.GetOutputPort())
    imageChangeInformation.SetOutputSpacing( 1, 1, 1 )
    imageChangeInformation.SetOutputOrigin( 0, 0, 0 )
    imageChangeInformation.Update()

    name = slicer.mrmlScene.GenerateUniqueName(slicer.util.toVTKString(name))
    volumeNode = slicer.mrmlScene.AddNewNodeByClass("vtkMRMLScalarVolumeNode", name)
    volumeNode.SetAndObserveImageData(imageChangeInformation.GetOutputDataObject(0))
    slicer.vtkMRMLVolumeArchetypeStorageNode.SetMetaDataDictionaryFromReader(volumeNode, reader)
    volumeNode.SetRASToIJKMatrix(reader.GetRasToIjkMatrix())
    volumeNode.CreateDefaultDisplayNodes()

    slicer.modules.DICOMInstance.reader = reader
    slicer.modules.DICOMInstance.imageChangeInformation = imageChangeInformation

    return(volumeNode)
Exemple #4
0
  def loadBabies(self,directoryPath,pattern,maxIndex=None):
    self.images = []
    filePaths = []
    index = 1
    import os.path
    while True:
      filePath = os.path.join(directoryPath, pattern % index)
      if not os.path.exists(filePath):
        break
      filePaths.append(filePath)
      index += 1
      if maxIndex and index > maxIndex:
        break

    if len(filePaths) == 0:
      return

    middleBabyPath = filePaths[len(filePaths)/2]
    babyVolume = self.babyVolume(middleBabyPath)

    #transtor = slicer.vtkMRMLTransformStorageNode()
    reader = reader = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
    reader.SetSingleFile(1)
    reader.SetUseOrientationFromFile(1)
    #reader.SetDesiredCoordinateOrientationToAxial()
    reader.SetOutputScalarTypeToNative()
    reader.SetUseNativeOriginOn()
    changeInfo = vtk.vtkImageChangeInformation()
    changeInfo.SetInputConnection( reader.GetOutputPort() )
    changeInfo.SetOutputSpacing( 1, 1, 1 )
    changeInfo.SetOutputOrigin( 0, 0, 0 )
    self.images = {}
    self.rasToIJKs = {}
    #self.toTemplate = {}
    for filePath in filePaths:
      print("Loading %s" % filePath)
      reader.SetArchetype(filePath)
      changeInfo.Update()
      self.rasToIJKs[filePath] = vtk.vtkMatrix4x4()
      self.rasToIJKs[filePath].DeepCopy(reader.GetRasToIjkMatrix())
      self.images[filePath] = vtk.vtkImageData()
      self.images[filePath].DeepCopy(changeInfo.GetOutput())
Exemple #5
0
    def setUp(self):
        import SampleData
        sampleDataLogic = SampleData.SampleDataLogic()
        dti = sampleDataLogic.downloadMRHead()
        self.file_name = dti.GetStorageNode().GetFileName()

        self.ritk = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
        self.ritk.SetUseOrientationFromFile(True)
        self.ritk.SetUseNativeOriginOn()
        self.ritk.SetOutputScalarTypeToNative()
        self.ritk.SetDesiredCoordinateOrientationToNative()
        self.ritk.SetArchetype(self.file_name)
        self.ritk.Update()

        self.rnrrd = slicer.vtkNRRDReader()
        self.rnrrd.SetFileName(self.file_name)
        self.rnrrd.Update()

        self.assertTrue(
            compare_vtk_matrix(self.ritk.GetRasToIjkMatrix(),
                               self.rnrrd.GetRasToIjkMatrix()))
    def setUp(self):
        from SampleData import SampleDataLogic
        brainSource = SampleDataLogic().sourceForSampleName('MRHead')
        self.file_name = SampleDataLogic().downloadSourceIntoCache(
            brainSource)[0]

        self.ritk = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
        self.ritk.SetUseOrientationFromFile(True)
        self.ritk.SetUseNativeOriginOn()
        self.ritk.SetOutputScalarTypeToNative()
        self.ritk.SetDesiredCoordinateOrientationToNative()
        self.ritk.SetArchetype(self.file_name)
        self.ritk.Update()

        self.rnrrd = teem.vtkTeemNRRDReader()
        self.rnrrd.SetFileName(self.file_name)
        self.rnrrd.Update()

        self.assertTrue(
            compare_vtk_matrix(self.ritk.GetRasToIjkMatrix(),
                               self.rnrrd.GetRasToIjkMatrix()))
    def setUp(self):
        from SampleData import SampleDataLogic
        brainSource = SampleDataLogic().sourceForSampleName('MRHead')
        self.file_name = SampleDataLogic().downloadSourceIntoCache(brainSource)[0]

        self.ritk = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
        self.ritk.SetUseOrientationFromFile(True)
        self.ritk.SetUseNativeOriginOn();
        self.ritk.SetOutputScalarTypeToNative()
        self.ritk.SetDesiredCoordinateOrientationToNative()
        self.ritk.SetArchetype(self.file_name)
        self.ritk.Update()

        self.rnrrd = teem.vtkTeemNRRDReader()
        self.rnrrd.SetFileName(self.file_name)
        self.rnrrd.Update()

        self.assertTrue(
            compare_vtk_matrix(
                self.ritk.GetRasToIjkMatrix(),
                self.rnrrd.GetRasToIjkMatrix()
            )
        )
    def load(self, loadable):
        """Load the selection
    """

        filePath = loadable.files[0]
        metadata = self.getMetadata(filePath)

        import vtkITK
        reader = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
        reader.SetArchetype(filePath)
        reader.AddFileName(filePath)
        reader.SetSingleFile(True)
        reader.SetOutputScalarTypeToNative()
        reader.SetDesiredCoordinateOrientationToNative()
        reader.SetUseNativeOriginOn()
        # GDCM is not particularly better in this than DCMTK, we just select one explicitly
        # so that we know which one is used
        reader.SetDICOMImageIOApproachToGDCM()
        reader.Update()
        imageData = reader.GetOutput()
        from __main__ import vtk
        if reader.GetErrorCode() != vtk.vtkErrorCode.NoError:
            errorString = vtk.vtkErrorCode.GetStringFromErrorCode(
                reader.GetErrorCode())
            raise ValueError(
                "Could not read image {0} from file {1}. Error is: {2}".format(
                    loadable.name, filePath, errorString))

        # Image origin and spacing is stored in IJK to RAS matrix
        imageData.SetSpacing(1.0, 1.0, 1.0)
        imageData.SetOrigin(0.0, 0.0, 0.0)

        volumeNode = slicer.mrmlScene.AddNewNodeByClass(
            "vtkMRMLScalarVolumeNode",
            slicer.mrmlScene.GenerateUniqueName(loadable.name))

        # I axis: scanline index (lateralSpacing)
        # J axis: sound propagation (axialSpacing)
        # K axis: slice (sliceSpacing)
        lateralSpacing = metadata['PixelSpacing'][1]
        axialSpacing = metadata['PixelSpacing'][0]
        sliceSpacing = metadata['SpacingBetweenSlices']

        ijkToRas = vtk.vtkMatrix4x4()
        ijkToRas.SetElement(0, 0, -1)
        ijkToRas.SetElement(1, 1, -1)  # so that J axis points toward posterior
        volumeNode.SetIJKToRASMatrix(ijkToRas)
        volumeNode.SetSpacing(lateralSpacing, axialSpacing, sliceSpacing)
        extent = imageData.GetExtent()
        volumeNode.SetOrigin(
            (extent[1] - extent[0] + 1) * 0.5 * lateralSpacing, 0,
            -(extent[5] - extent[2] + 1) * 0.5 * sliceSpacing)
        volumeNode.SetAndObserveImageData(imageData)

        # Apply scan conversion transform
        acquisitionTransform = self.createAcquisitionTransform(
            volumeNode, metadata)
        volumeNode.SetAndObserveTransformNodeID(acquisitionTransform.GetID())

        # Create Subject hierarchy nodes for the loaded series
        self.addSeriesInSubjectHierarchy(loadable, volumeNode)

        # Place transform in the same subject hierarchy folder as the volume node
        shNode = slicer.vtkMRMLSubjectHierarchyNode.GetSubjectHierarchyNode(
            slicer.mrmlScene)
        volumeParentItemId = shNode.GetItemParent(
            shNode.GetItemByDataNode(volumeNode))
        shNode.SetItemParent(shNode.GetItemByDataNode(acquisitionTransform),
                             volumeParentItemId)

        # Show in slice views
        selectionNode = slicer.app.applicationLogic().GetSelectionNode()
        selectionNode.SetReferenceActiveVolumeID(volumeNode.GetID())
        slicer.app.applicationLogic().PropagateVolumeSelection(1)

        return volumeNode
  def load(self,loadable):
    """Load the selection
    """

    outputSequenceNodes = []
    for filePath in loadable.files:

      import vtkITK
      if loadable.grayscale:
        reader = vtkITK.vtkITKArchetypeImageSeriesScalarReader()
      else:
        reader = vtkITK.vtkITKArchetypeImageSeriesVectorReaderFile()
      reader.SetArchetype(filePath)
      reader.AddFileName(filePath)
      reader.SetSingleFile(True)
      reader.SetOutputScalarTypeToNative()
      reader.SetDesiredCoordinateOrientationToNative()
      reader.SetUseNativeOriginOn()
      # GDCM is not particularly better in this than DCMTK, we just select one explicitly
      # so that we know which one is used
      reader.SetDICOMImageIOApproachToGDCM()
      reader.Update()
      if reader.GetErrorCode() != vtk.vtkErrorCode.NoError:
          errorString = vtk.vtkErrorCode.GetStringFromErrorCode(reader.GetErrorCode())
          raise ValueError("Could not read image {0} from file {1}. Error is: {2}".format(loadable.name, filePath, errorString))

      volume = reader.GetOutput()

      [spacingX, spacingY, frameTimeMsec] = volume.GetSpacing()

      volume.SetSpacing(1.0, 1.0, 1.0)

      outputSequenceNode = slicer.mrmlScene.AddNewNodeByClass("vtkMRMLSequenceNode")
      if frameTimeMsec == 1.0:
        # frame time is not found, set it to 1.0fps
        frameTime = 1
        outputSequenceNode.SetIndexName("frame")
        outputSequenceNode.SetIndexUnit("")
        playbackRateFps = 10
      else:
        frameTime = frameTimeMsec * 0.001
        outputSequenceNode.SetIndexName("time")
        outputSequenceNode.SetIndexUnit("s")
        playbackRateFps = 1.0/frameTime

      if loadable.grayscale:
        tempFrameVolume = slicer.mrmlScene.AddNewNodeByClass("vtkMRMLScalarVolumeNode")
      else:
        tempFrameVolume = slicer.mrmlScene.AddNewNodeByClass("vtkMRMLVectorVolumeNode")

      # Rotate 180deg, otherwise the image would appear upside down
      ijkToRAS = vtk.vtkMatrix4x4()
      ijkToRAS.SetElement(0,0,-1.0)
      ijkToRAS.SetElement(1,1,-1.0)
      tempFrameVolume.SetIJKToRASMatrix(ijkToRAS)

      tempFrameVolume.SetSpacing(spacingX, spacingY, 1.0)

      numberOfFrames = volume.GetDimensions()[2]
      extent = volume.GetExtent()
      numberOfFrames = extent[5]-extent[4]+1
      for frame in range(numberOfFrames):

        crop = vtk.vtkImageClip()
        crop.SetInputData(volume)
        crop.SetOutputWholeExtent(extent[0], extent[1], extent[2], extent[3], extent[4]+frame, extent[4]+frame)
        crop.ClipDataOn()
        crop.Update()
        croppedOutput = crop.GetOutput()
        croppedOutput.SetExtent(extent[0], extent[1], extent[2], extent[3], 0, 0)
        tempFrameVolume.SetAndObserveImageData(croppedOutput)
        if type(frameTime)==int:
          timeStampSec = str(frame * frameTime)
        else:
          timeStampSec = "{:.3f}".format(frame * frameTime)
        outputSequenceNode.SetDataNodeAtValue(tempFrameVolume, timeStampSec)

      slicer.mrmlScene.RemoveNode(tempFrameVolume)

      if len(loadable.files) == 1:
        outputSequenceNode.SetName(loadable.name)
      else:
        ds = dicom.read_file(filePath, stop_before_pixels=True)
        if hasattr(ds, 'PositionerPrimaryAngle') and hasattr(ds, 'PositionerSecondaryAngle'):
          outputSequenceNode.SetName('{0} ({1}/{2})'.format(loadable.name, ds.PositionerPrimaryAngle,ds.PositionerSecondaryAngle))
        else:
          outputSequenceNode.SetName(loadable.name)

      slicer.mrmlScene.AddNode(outputSequenceNode)

      # Create storage node that allows saving node as nrrd
      outputSequenceStorageNode = slicer.vtkMRMLVolumeSequenceStorageNode()
      slicer.mrmlScene.AddNode(outputSequenceStorageNode)
      outputSequenceNode.SetAndObserveStorageNodeID(outputSequenceStorageNode.GetID())

      outputSequenceNodes.append(outputSequenceNode)

    if not hasattr(loadable, 'createBrowserNode') or loadable.createBrowserNode:
      # Add a browser node and show the volume in the slice viewer for user convenience
      outputSequenceBrowserNode = slicer.vtkMRMLSequenceBrowserNode()
      outputSequenceBrowserNode.SetName(slicer.mrmlScene.GenerateUniqueName(loadable.name+' browser'))
      outputSequenceBrowserNode.SetPlaybackRateFps(playbackRateFps)
      slicer.mrmlScene.AddNode(outputSequenceBrowserNode)

      # Add all sequences to the sequence browser
      first = True
      for outputSequenceNode in outputSequenceNodes:
        #outputSequenceBrowserNode.SetAndObserveMasterSequenceNodeID(outputSequenceNode.GetID())
        outputSequenceBrowserNode.AddSynchronizedSequenceNode(outputSequenceNode)
        proxyVolumeNode = outputSequenceBrowserNode.GetProxyNode(outputSequenceNode)
        # create Subject hierarchy nodes for the loaded series
        self.addSeriesInSubjectHierarchy(loadable, proxyVolumeNode)

        if first:
          first = False
          # Automatically select the volume to display
          appLogic = slicer.app.applicationLogic()
          selNode = appLogic.GetSelectionNode()
          selNode.SetReferenceActiveVolumeID(proxyVolumeNode.GetID())
          appLogic.PropagateVolumeSelection()
          appLogic.FitSliceToAll()
          slicer.modules.sequences.setToolBarActiveBrowserNode(outputSequenceBrowserNode)

      # Show sequence browser toolbar
      slicer.modules.sequences.showSequenceBrowser(outputSequenceBrowserNode)

    return outputSequenceNode