def to_vtk(n_array, spacing, slice_number, orientation): try: dz, dy, dx = n_array.shape except ValueError: dy, dx = n_array.shape dz = 1 v_image = numpy_support.numpy_to_vtk(n_array.flat) if orientation == 'AXIAL': extent = (0, dx -1, 0, dy -1, slice_number, slice_number + dz - 1) elif orientation == 'SAGITAL': dx, dy, dz = dz, dx, dy extent = (slice_number, slice_number + dx - 1, 0, dy - 1, 0, dz - 1) elif orientation == 'CORONAL': dx, dy, dz = dx, dz, dy extent = (0, dx - 1, slice_number, slice_number + dy - 1, 0, dz - 1) # Generating the vtkImageData image = vtk.vtkImageData() image.SetOrigin(0, 0, 0) image.SetSpacing(spacing) image.SetDimensions(dx, dy, dz) # SetNumberOfScalarComponents and SetScalrType were replaced by # AllocateScalars # image.SetNumberOfScalarComponents(1) # image.SetScalarType(numpy_support.get_vtk_array_type(n_array.dtype)) image.AllocateScalars(numpy_support.get_vtk_array_type(n_array.dtype), 1) image.SetExtent(extent) image.GetPointData().SetScalars(v_image) image_copy = vtk.vtkImageData() image_copy.DeepCopy(image) return image_copy
def onCenterPointSet(self, xy): import vtk.util.numpy_support as vnp zFrameTemplateVolume = self.zFrameTemplateVolumeSelector.currentNode() volumesLogic = slicer.modules.volumes.logic() zFrameTemplateMask = volumesLogic.CreateLabelVolume(slicer.mrmlScene, zFrameTemplateVolume, 'zFrameTemplateMask') imageDataWorkingCopy = vtk.vtkImageData() imageDataWorkingCopy.DeepCopy(zFrameTemplateMask.GetImageData()) newLabelNodeImage=vtk.vtkImageData() newLabelNodeImage.AllocateScalars(vtk.VTK_SHORT, 1) newLabelNodeImage.SetExtent(zFrameTemplateMask.GetImageData().GetExtent()) numpyArray = vnp.vtk_to_numpy(imageDataWorkingCopy.GetPointData().GetScalars()).reshape(imageDataWorkingCopy.GetDimensions()).transpose(2,1,0) numpyArray[6:10,70:185,65:190].fill(1) spacing = imageDataWorkingCopy.GetSpacing() vtk_data = vnp.numpy_to_vtk(num_array=numpyArray.ravel(), deep=True, array_type=vtk.VTK_SHORT) newLabelNodeImage.GetPointData().SetScalars(vtk_data) dims = numpyArray.shape newLabelNodeImage.SetDimensions(dims[2], dims[1], dims[0]) newLabelNodeImage.SetOrigin(0,0,0) newLabelNodeImage.SetSpacing(spacing[0], spacing[1], spacing[2]) zFrameTemplateMask.SetAndObserveImageData(newLabelNodeImage) # update the default label map to the generic anatomy colors labelDisplayNode = zFrameTemplateMask.GetDisplayNode() labelColorTable = slicer.util.getNode('GenericAnatomyColors') labelDisplayNode.SetAndObserveColorNodeID(labelColorTable.GetID()) self.redCompositeNode.SetBackgroundVolumeID(zFrameTemplateVolume.GetID()) self.redCompositeNode.SetLabelVolumeID(zFrameTemplateMask.GetID()) self.redCompositeNode.SetLabelOpacity(0.6) self.maskedVolume = self.createMaskedVolume(zFrameTemplateVolume, zFrameTemplateMask)
def read(self, path): try: mat_dict = scipy.io.loadmat(path) except NotImplementedError as e: # matlab v7.3 requires h5py to load if 'matlab v7.3' in str(e).lower(): print('Tomviz does not currently support matlab v7.3 files') print('Please convert the file to matlab v7.2 or earlier') return vtkImageData() raise data = None for item in mat_dict.values(): # Assume only one 3D array per file if isinstance(item, np.ndarray): if len(item.shape) == 3: data = item break if data is None: return vtkImageData() image_data = vtkImageData() (x, y, z) = data.shape image_data.SetOrigin(0, 0, 0) image_data.SetSpacing(1, 1, 1) image_data.SetExtent(0, x - 1, 0, y - 1, 0, z - 1) tomviz.utils.set_array(image_data, data) return image_data
def __init__(self, inputVolumes, outputVolume): """Configure outputVolume and an iterationVolume to match the first inputVolume.""" self.inputVolumes = inputVolumes self.outputVolume = outputVolume if len(inputVolumes) < 1: raise "Must have at least one input volume" self.volume0 = inputVolumes[0] if not self.volume0.GetImageData(): raise "Must have a valid input volume with image data" # TODO: caller should be required to specify all scratch volumes iterationName = '%s-iteration' % self.outputVolume.GetName() self.iterationVolume = slicer.util.getNode(iterationName) if not self.iterationVolume: self.iterationVolume = slicer.vtkMRMLScalarVolumeNode() self.iterationVolume.SetName(iterationName) slicer.mrmlScene.AddNode(self.iterationVolume) rasToIJK = vtk.vtkMatrix4x4() self.volume0.GetRASToIJKMatrix(rasToIJK) for volume in [self.iterationVolume, self.outputVolume]: volume.SetRASToIJKMatrix(rasToIJK) volume.SetAndObserveTransformNodeID(self.volume0.GetTransformNodeID()) image = vtk.vtkImageData() image.SetDimensions(self.volume0.GetImageData().GetDimensions()) image.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, 4) # TODO: needs to be RGBA for rendering volume.SetAndObserveImageData(image) self.header = """ #version 120 vec3 transformPoint(const in vec3 samplePoint) { return samplePoint; // identity } """ self.vertexShaderTemplate = """ #version 120 attribute vec3 vertexAttribute; attribute vec2 textureCoordinateAttribute; varying vec3 interpolatedTextureCoordinate; void main() { interpolatedTextureCoordinate = vec3(textureCoordinateAttribute, .5); gl_Position = vec4(vertexAttribute, 1.); } """ self.readBackToVolumeNode = False self.dummyImage = vtk.vtkImageData() self.dummyImage.SetDimensions(5,5,5) self.dummyImage.AllocateScalars(vtk.VTK_SHORT, 1)
def FixGantryTilt(imagedata, tilt): """ Fix gantry tilt given a vtkImageData and the tilt value. Return new vtkImageData. """ # Retrieve data from original imagedata extent = [int(value) for value in imagedata.GetExtent()] origin = imagedata.GetOrigin() spacing = [float(value) for value in imagedata.GetSpacing()] n_slices = int(extent[5]) new_zspacing = math.cos(tilt*(math.acos(-1.0)/180.0)) * spacing[2] #zspacing translate_coef = math.tan(tilt*math.pi/180.0)*new_zspacing*(n_slices-1) # Class responsible for translating data reslice = vtk.vtkImageReslice() reslice.SetInput(imagedata) reslice.SetInterpolationModeToLinear() # Translation will create new pixels. Let's set new pixels' colour to black. reslice.SetBackgroundLevel(imagedata.GetScalarRange()[0]) # Class responsible for append translated data append = vtk.vtkImageAppend() append.SetAppendAxis(2) # Translate and append each slice for i in xrange(n_slices+1): slice_imagedata = vtk.vtkImageData() value = math.tan(tilt*math.pi/180.0) * new_zspacing * i new_origin1 = origin[1] + value - translate_coef # Translate data reslice.SetOutputOrigin(origin[0], new_origin1, origin[2]) reslice.SetOutputExtent(extent[0], extent[1], extent[2], extent[3], i,i) reslice.Update() # Append data slice_imagedata.DeepCopy(reslice.GetOutput()) slice_imagedata.UpdateInformation() append.AddInput(slice_imagedata) append.Update() # Final imagedata imagedata = vtk.vtkImageData() imagedata.DeepCopy(append.GetOutput()) imagedata.SetSpacing(spacing[0], spacing[1], new_zspacing) imagedata.SetExtent(extent) imagedata.UpdateInformation() return imagedata
def removeIslandsMorphology(self): """ Remove cruft from image by eroding away by iterations number of layers of surface pixels and then saving only islands that are bigger than the minimumSize. Then dilate back and save only the pixels that are in both the original and result image. Result is that small islands outside the foreground and small features on the foreground are removed. By calling the decrufter twice with fg and bg reversed, you can clean up small features in a label map while preserving the original boundary in other places. """ if not self.sliceLogic: self.sliceLogic = self.editUtil.getSliceLogic() parameterNode = self.editUtil.getParameterNode() self.minimumSize = int(parameterNode.GetParameter("IslandEffect,minimumSize")) self.fullyConnected = bool(parameterNode.GetParameter("IslandEffect,fullyConnected")) labelImage = vtk.vtkImageData() labelImage.DeepCopy( self.getScopedLabelInput() ) label = self.editUtil.getLabel() slicer.modules.EditorWidget.toolsBox.undoRedo.saveState() self.removeIslandsMorphologyDecruft(labelImage,0,label) self.getScopedLabelOutput().DeepCopy(labelImage) self.applyScopedLabel() slicer.app.processEvents(qt.QEventLoop.ExcludeUserInputEvents) self.removeIslandsMorphologyDecruft(labelImage,label,0) self.getScopedLabelOutput().DeepCopy(labelImage) self.applyScopedLabel()
def create_image_data(nx, ny, nz, dx=1.0, dy=1.0, dz=1.0, ox=0, oy=0, oz=0): """ Construct an empty vtkImageData. This data structure is a regular grid with constant spacing. :param nx: number of grid points along x-axis :param ny: number of grid points along y-axis :param nz: number of grid points along z-axis :param dx: spacing along x-axis :param dy: spacing along y-axis :param dz: spacing along z-axis :param ox: origin of x-axis :param oy: origin of y-axis :param oz: origin of z-axis :type nx: int :type ny: int :type nz: int :type dx: float :type dy: float :type dz: float :type ox: float :type oy: float :type oz: float >>> image_data = create_image_data(32, 32, 32) """ image_data = vtk.vtkImageData() image_data.SetDimensions(nx, ny, nz) image_data.SetExtent(0, nx - 1, 0, ny - 1, 0, nz - 1) image_data.SetOrigin(ox, oy, oz) image_data.SetSpacing(dx, dy, dz) return image_data
def createSampleLabelmapVolumeNode(self, volumeNode, name, label, colorNode=None): self.assertTrue( volumeNode != None ) self.assertTrue( volumeNode.IsA('vtkMRMLScalarVolumeNode') ) self.assertTrue( label > 0 ) sampleLabelmapNode = slicer.vtkMRMLLabelMapVolumeNode() sampleLabelmapNode.SetName(name) sampleLabelmapNode = slicer.mrmlScene.AddNode(sampleLabelmapNode) sampleLabelmapNode.Copy(volumeNode) imageData = vtk.vtkImageData() imageData.DeepCopy(volumeNode.GetImageData()) sampleLabelmapNode.SetAndObserveImageData(imageData) extent = imageData.GetExtent() for x in xrange(extent[0], extent[1]+1): for y in xrange(extent[2], extent[3]+1): for z in xrange(extent[4], extent[5]+1): if (x >= (extent[1]/4) and x <= (extent[1]/4) * 3) and (y >= (extent[3]/4) and y <= (extent[3]/4) * 3) and (z >= (extent[5]/4) and z <= (extent[5]/4) * 3): imageData.SetScalarComponentFromDouble(x,y,z,0,label) else: imageData.SetScalarComponentFromDouble(x,y,z,0,0) # Display labelmap labelmapVolumeDisplayNode = slicer.vtkMRMLLabelMapVolumeDisplayNode() slicer.mrmlScene.AddNode(labelmapVolumeDisplayNode) if colorNode == None: colorNode = slicer.util.getNode('GenericAnatomyColors') self.assertTrue( colorNode != None ) labelmapVolumeDisplayNode.SetAndObserveColorNodeID(colorNode.GetID()) labelmapVolumeDisplayNode.VisibilityOn() sampleLabelmapNodeName = slicer.mrmlScene.GenerateUniqueName(name) sampleLabelmapNode.SetName(sampleLabelmapNodeName) sampleLabelmapNode.SetAndObserveDisplayNodeID(labelmapVolumeDisplayNode.GetID()) return sampleLabelmapNode
def convertArray2vtkImage(self, nparray, t_ImagedataVTK, npImagesandMask): """ Takes a numpy.ndarray and converts it to a vtkimageData. require npImagesandMask to pass on image info """ # Create vtk object size_array = npImagesandMask['dims'][0]*npImagesandMask['dims'][1]*npImagesandMask['dims'][2] flatim = nparray.transpose(2,1,0) flatim = flatim.flatten() # create vtk image vtk_image = vtk.vtkImageData() vtk_image.DeepCopy(t_ImagedataVTK) vtk_image.SetNumberOfScalarComponents(1) vtk_image.SetScalarTypeToDouble() vtk_image.AllocateScalars() # Get scalars from numpy image_array = vtk.vtkDoubleArray() image_array.SetNumberOfValues(size_array) image_array.SetNumberOfComponents(1) # not too efficient convertion of np.array to vtk. Far from ideal for k in range(size_array): image_array.InsertTuple1(k,flatim[k]) vtk_image.GetPointData().SetScalars(image_array) vtk_image.Update() return vtk_image
def IsosurfaceInitialize(self): self.PrintLog('Isosurface initialization.') if self.Interactive: queryString = "Please input isosurface level (\'n\' for none): " self.IsoSurfaceValue = self.ThresholdInput(queryString) imageMathematics = vtk.vtkImageMathematics() imageMathematics.SetInput(self.Image) imageMathematics.SetConstantK(-1.0) imageMathematics.SetOperationToMultiplyByK() imageMathematics.Update() subtract = vtk.vtkImageMathematics() subtract.SetInput(imageMathematics.GetOutput()) subtract.SetOperationToAddConstant() subtract.SetConstantC(self.IsoSurfaceValue) subtract.Update() self.InitialLevelSets = vtk.vtkImageData() self.InitialLevelSets.DeepCopy(subtract.GetOutput()) self.InitialLevelSets.Update() self.IsoSurfaceValue = 0.0
def __init__(self, sliceWidget): super(ThresholdEffectTool,self).__init__(sliceWidget) # create a logic instance to do the non-gui work self.logic = ThresholdEffectLogic(self.sliceWidget.sliceLogic()) self.logic.undoRedo = self.undoRedo # interaction state variables self.min = 0 self.max = 0 # class instances self.lut = None self.thresh = None self.map = None # feedback actor self.cursorMapper = vtk.vtkImageMapper() self.cursorDummyImage = vtk.vtkImageData() self.cursorDummyImage.AllocateScalars(vtk.VTK_UNSIGNED_INT, 1) self.cursorMapper.SetInputData( self.cursorDummyImage ) self.cursorActor = vtk.vtkActor2D() self.cursorActor.VisibilityOff() self.cursorActor.SetMapper( self.cursorMapper ) self.cursorMapper.SetColorWindow( 255 ) self.cursorMapper.SetColorLevel( 128 ) self.actors.append( self.cursorActor ) self.renderer.AddActor2D( self.cursorActor )
def ndarray2vtkImageData(ndarray, cast_type=11, spacing=[1, 1, 1]): """ Convert a NumPy array to a vtkImageData, with a default casting type VTK_DOUBLE :param ndarray: input NumPy array, can be 3D array :param cast_type: 11 means VTK_DOUBLE :return: a vtkImageData """ # Convert numpy array to VTK array (vtkDoubleArray) vtk_data_array = numpy_support.numpy_to_vtk( num_array=ndarray.transpose(2, 1, 0).ravel(), deep=True, array_type=vtk.VTK_DOUBLE) # Convert the VTK array to vtkImageData img_vtk = vtk.vtkImageData() img_vtk.SetDimensions(ndarray.shape) img_vtk.SetSpacing(spacing[::-1]) # Note the order should be reversed! img_vtk.GetPointData().SetScalars(vtk_data_array) # is a vtkImageData # casting cast = vtk.vtkImageCast() cast.SetInputData(img_vtk) cast.SetOutputScalarType(cast_type) cast.Update() return cast.GetOutput() # vtkImageData
def DICOMReaderToNumpy(directory): file_list = glob.glob(directory + os.sep + "*") file_list = sorted(file_list) ipp = gdcm.IPPSorter() ipp.SetComputeZSpacing(True) ipp.Sort(file_list) file_list = ipp.GetFilenames() array = vtk.vtkStringArray() for x in xrange(len(file_list)): array.InsertValue(x, file_list[x]) read = vtkgdcm.vtkGDCMImageReader() read.SetFileNames(array) read.Update() img = vtk.vtkImageData() img.DeepCopy(read.GetOutput()) img.SetSpacing(1, 1, 1) img.Update() ex = img.GetExtent() image = vtk.util.numpy_support.vtk_to_numpy(img.GetPointData().GetScalars()) image = image.reshape((ex[5] + 1, ex[1] + 1, ex[3] + 1)) return ApplyWindowLevel(image, 2000, 300)
def SeedInitialize(self): self.PrintLog('Seed initialization.') queryString = 'Please place seeds' seeds = self.SeedInput(queryString,0) self.InitialLevelSets = vtk.vtkImageData() self.InitialLevelSets.DeepCopy(self.Image) self.InitialLevelSets.Update() levelSetsInputScalars = self.InitialLevelSets.GetPointData().GetScalars() levelSetsInputScalars.FillComponent(0,1.0) dimensions = self.Image.GetDimensions() for i in range(seeds.GetNumberOfPoints()): id = self.Image.FindPoint(seeds.GetPoint(i)) levelSetsInputScalars.SetComponent(id,0,-1.0) dilateErode = vtk.vtkImageDilateErode3D() dilateErode.SetInput(self.InitialLevelSets) dilateErode.SetDilateValue(-1.0) dilateErode.SetErodeValue(1.0) dilateErode.SetKernelSize(3,3,3) dilateErode.Update() self.InitialLevelSets.DeepCopy(dilateErode.GetOutput()) self.IsoSurfaceValue = 0.0
def WriteLonI(self, src, dest): dim = src.GetDimensions() i = vtk.vtkImageData().NewInstance() i.SetDimensions(dim[0],dim[1],1) i.AllocateScalars(vtk.VTK_UNSIGNED_CHAR,3) for x in range(0,dim[0]): for y in range(0,dim[1]): if (src.GetScalarComponentAsDouble(x,y,0,0)==0): for c in range(0,3): i.SetScalarComponentFromDouble(x,y,0,c,dest.GetScalarComponentAsDouble(x,y,0,c)) else: if ( (src.GetScalarComponentAsDouble(x+1,y-1,0,0)==1) and (src.GetScalarComponentAsDouble(x+1,y,0,0)==1) and (src.GetScalarComponentAsDouble(x+1,y+1,0,0)==1) and (src.GetScalarComponentAsDouble(x,y+1,0,0)==1) and (src.GetScalarComponentAsDouble(x,y-1,0,0)==1) and (src.GetScalarComponentAsDouble(x-1,y+1,0,0)==1) and (src.GetScalarComponentAsDouble(x-1,y,0,0)==1) and (src.GetScalarComponentAsDouble(x-1,y-1,0,0)==1)): for c in range(0,3): i.SetScalarComponentFromDouble(x,y,0,c,dest.GetScalarComponentAsDouble(x,y,0,c)) else: i.SetScalarComponentFromDouble(x,y,0,0,0) i.SetScalarComponentFromDouble(x,y,0,1,250) i.SetScalarComponentFromDouble(x,y,0,2,0) i.Modified() return i
def run(self): global vtk_error #----- verify extension ------------------ extension = VerifyDataType(self.filepath) file_name = self.filepath.split(os.path.sep)[-1] n_array = ReadBitmap(self.filepath) if not(isinstance(n_array, numpy.ndarray)): return False image = converters.to_vtk(n_array, spacing=(1,1,1),\ slice_number=1, orientation="AXIAL") dim = image.GetDimensions() x = dim[0] y = dim[1] img = vtk.vtkImageResample() img.SetInputData(image) img.SetAxisMagnificationFactor ( 0, 0.25 ) img.SetAxisMagnificationFactor ( 1, 0.25 ) img.SetAxisMagnificationFactor ( 2, 1 ) img.Update() tp = img.GetOutput().GetScalarTypeAsString() image_copy = vtk.vtkImageData() image_copy.DeepCopy(img.GetOutput()) thumbnail_path = tempfile.mktemp() write_png = vtk.vtkPNGWriter() write_png.SetInputConnection(img.GetOutputPort()) write_png.AddObserver("WarningEvent", VtkErrorPNGWriter) write_png.SetFileName(thumbnail_path) write_png.Write() if vtk_error: img = vtk.vtkImageCast() img.SetInputData(image_copy) img.SetOutputScalarTypeToUnsignedShort() #img.SetClampOverflow(1) img.Update() write_png = vtk.vtkPNGWriter() write_png.SetInputConnection(img.GetOutputPort()) write_png.SetFileName(thumbnail_path) write_png.Write() vtk_error = False id = wx.NewId() bmp_item = [self.filepath, thumbnail_path, extension, x, y,\ str(x) + ' x ' + str(y), file_name, id] self.bmp_file.Add(bmp_item)
def create_volume_node(volume_type, attach_display_node = False, dimensions=None, prefix=''): """ Creates a volume node and inserts it into the MRML tree """ if volume_type not in __VOLUME_TYPES__: raise ValueError('Volume type %s is not valid' % volume_type ) volume_node = eval('slicer.vtkMRML%sVolumeNode()' % volume_type) volume_node.SetName(slicer.mrmlScene.GetUniqueNameByString('%s%s' % (prefix, volume_type))) if dimensions: image_data = vtk.vtkImageData() image_data.SetDimensions(dimensions) if vtk.VTK_MAJOR_VERSION <= 5: image_data.AllocateScalars() else: image_data.AllocateScalars(vtk.VTK_UNSIGNED_INT, 1) volume_node.SetAndObserveImageData(image_data) slicer.mrmlScene.AddNode(volume_node) if attach_display_node: display_node = eval('slicer.vtkMRML%sVolumeDisplayNode()' % volume_type) slicer.mrmlScene.AddNode(display_node) volume_node.AddAndObserveDisplayNodeID( display_node.GetID() ) return volume_node
def dat2mhd(fn): with open("L2_17aug.dat") as fd: D = np.fromfile(file=fd, dtype=np.uint8).reshape((256, 256, 120)).astype("float32") / 255.0 D = np.log(D + 1) from scipy.ndimage.interpolation import zoom D = zoom(D, [1, 1, 256.0 / 120.0]) flat_d = D.transpose(2, 1, 0).flatten() vtk_d_array = ns.numpy_to_vtk(flat_d) image = vtk.vtkImageData() points = image.GetPointData() points.SetScalars(vtk_d_array) image.SetDimensions(D.shape) image.Update() w = vtk.vtkMetaImageWriter() w.SetFileName("bla.hdr") w.SetInput(image) w.Write()
def createMaskfromMesh(self, VOI_mesh, im): """ Takes an image and a VOI_mesh and returns a boolean image with only 1s inside the VOI_mesh """ # Create an Image of Fext white_image = vtk.vtkImageData() white_image.DeepCopy(im) # polygonal data --> image stencil: pol2stenc = vtk.vtkPolyDataToImageStencil() pol2stenc.SetInputData(VOI_mesh) pol2stenc.SetOutputOrigin(im.GetOrigin()) pol2stenc.SetOutputSpacing(im.GetSpacing()) pol2stenc.SetOutputWholeExtent(white_image.GetExtent()) pol2stenc.SetInformationInput(white_image) pol2stenc.Update() # cut the corresponding white image and set the background: imgstenc = vtk.vtkImageStencil() imgstenc.SetInputData(white_image) imgstenc.SetStencilData(pol2stenc.GetOutput()) imgstenc.ReverseStencilOff() imgstenc.SetBackgroundValue(0.0) imgstenc.Update() # write to image dims = im.GetDimensions() scalars = imgstenc.GetOutput().GetPointData().GetScalars() np_scalars = vtk_to_numpy(scalars) np_scalars = np_scalars.reshape(dims[2], dims[1], dims[0]) np_scalars = np_scalars.transpose(2,1,0) return np_scalars
def __init__(self): self.lookupTable = vtk.vtkLookupTable() self.lookupTable.SetRampToLinear() self.lookupTable.SetNumberOfTableValues(2) self.lookupTable.SetTableRange(0, 1) self.lookupTable.SetTableValue(0, 0, 0, 0, 0) self.colorMapper = vtk.vtkImageMapToRGBA() self.colorMapper.SetOutputFormatToRGBA() self.colorMapper.SetLookupTable(self.lookupTable) self.thresholdFilter = vtk.vtkImageThreshold() self.thresholdFilter.SetInValue(1) self.thresholdFilter.SetOutValue(0) self.thresholdFilter.SetOutputScalarTypeToUnsignedChar() # Feedback actor self.mapper = vtk.vtkImageMapper() self.dummyImage = vtk.vtkImageData() self.dummyImage.AllocateScalars(vtk.VTK_UNSIGNED_INT, 1) self.mapper.SetInputData(self.dummyImage) self.actor = vtk.vtkActor2D() self.actor.VisibilityOff() self.actor.SetMapper(self.mapper) self.mapper.SetColorWindow(255) self.mapper.SetColorLevel(128) # Setup pipeline self.colorMapper.SetInputConnection(self.thresholdFilter.GetOutputPort()) self.mapper.SetInputConnection(self.colorMapper.GetOutputPort())
def takeScreenshot(self,name,description,type=-1): # show the message even if not taking a screen shot slicer.util.delayDisplay('Take screenshot: '+description+'.\nResult is available in the Annotations module.', 3000) lm = slicer.app.layoutManager() # switch on the type to get the requested window widget = 0 if type == slicer.qMRMLScreenShotDialog.FullLayout: # full layout widget = lm.viewport() elif type == slicer.qMRMLScreenShotDialog.ThreeD: # just the 3D window widget = lm.threeDWidget(0).threeDView() elif type == slicer.qMRMLScreenShotDialog.Red: # red slice window widget = lm.sliceWidget("Red") elif type == slicer.qMRMLScreenShotDialog.Yellow: # yellow slice window widget = lm.sliceWidget("Yellow") elif type == slicer.qMRMLScreenShotDialog.Green: # green slice window widget = lm.sliceWidget("Green") else: # default to using the full window widget = slicer.util.mainWindow() # reset the type so that the node is set correctly type = slicer.qMRMLScreenShotDialog.FullLayout # grab and convert to vtk image data qimage = ctk.ctkWidgetsUtils.grabWidget(widget) imageData = vtk.vtkImageData() slicer.qMRMLUtils().qImageToVtkImageData(qimage,imageData) annotationLogic = slicer.modules.annotations.logic() annotationLogic.CreateSnapShot(name, description, type, 1, imageData)
def __init__(self, image_handler): self._name = 'Image View' self._view = PythonQt.dd.ddQVTKWidgetView() self._image_handler = image_handler self._image = vtk.vtkImageData() self._prev_attrib = None # Initialize the view. self._view.installImageInteractor() # Add actor. self._image_actor = vtk.vtkImageActor() vtk_SetInputData(self._image_actor, self._image) self._image_actor.SetVisibility(False) self._view.renderer().AddActor(self._image_actor) self._view.orientationMarkerWidget().Off() self._view.backgroundRenderer().SetBackground(0, 0, 0) self._view.backgroundRenderer().SetBackground2(0, 0, 0) self._depth_mapper = None # Add timer. self._render_timer = TimerCallback( targetFps=60, callback=self.render) self._render_timer.start()
def Execute(self): self.PrintLog('Converting Numpy Array to vtkImageData') self.Image = vtk.vtkImageData() self.Image.SetDimensions(self.ArrayDict['Dimensions']) self.Image.SetOrigin(self.ArrayDict['Origin']) self.Image.SetSpacing(self.ArrayDict['Spacing']) self.Image.SetExtent((0, self.ArrayDict['Dimensions'][0] - 1, 0, self.ArrayDict['Dimensions'][1] - 1, 0, self.ArrayDict['Dimensions'][2] - 1,)) self.PrintLog('converting point data') for pointKey in self.ArrayDict['PointData'].keys(): if np.issubdtype(self.ArrayDict['PointData'][pointKey].dtype, np.floating): pointDataArrayType = vtk.VTK_FLOAT else: for checkDt in [int, np.uint8, np.uint16, np.uint32, np.uint64]: if np.issubdtype(self.ArrayDict['PointData'][pointKey].dtype, checkDt): pointDataArrayType = vtk.VTK_INT break else: continue flatArray = self.ArrayDict['PointData'][pointKey].ravel(order='F') pointDataArray = dsa.numpyTovtkDataArray(flatArray, name=pointKey, array_type=pointDataArrayType) self.Image.GetPointData().SetActiveScalars(pointKey) self.Image.GetPointData().SetScalars(pointDataArray)
def sumManualSegmentations(self, manualSegmentationsDirectory, mergedVolume): # Get the manual segmentations and create a single summed image import glob manualSegmentationFilenames = glob.glob(manualSegmentationsDirectory+"/*.mha") # Get the first image which each successive image will be added to reader = vtk.vtkMetaImageReader() reader.SetFileName(manualSegmentationFilenames[0]) reader.Update() summedImage = vtk.vtkImageData() summedImage.SetExtent(reader.GetOutput().GetExtent()) summedImage.AllocateScalars(vtk.VTK_UNSIGNED_CHAR,1) summedImage.ShallowCopy(reader.GetOutput()) # Initialize filter to add images together mathFilter = vtk.vtkImageMathematics() # Iterate list and add each new image for currentFile in manualSegmentationFilenames[1:]: # Get new image reader.SetFileName(currentFile) reader.Update() # Add it to existing summation mathFilter.SetInput1Data(summedImage) mathFilter.SetInput2Data(reader.GetOutput()) mathFilter.Update() # Get new summation summedImage.ShallowCopy(mathFilter.GetOutput()) # Add summed image to slicer scene mergedVolume.SetRASToIJKMatrix(self.rasToIjk) mergedVolume.SetIJKToRASMatrix(self.ijkToRas) mergedVolume.SetAndObserveImageData(summedImage)
def coprocess(time, timeStep, grid, attributes): global coProcessor import vtk from paraview.vtk import vtkPVCatalyst as catalyst import paraview from paraview.vtk.util import numpy_support dataDescription = catalyst.vtkCPDataDescription() dataDescription.SetTimeData(time, timeStep) dataDescription.AddInput("input") if coProcessor.RequestDataDescription(dataDescription): import fedatastructures imageData = vtk.vtkImageData() imageData.SetExtent(grid.XStartPoint, grid.XEndPoint, 0, grid.NumberOfYPoints-1, 0, grid.NumberOfZPoints-1) imageData.SetSpacing(grid.Spacing) velocity = numpy_support.numpy_to_vtk(attributes.Velocity) velocity.SetName("velocity") imageData.GetPointData().AddArray(velocity) pressure = numpy_support.numpy_to_vtk(attributes.Pressure) pressure.SetName("pressure") imageData.GetCellData().AddArray(pressure) dataDescription.GetInputDescriptionByName("input").SetGrid(imageData) dataDescription.GetInputDescriptionByName("input").SetWholeExtent(0, grid.NumberOfGlobalXPoints-1, 0, grid.NumberOfYPoints-1, 0, grid.NumberOfZPoints-1) coProcessor.CoProcess(dataDescription)
def mask_color(image, mask_color): """ Turns a color transparent; assumes that everything else should be the inverse color of mask_color (1-r , 1-b, 1-g) """ from math import floor mask_color = [ floor(255 * component) for component in mask_color] keep_color = [ 255 - component for component in mask_color] # Create an image with an alpha channel image_data = vtkImageData() width, height, _ = image.GetDimensions() image_data = img(width, height) # Consider tracking what the min and max opacities are, and mapping all opacities to that range # Probably hide that behind a KWARG opation; sounds like extra cycles for not a lot of gain. # Copy over the pixels from image for x in range(width): for y in range(height): for component in range(3): pix_component = image.GetScalarComponentAsFloat(x, y, 0, component) # Remap all colors to the keep color; we're using alpha to get rid of the mask color image_data.SetScalarComponentFromFloat(x, y, 0, component, keep_color[component]) # Since the mask color is the inverse of the keep color, we only need one component to figure out the alpha alpha = floor(abs(mask_color[component] - pix_component) / abs(keep_color[component] - mask_color[component]) * 255) alpha = min(alpha, 255) if alpha < 10: # Colors aren't perfect; let's just chop everything off below here, this is basically invisible anyway alpha = 0 if alpha > 245: alpha = 255 image_data.SetScalarComponentFromFloat(x, y, 0, 3, alpha) return image_data
def __init__(self): pypes.pypeScript.__init__(self) self.CubeSource = vtk.vtkCubeSource() self.CubeActor = vtk.vtkActor() self.BoxActive = 0 self.BoxBounds = [0.0, 0.0, 0.0, 0.0, 0.0, 0.0] self.CroppedImage = vtk.vtkImageData() self.vmtkRenderer = None self.OwnRenderer = 0 self.PlaneWidgetX = None self.PlaneWidgetY = None self.PlaneWidgetZ = None self.BoxWidget = None self.Image = None self.Interactive = 1 self.SetScriptName('vmtkimagevoiselector') self.SetScriptDoc('select a cubical volume of interest and get rid of the rest of the image') self.SetInputMembers([ ['Image','i','vtkImageData',1,'','the input image','vmtkimagereader'], ['Interactive','interactive','bool',1,'','toggle interactivity'], ['BoxBounds','boxbounds','float',6,'','bounds of the cubical region of interest'], ['vmtkRenderer','renderer','vmtkRenderer',1,'','external renderer'] ]) self.SetOutputMembers([ ['Image','o','vtkImageData',1,'','the output image','vmtkimagewriter'] ])
def __init__(self,volumeNode): self.volumeNode = volumeNode self.stashImage = vtk.vtkImageData() self.stash = slicer.vtkImageStash() self.stashImage.DeepCopy( volumeNode.GetImageData() ) self.stash.SetStashImage( self.stashImage ) self.stash.ThreadedStash()
assert mbw.GetBlock(1).GetPointData().GetNumberOfArrays() == 0 mbw.PointData.append(na2, 'foo') assert mbw.GetBlock(0).GetPointData().GetNumberOfArrays() == 1 assert mbw.GetBlock(1).GetPointData().GetNumberOfArrays() == 0 assert mbw.GetBlock(0).GetPointData().GetArray(0).GetName() == 'foo' mbw.PointData.append(algs.max(na2), "maxfoo") assert mbw.GetBlock(0).GetPointData().GetNumberOfArrays() == 2 assert mbw.GetBlock(1).GetPointData().GetNumberOfArrays() == 1 assert mbw.GetBlock(0).GetPointData().GetArray(1).GetName() == 'maxfoo' # -------------------------------------- mb = vtk.vtkMultiBlockDataSet() mb.SetBlock(0, vtk.vtkImageData()) mb.SetBlock(1, vtk.vtkImageData()) assert dsa.WrapDataObject(mb).Points is na mb = vtk.vtkMultiBlockDataSet() mb.SetBlock(0, vtk.vtkStructuredGrid()) mb.SetBlock(1, vtk.vtkImageData()) assert dsa.WrapDataObject(mb).Points is na mb = vtk.vtkMultiBlockDataSet() sg = vtk.vtkStructuredGrid() sg.SetPoints(vtk.vtkPoints()) mb.SetBlock(0, sg) mb.SetBlock(1, vtk.vtkImageData()) assert dsa.WrapDataObject(mb).Points.Arrays[0] is not na assert dsa.WrapDataObject(mb).Points.Arrays[1] is na
def text(self, txt, pos=(0,0,0), s=1, c=None, alpha=1, bg=None, font="Theemim", dpi=500, justify="bottom-left", ): """Build an image from a string.""" if c is None: # automatic black or white if vedo.settings.plotter_instance and vedo.settings.plotter_instance.renderer: c = (0.9, 0.9, 0.9) if np.sum(vedo.settings.plotter_instance.renderer.GetBackground()) > 1.5: c = (0.1, 0.1, 0.1) else: c = (0.3, 0.3, 0.3) r = vtk.vtkTextRenderer() img = vtk.vtkImageData() tp = vtk.vtkTextProperty() tp.BoldOff() tp.SetColor(colors.getColor(c)) tp.SetJustificationToLeft() if "top" in justify: tp.SetVerticalJustificationToTop() if "bottom" in justify: tp.SetVerticalJustificationToBottom() if "cent" in justify: tp.SetVerticalJustificationToCentered() tp.SetJustificationToCentered() if "left" in justify: tp.SetJustificationToLeft() if "right" in justify: tp.SetJustificationToRight() if font.lower() == "courier": tp.SetFontFamilyToCourier() elif font.lower() == "times": tp.SetFontFamilyToTimes() elif font.lower() == "arial": tp.SetFontFamilyToArial() else: tp.SetFontFamily(vtk.VTK_FONT_FILE) tp.SetFontFile(utils.getFontPath(font)) if bg: bgcol = colors.getColor(bg) tp.SetBackgroundColor(bgcol) tp.SetBackgroundOpacity(alpha * 0.5) tp.SetFrameColor(bgcol) tp.FrameOn() #GetConstrainedFontSize (const vtkUnicodeString &str, # vtkTextProperty *tprop, int targetWidth, int targetHeight, int dpi) fs = r.GetConstrainedFontSize(txt, tp, 900, 1000, dpi) tp.SetFontSize(fs) r.RenderString(tp, txt, img, [1,1], dpi) # RenderString (vtkTextProperty *tprop, const vtkStdString &str, # vtkImageData *data, int textDims[2], int dpi, int backend=Default) self.SetInputData(img) self.GetMapper().Modified() self.SetPosition(pos) x0, x1 = self.xbounds() if x1 != x0: sc = s/(x1-x0) self.SetScale(sc,sc,sc) return self
def __init__( self, inputobj=None, c='RdBu_r', alpha=(0.0, 0.0, 0.2, 0.4, 0.8, 1.0), alphaGradient=None, alphaUnit=1, mode=0, shade=False, spacing=None, dims=None, origin=None, mapper='smart', ): vtk.vtkVolume.__init__(self) BaseGrid.__init__(self) ################### if isinstance(inputobj, str): if "https://" in inputobj: from vedo.io import download inputobj = download(inputobj, verbose=False) # fpath elif os.path.isfile(inputobj): pass else: inputobj = sorted(glob.glob(inputobj)) ################### if 'gpu' in mapper: self._mapper = vtk.vtkGPUVolumeRayCastMapper() elif 'opengl_gpu' in mapper: self._mapper = vtk.vtkOpenGLGPUVolumeRayCastMapper() elif 'smart' in mapper: self._mapper = vtk.vtkSmartVolumeMapper() elif 'fixed' in mapper: self._mapper = vtk.vtkFixedPointVolumeRayCastMapper() elif isinstance(mapper, vtk.vtkMapper): self._mapper = mapper else: print("Error unknown mapper type", [mapper]) raise RuntimeError() self.SetMapper(self._mapper) ################### inputtype = str(type(inputobj)) #colors.printc('Volume inputtype', inputtype) if inputobj is None: img = vtk.vtkImageData() elif utils.isSequence(inputobj): if isinstance(inputobj[0], str): # scan sequence of BMP files ima = vtk.vtkImageAppend() ima.SetAppendAxis(2) pb = utils.ProgressBar(0, len(inputobj)) for i in pb.range(): f = inputobj[i] picr = vtk.vtkBMPReader() picr.SetFileName(f) picr.Update() mgf = vtk.vtkImageMagnitude() mgf.SetInputData(picr.GetOutput()) mgf.Update() ima.AddInputData(mgf.GetOutput()) pb.print('loading...') ima.Update() img = ima.GetOutput() else: if "ndarray" not in inputtype: inputobj = np.array(inputobj) if len(inputobj.shape) == 1: varr = numpy_to_vtk(inputobj, deep=True, array_type=vtk.VTK_FLOAT) else: if len(inputobj.shape) > 2: inputobj = np.transpose(inputobj, axes=[2, 1, 0]) varr = numpy_to_vtk(inputobj.ravel(order='F'), deep=True, array_type=vtk.VTK_FLOAT) varr.SetName('input_scalars') img = vtk.vtkImageData() if dims is not None: img.SetDimensions(dims) else: if len(inputobj.shape) == 1: colors.printc( "Error: must set dimensions (dims keyword) in Volume.", c='r') raise RuntimeError() img.SetDimensions(inputobj.shape) img.GetPointData().SetScalars(varr) #to convert rgb to numpy # img_scalar = data.GetPointData().GetScalars() # dims = data.GetDimensions() # n_comp = img_scalar.GetNumberOfComponents() # temp = numpy_support.vtk_to_numpy(img_scalar) # numpy_data = temp.reshape(dims[1],dims[0],n_comp) # numpy_data = numpy_data.transpose(0,1,2) # numpy_data = np.flipud(numpy_data) elif "ImageData" in inputtype: img = inputobj elif isinstance(inputobj, Volume): img = inputobj.inputdata() elif "UniformGrid" in inputtype: img = inputobj elif hasattr( inputobj, "GetOutput"): # passing vtk object, try extract imagdedata if hasattr(inputobj, "Update"): inputobj.Update() img = inputobj.GetOutput() elif isinstance(inputobj, str): from vedo.io import loadImageData, download if "https://" in inputobj: inputobj = download(inputobj, verbose=False) img = loadImageData(inputobj) else: colors.printc("Volume(): cannot understand input type:\n", inputtype, c='r') return if dims is not None: img.SetDimensions(dims) if origin is not None: img.SetOrigin(origin) ### DIFFERENT from volume.origin()! if spacing is not None: img.SetSpacing(spacing) self._data = img self._mapper.SetInputData(img) self.mode(mode).color(c).alpha(alpha).alphaGradient(alphaGradient) self.GetProperty().SetShade(True) self.GetProperty().SetInterpolationType(1) self.GetProperty().SetScalarOpacityUnitDistance(alphaUnit) # remember stuff: self._mode = mode self._color = c self._alpha = alpha self._alphaGrad = alphaGradient self._alphaUnit = alphaUnit
def CreateImageData(self, filelist, zspacing, size, bits): message = _("Generating multiplanar visualization...") if not const.VTK_WARNING: log_path = os.path.join(const.USER_LOG_DIR, 'vtkoutput.txt') fow = vtk.vtkFileOutputWindow() fow.SetFileName(log_path) ow = vtk.vtkOutputWindow() ow.SetInstance(fow) x,y = size px, py = utils.predict_memory(len(filelist), x, y, bits) utils.debug("Image Resized to >>> %f x %f" % (px, py)) if (x == px) and (y == py): const.REDUCE_IMAGEDATA_QUALITY = 0 else: const.REDUCE_IMAGEDATA_QUALITY = 1 if not(const.REDUCE_IMAGEDATA_QUALITY): update_progress= vtk_utils.ShowProgress(1, dialog_type = "ProgressDialog") array = vtk.vtkStringArray() for x in xrange(len(filelist)): if not self.running: return False array.InsertValue(x,filelist[x]) if not self.running: return False reader = vtkgdcm.vtkGDCMImageReader() reader.SetFileNames(array) reader.AddObserver("ProgressEvent", lambda obj,evt: update_progress(reader,message)) reader.Update() if not self.running: reader.AbortExecuteOn() return False # The zpacing is a DicomGroup property, so we need to set it imagedata = vtk.vtkImageData() imagedata.DeepCopy(reader.GetOutput()) spacing = imagedata.GetSpacing() imagedata.SetSpacing(spacing[0], spacing[1], zspacing) else: update_progress= vtk_utils.ShowProgress(2*len(filelist), dialog_type = "ProgressDialog") # Reformat each slice and future append them appender = vtk.vtkImageAppend() appender.SetAppendAxis(2) #Define Stack in Z # Reformat each slice for x in xrange(len(filelist)): # TODO: We need to check this automatically according # to each computer's architecture # If the resolution of the matrix is too large if not self.running: return False reader = vtkgdcm.vtkGDCMImageReader() reader.SetFileName(filelist[x]) reader.AddObserver("ProgressEvent", lambda obj,evt: update_progress(reader,message)) reader.Update() #Resample image in x,y dimension slice_imagedata = ResampleImage2D(reader.GetOutput(), px, py, update_progress) #Stack images in Z axes appender.AddInput(slice_imagedata) #appender.AddObserver("ProgressEvent", lambda obj,evt:update_progress(appender)) appender.Update() # The zpacing is a DicomGroup property, so we need to set it if not self.running: return False imagedata = vtk.vtkImageData() imagedata.DeepCopy(appender.GetOutput()) spacing = imagedata.GetSpacing() imagedata.SetSpacing(spacing[0], spacing[1], zspacing) imagedata.AddObserver("ProgressEvent", lambda obj,evt: update_progress(imagedata,message)) imagedata.Update() return imagedata
def removeIslandsMorphologyDecruft(self, image, foregroundLabel, backgroundLabel, iterations=1): # # make binary mask foregroundLabel->1, backgroundLabel->0 # binThresh = vtk.vtkImageThreshold() binThresh.SetInputData(image) binThresh.ThresholdBetween(foregroundLabel, foregroundLabel) binThresh.SetInValue(1) binThresh.SetOutValue(0) binThresh.Update() # # first, erode iterations number of times # eroder = slicer.vtkImageErode() eroderImage = vtk.vtkImageData() eroderImage.DeepCopy(binThresh.GetOutput()) eroder.SetInputData(eroderImage) for iteration in range(iterations): eroder.SetForeground(1) eroder.SetBackground(0) eroder.SetNeighborTo8() eroder.Update() eroderImage.DeepCopy(eroder.GetOutput()) # # now save only islands bigger than a specified size # # note that island operation happens in unsigned long space # but the slicer editor works in Short castIn = vtk.vtkImageCast() castIn.SetInputConnection(eroder.GetInputConnection(0, 0)) castIn.SetOutputScalarTypeToUnsignedLong() # now identify the islands in the inverted volume # and find the pixel that corresponds to the background islandMath = vtkITK.vtkITKIslandMath() islandMath.SetInputConnection(castIn.GetOutputPort()) islandMath.SetFullyConnected(self.fullyConnected) islandMath.SetMinimumSize(self.minimumSize) # note that island operation happens in unsigned long space # but the slicer editor works in Short castOut = vtk.vtkImageCast() castOut.SetInputConnection(islandMath.GetOutputPort()) castOut.SetOutputScalarTypeToShort() castOut.Update() islandCount = islandMath.GetNumberOfIslands() islandOrigCount = islandMath.GetOriginalNumberOfIslands() ignoredIslands = islandOrigCount - islandCount print("%d islands created (%d ignored)" % (islandCount, ignoredIslands)) # # now map everything back to 0 and 1 # thresh = vtk.vtkImageThreshold() thresh.SetInputConnection(castOut.GetOutputPort()) thresh.ThresholdByUpper(1) thresh.SetInValue(1) thresh.SetOutValue(0) thresh.Update() # # now, dilate back (erode background) iterations_plus_one number of times # dilater = slicer.vtkImageErode() dilaterImage = vtk.vtkImageData() dilaterImage.DeepCopy(thresh.GetOutput()) dilater.SetInputData(dilaterImage) for iteration in range(1 + iterations): dilater.SetForeground(0) dilater.SetBackground(1) dilater.SetNeighborTo8() dilater.Update() dilaterImage.DeepCopy(dilater.GetOutput()) # # only keep pixels in both original and dilated result # logic = vtk.vtkImageLogic() logic.SetInputConnection(0, dilater.GetInputConnection(0, 0)) logic.SetInputConnection(1, binThresh.GetOutputPort()) #if foregroundLabel == 0: # logic.SetOperationToNand() #else: logic.SetOperationToAnd() logic.SetOutputTrueValue(1) logic.Update() # # convert from binary mask to 1->foregroundLabel, 0->backgroundLabel # unbinThresh = vtk.vtkImageThreshold() unbinThresh.SetInputConnection(logic.GetOutputPort()) unbinThresh.ThresholdBetween(1, 1) unbinThresh.SetInValue(foregroundLabel) unbinThresh.SetOutValue(backgroundLabel) unbinThresh.Update() image.DeepCopy(unbinThresh.GetOutput())
pl3d.SetXYZFileName(VTK_DATA_ROOT + "/Data/combxyz.bin") pl3d.SetQFileName(VTK_DATA_ROOT + "/Data/combq.bin") pl3d.SetScalarFunctionNumber(100) pl3d.SetVectorFunctionNumber(202) pl3d.Update() output = pl3d.GetOutput().GetBlock(0) plane = vtk.vtkExtractGrid() plane.SetInputData(output) plane.SetVOI(0, 57, 0, 33, 0, 0) plane.Update() # Create some data to use for the (image) blanking # blankImage = vtk.vtkImageData() # vtkType.h has definitions for vtk datatypes VTK_INT, VTK_FLOAT, etc. that # don't get wrapped in Python. VTK_UNSIGNED_CHAR = 3 blankImage.SetDimensions(57, 33, 1) blankImage.AllocateScalars(VTK_UNSIGNED_CHAR, 1) blankImage.GetPointData().GetScalars().SetName("blankScalars") blanking = blankImage.GetPointData().GetScalars() numBlanks = 57 * 33 i = 0 while i < numBlanks: blanking.SetComponent(i, 0, vtk.vtkDataSetAttributes.HIDDENPOINT) i += 1
import nibabel as nib import vtk import numpy as np fold = './' img1 = nib.load(fold + 'image_lr.nii.gz') # load and save img1_data = img1.get_data() #获取标量场数据 dims = img1.shape #数据场维度 spacing = (img1.header['pixdim'][1], img1.header['pixdim'][2], img1.header['pixdim'][3]) image = vtk.vtkImageData() #生成vtkImageData对象 image.SetDimensions(dims[0], dims[1], dims[2]) #设置vtkImageData对象的维度 image.SetSpacing(spacing[0], spacing[1], spacing[2]) #设置间隔 image.SetOrigin(0, 0, 0) image.SetExtent(0, dims[0] - 1, 0, dims[1] - 1, 0, dims[2] - 1) if vtk.VTK_MAJOR_VERSION <= 5: image.SetNumberOfScalarComponents(1) #vtkImageData sclalarArray tuple'size image.SetScalarTypeToShort() else: image.AllocateScalars(vtk.VTK_SHORT, 1) # intRange = (-100, 900) max_u_short = 1000 for z in range(dims[2]): for y in range(dims[1]):
def read_vtk_2d(name): gridreader = vtk.vtkXMLStructuredGridReader() gridreader.SetFileName(name) #gridreader.SetPointArrayStatus("Density",0) selection=gridreader.GetPointDataArraySelection() selection.DisableArray("Density") #selection.DisableArray("Velocity") #selection.DisableArray("Phase") gridreader.Update() grid = gridreader.GetOutput() data = grid.GetPointData() points=grid.GetPoints() dims =grid.GetDimensions() data.SetActiveScalars("Phase"); data.SetActiveVectors("Velocity") velocity=data.GetArray("Velocity") phase = data.GetArray("Phase") image=vtk.vtkImageData() image.SetSpacing(1.0,1.0,1.0) image.SetOrigin(0.0,0.0,0.0) image.SetDimensions(dims[0],dims[1],dims[2]) image.GetPointData().SetScalars(phase) image.GetPointData().SetVectors(velocity) image.Update() print "image=",image extract=vtk.vtkExtractVOI() extract.SetInput(image) extract.SetVOI(0,0,0,dims[1]-1,0,dims[2]-1) extract.Update() contour=vtk.vtkContourFilter() contour.SetInputConnection(extract.GetOutputPort()) contour.SetValue(0,0.0) contour.Update() probe=vtk.vtkProbeFilter() probe.SetInputConnection(contour.GetOutputPort()) probe.SetSource(image) #probe.SpatialMatchOn() probe.Update() print "Probe=",probe.GetOutput() cont=probe.GetOutput() vel=cont.GetPointData().GetArray("Velocity") phi=cont.GetPointData().GetArray("Phase") cont_points=cont.GetPoints() x_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) y_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) z_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) velx_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) vely_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) velz_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) phi_numpy=numpy.zeros(cont_points.GetNumberOfPoints()) for counter in range(0,cont.GetPoints().GetNumberOfPoints()): x,y,z=cont_points.GetPoint(counter) x_numpy[counter]=x y_numpy[counter]=y z_numpy[counter]=z velx_numpy[counter]=vel.GetTuple3(counter)[0] vely_numpy[counter]=vel.GetTuple3(counter)[1] velz_numpy[counter]=vel.GetTuple3(counter)[2] phi_numpy[counter]=phi.GetTuple1(counter) #Velocity of the interface vz=numpy.zeros([dims[1],dims[2]]) vy=numpy.zeros([dims[1],dims[2]]) vx=numpy.zeros([dims[1],dims[2]]) phase_numpy=numpy.zeros([dims[1],dims[2]]) print vz.shape print vy.shape for coory in range(0,dims[1]): for coorz in range(0,dims[2]): counter=coorz*dims[0]*dims[1]+coory*dims[0] velx,vely,velz=velocity.GetTuple3(counter) vz[coory,coorz]=velz vy[coory,coorz]=vely vx[coory,coorz]=velx phase_numpy[coory,coorz]=phase.GetTuple1(counter) center=phase_numpy[0,:] z1 = numpy.min(numpy.where(center < 0.0)) z2 = numpy.max(numpy.where(center < 0.0)) if z1==0: z2=numpy.min(numpy.where(center>0.0))+dims[2] z1=numpy.max(numpy.where(center>0.0)) print z1,z2 mid =((z1+z2)/2)%dims[2] print vz[0,z2%dims[2]] print vz[0,((z1+z2)/2)%dims[2]] y_numpy=y_numpy/50.0 z_numpy=z_numpy/50.0 fig=pylab.figure(figsize=(10,3)) pylab.plot(z_numpy,y_numpy,"o",markersize=5,color="black") pylab.ylim(ymax=1.0) #pylab.xlim(xmin=0.1,xmax=5) #pylab.ylim(ymin=0.01) #numpy.savetxt("capillary.dat",zip(capillaries,widths)) pylab.xticks(fontsize=16) pylab.yticks(fontsize=16) pylab.ylabel(r'''$y$''',fontsize=30) pylab.xlabel(r'''$z$''',fontsize=30) fig.subplots_adjust(bottom=0.25) pylab.savefig("velocity_interface_contour.eps",dpi=300) #labels=[r'''$H_{eff}='''+str(value-2)+r'''$''' for value in ny] #leg=pylab.legend(["CPU results","Refined grid","Large body force","Heil","GPU results"],fancybox=True) #legtext = leg.get_texts() # all the text.Text instance in the legend #for text in legtext: # text.set_fontsize(20) #pylab.figure() #pylab.plot(z_numpy,phi_numpy,"g+") #pylab.figure() #pylab.plot(z_numpy,velx_numpy,"+") #pylab.figure() #pylab.plot(z_numpy,vely_numpy,"+") fig=pylab.figure(figsize=(10,3)) pylab.plot(z_numpy,velz_numpy,"o",markersize=5,color="black") #pylab.plot(z_numpy,y_numpy,"o",markersize=5,color="black") #pylab.xlim(xmin=0.1,xmax=5) #pylab.ylim(ymin=0.01) #numpy.savetxt("capillary.dat",zip(capillaries,widths)) pylab.xticks(fontsize=16) pylab.yticks(fontsize=16) pylab.ylabel(r'''$U$''',fontsize=30) pylab.xlabel(r'''$z$''',fontsize=30) fig.subplots_adjust(bottom=0.25) pylab.savefig("velocity_interface_values.eps",dpi=300)
def __init__(self, arr, renderWindow): self.arr = arr # input volume self.renderWindow = renderWindow #output render window from vtk.util import numpy_support as nps # We begin by creating the data we want to render. # For this tutorial, we create a 3D-image containing three overlaping cubes. # This data can of course easily be replaced by data from a medical CT-scan or anything else three dimensional. fmin,fmax = np.min(arr),np.max(arr) def nfv(t): return fmin+t*(fmax - fmin) scalars = nps.numpy_to_vtk(arr.ravel()) scalars.SetName("Scalars") imageData = vtk.vtkImageData() imageData.SetDimensions(arr.shape) #assume 0,0 origin and 1,1 spacing. #__depthImageData.SetSpacing([1,1]) #__depthImageData.SetOrigin([0,0]) imageData.GetPointData().SetScalars(scalars) imageData.SetExtent(0, arr.shape[2]-1, 0, arr.shape[1]-1, 0, arr.shape[0]-1) # The following class is used to store transparencyv-values for later retrival. In our case, we want the value 0 to be # completly opaque whereas the three different cubes are given different transperancy-values to show how it works. alphaChannelFunc = vtk.vtkPiecewiseFunction() alphaChannelFunc.AddPoint(nfv(0.0) , 0.0) alphaChannelFunc.AddPoint(nfv(0.2) , 0.01) alphaChannelFunc.AddPoint(nfv(0.5) , 0.1) alphaChannelFunc.AddPoint(nfv(1.0) , 0.2) # This class stores color data and can create color tables from a few color points. For this demo, we want the three cubes # to be of the colors red green and blue. colorFunc = vtk.vtkColorTransferFunction() colorFunc.AddRGBPoint(nfv(0.01) , 0.0, 0.0, 1.0) colorFunc.AddRGBPoint(nfv(0.5) , 1.0, 1.0, 1.0) colorFunc.AddRGBPoint(nfv(1.0) , 1.0, 0.0, 0.0) # The preavius two classes stored properties. Because we want to apply these properties to the volume we want to render, # we have to store them in a class that stores volume prpoperties. volumeProperty = vtk.vtkVolumeProperty() volumeProperty.SetColor(colorFunc) volumeProperty.ShadeOn() volumeProperty.SetScalarOpacity(alphaChannelFunc) # We can finally create our volume. We also have to specify the data for it, as well as how the data will be rendered. volumeMapper = vtk.vtkOpenGLGPUVolumeRayCastMapper() volumeMapper.SetInputData(imageData) if vtk.VTK_MAJOR_VERSION > 5 else volumeMapper.SetInputConnection(imageData.GetProducerPort()) # The class vtkVolume is used to pair the preaviusly declared volume as well as the properties to be used when rendering that volume. volume = vtk.vtkVolume() volume.SetMapper(volumeMapper) volume.SetProperty(volumeProperty) # Add a bounding box around the dataset bbFilter = vtk.vtkOutlineFilter() bbFilter.SetInputData(imageData) if vtk.VTK_MAJOR_VERSION > 5 else bbFilter.SetInputConnection(imageData.GetProducerPort()) bbMapper = vtk.vtkDataSetMapper() bbMapper.SetInputConnection(bbFilter.GetOutputPort()) bbActor = vtk.vtkActor() bbActor.GetProperty().EdgeVisibilityOn() bbActor.GetProperty().SetEdgeColor(1,1,1) bbActor.SetMapper(bbMapper) # add a renderer to the widget self.ren = vtk.vtkRenderer() self.renderWindow.AddRenderer(self.ren) # add a volume and ResetCamera self.ren.AddVolume(volume) self.ren.AddActor(bbActor) self.ren.ResetCamera() #prepare interactor istyle = vtk.vtkInteractorStyleTrackballCamera() self.iren = self.renderWindow.GetInteractor() self.iren.SetInteractorStyle(istyle) self.iren.Initialize() self.imageData = imageData self.volumeMapper = volumeMapper
def __vtu2mhd__(vtp, spacing=[1.0, 1.0, 1.0]): from math import ceil bounds = [0.0] * 6 vtp.GetBounds(bounds) #print bounds whiteImage = vtk.vtkImageData() whiteImage.SetSpacing(spacing) ## compute dimensions dim = [0.0, 0.0, 0.0] for i in range(3): #print (bounds[i * 2 + 1] - bounds[i * 2])/ spacing[i] dim[i] = ceil((bounds[i * 2 + 1] - bounds[i * 2]) / spacing[i]) print dim whiteImage.SetDimensions(dim) whiteImage.SetExtent(0, dim[0] - 1, 0, dim[1] - 1, 0, dim[2] - 1) origin = [0.0, 0.0, 0.0] origin[0] = bounds[0] + spacing[0] / 2 origin[1] = bounds[2] + spacing[1] / 2 origin[2] = bounds[4] + spacing[2] / 2 whiteImage.SetOrigin(origin) if vtk.VTK_MAJOR_VERSION <= 5: whiteImage.SetScalarTypeToUnsignedChar() whiteImage.AllocateScalars() else: whiteImage.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, 1) ## Fill the image with foreground voxels: inval = 255 outval = 0 count = whiteImage.GetNumberOfPoints() for i in range(count): whiteImage.GetPointData().GetScalars().SetTuple1(i, inval) ## Polygonal data --> image stencil: pol2stenc = vtk.vtkPolyDataToImageStencil() if vtk.VTK_MAJOR_VERSION <= 5: pol2stenc.SetInput(vtp) else: pol2stenc.SetInputData(vtp) pol2stenc.SetOutputOrigin(origin) pol2stenc.SetOutputSpacing(spacing) pol2stenc.SetOutputWholeExtent(whiteImage.GetExtent()) pol2stenc.Update() ## Cut the corresponding white image and set the background: imgstenc = vtk.vtkImageStencil() if vtk.VTK_MAJOR_VERSION <= 5: imgstenc.SetInput(whiteImage) imgstenc.SetStencil(pol2stenc.GetOutput()) else: imgstenc.SetInputData(whiteImage) imgstenc.SetStencilConnection(pol2stenc.GetOutputPort()) imgstenc.ReverseStencilOff() imgstenc.SetBackgroundValue(outval) imgstenc.Update() return pol2stenc
def readPVGPGrid(headerfile, pdo=None, path=None): """ Description ----------- Generates vtkImageData from the uniform grid defined in the PVGP uniformly gridded data format. Parameters ---------- `headerfile` : str - The file name / absolute path for the input header file that cotains all parameters and pointers to file locations. `pdo` : vtk.vtkImageData, optional - A pointer to the output data object. `path` : str, optional - The absolute path to the PVGP grid database to override the path in the header file. Returns ------- Returns vtkImageData """ if pdo is None: pdo = vtk.vtkImageData() # vtkImageData # Read and parse header file with open(headerfile, 'r') as f: lib = json.load(f) basename = lib['basename'] extent = lib['extent'] spacing = lib['spacing'] origin = lib['origin'] order = lib['order'] endian = lib['endian'] numArrays = lib['numArrays'] dataArrays = lib['dataArrays'] if path is None: path = lib['originalPath'] # Grab Parameters n1, n2, n3 = extent ox, oy, oz = origin sx, sy, sz = spacing # Setup vtkImageData pdo.SetDimensions(n1, n2, n3) pdo.SetExtent(0,n1-1, 0,n2-1, 0,n3-1) pdo.SetOrigin(ox, oy, oz) pdo.SetSpacing(sx, sy, sz) # Read in data arrays dataArrs = [] dataNames = [] vtktypes = [] for darr in dataArrays: dataNames.append(darr) dtype, sdtype, num_bytes, vtktype = _getdtypes(dataArrays[darr]['dtype']) vtktypes.append(vtktype) # Grab and decode data array encoded = base64.b64decode(dataArrays[darr]['data']) raw = struct.unpack(endian+str(n1*n2*n3)+sdtype, encoded) dataArrs.append(np.asarray(raw, dtype=dtype)) """TODO: if order is not 'F': # Reshape the arrays arr = np.reshape(arr, (n1,n2,n3), order=order).flatten(order='C')""" # vtk data arrays for i in range(numArrays): arr = dataArrs[i] VTK_data = nps.numpy_to_vtk(num_array=arr, deep=True, array_type=vtktypes[i]) VTK_data.SetName(dataNames[i]) pdo.GetPointData().AddArray(VTK_data) return pdo
def convert_to_phys(data, filename="test.vti", cfg=None, drho=1, dx=1, dt=1, visc=-1.0 / 12.0, verbose=False): ''' Convert to physical unit, geometry (and values) :param cfg: geometry config ( json) :param data: file from sailfish simulation ''' if drho == 1 and dx == 1 and dt == 1: convert_fields = False else: convert_fields = True writer = vtk.vtkXMLImageDataWriter() writer.SetFileName(filename) grid = vtk.vtkImageData() if cfg: gx, gy, gz = reversed(cfg['size']) origin, spacing = get_minmax4voxel(cfg, lattice=True, get_origin_spacing=True) else: gx, gy, gz = reversed(data['rho'].shape) origin = (0, 0, 0) spacing = (1, 1, 1) grid.SetDimensions(gx, gy, gz) grid.SetOrigin(*origin) grid.SetSpacing(*spacing) pd = grid.GetPointData() phys_name = dict() if hasattr(data, 'files'): for _name in data.files: field = data[_name] if convert_fields: if _name == 'rho': phys_name[_name] = 'p [Pa]' field *= 1.0 / 3.0 * drho * (dx / dt)**2 elif _name == 'v': phys_name[_name] = 'v [m/s]' field *= (dx / dt) elif _name.startswith('stress_'): phys_name[_name] = _name + " [Pa]" field *= -6 * visc / (1 + 6 * visc) * drho * (dx / dt)**2 else: phys_name[_name] = _name else: phys_name[_name] = _name if verbose: print("processing:", _name, phys_name[_name], end='') if len(data[_name].shape) == 3: if verbose: print(" scalar field:", data[_name].shape, end='') pd.AddArray(prepare_vtk_data(phys_name[_name], 1, field)) elif len(data[_name].shape) == 4: assert (data[_name].shape[0] == 3) field = np.rollaxis(field, 0, 4) pd.AddArray(prepare_vtk_data(phys_name[_name], 3, field)) if verbose: print(" vector field:", data[_name].shape, end='') else: if verbose: print(" ignoring field with shape:", data[_name].shape, end='') if verbose: print("... ok") else: if verbose: print( "processing a scalar, no units conv, writing to vtk scalar 's' " ) assert (len(data.shape) == 3) pd.AddArray(prepare_vtk_data("s", 1, data)) if verbose: print("finished") writer.SetInputData(grid) writer.Write()
def _export_data(self): import vtk # collect necessary information from the export box llc = np.array( (self.xminBox.value(), self.yminBox.value(), self.zminBox.value())) urc = np.array( (self.xmaxBox.value(), self.ymaxBox.value(), self.zmaxBox.value())) res = np.array( (self.xResBox.value(), self.yResBox.value(), self.zResBox.value())) dx, dy, dz = (urc - llc) / res if any(llc >= urc): self._warn("Bounds of export data are invalid.") return filename, ext = QtWidgets.QFileDialog.getSaveFileName( self, "Set VTK Filename", "tally_data.vti", "VTK Image (.vti)") # check for cancellation if filename == "": return if filename[-4:] != ".vti": filename += ".vti" ### Generate VTK Data ### # create empty array to store our values export_tally_data = self.tallyCheckBox.checkState( ) == QtCore.Qt.Checked if export_tally_data: tally_data = np.zeros(res[::-1], dtype=float) # create empty arrays for other model properties if requested export_cells = self.geomCheckBox.checkState() == QtCore.Qt.Checked if export_cells: cells = np.zeros(res[::-1], dtype='int32') export_materials = self.matsCheckBox.checkState() == QtCore.Qt.Checked if export_materials: mats = np.zeros(res[::-1], dtype='int32') export_temperatures = self.tempCheckBox.checkState( ) == QtCore.Qt.Checked if export_temperatures: temps = np.zeros(res[::-1], dtype='float') export_densities = self.densityCheckBox.checkState( ) == QtCore.Qt.Checked if export_densities: rhos = np.zeros(res[::-1], dtype='float') # get a copy of the current view view = copy.deepcopy(self.model.currentView) # adjust view settings to match those set in the export dialog x0, y0, z0 = (llc + urc) / 2.0 view.width = urc[0] - llc[0] view.height = urc[1] - llc[1] view.h_res = res[0] view.v_res = res[1] view.tallyDataVisible = True z0 = llc[2] + dz / 2.0 # progress bar to make sure the user knows something is happening # large mesh tallies could take a long time to export progressBar = QtWidgets.QProgressDialog("Accumulating data...", "Cancel", 0, res[2]) progressBar.setWindowModality(QtCore.Qt.WindowModal) # get a view of the tally data for each x, y slice: for k in range(res[2]): z = z0 + k * dz view.origin = (x0, y0, z) view.basis = 'xy' self.model.activeView = view self.model.makePlot() if export_tally_data: image_data = self.model.create_tally_image(view) tally_data[k] = image_data[0][::-1] if export_cells: cells[k] = self.model.cell_ids[::-1] if export_materials: mats[k] = self.model.mat_ids[::-1] if export_temperatures: temps[k] = self.model.temperatures[::-1] if export_densities: rhos[k] = self.model.densities[::-1] progressBar.setValue(k) if progressBar.wasCanceled(): return vtk_image = vtk.vtkImageData() vtk_image.SetDimensions(res + 1) vtk_image.SetSpacing(dx, dy, dz) vtk_image.SetOrigin(llc) if export_tally_data: # assign tally data to double array vtk_data = vtk.vtkDoubleArray() vtk_data.SetName(self.dataLabelField.text()) vtk_data.SetArray(tally_data, tally_data.size, True) vtk_image.GetCellData().AddArray(vtk_data) if export_cells: cell_data = vtk.vtkIntArray() cell_data.SetName("cells") cell_data.SetArray(cells, cells.size, True) vtk_image.GetCellData().AddArray(cell_data) if export_materials: mat_data = vtk.vtkIntArray() mat_data.SetName("mats") mat_data.SetArray(mats, mats.size, True) vtk_image.GetCellData().AddArray(mat_data) if export_temperatures: temp_data = vtk.vtkDoubleArray() temp_data.SetName("temperature") temp_data.SetArray(temps, temps.size, True) vtk_image.GetCellData().AddArray(temp_data) if export_densities: rho_data = vtk.vtkDoubleArray() rho_data.SetName("density") rho_data.SetArray(rhos, rhos.size, True) vtk_image.GetCellData().AddArray(rho_data) progressBar.setLabel( QtWidgets.QLabel("Writing VTK Image file: {}...".format(filename))) writer = vtk.vtkXMLImageDataWriter() writer.SetInputData(vtk_image) writer.SetFileName(filename) writer.Write() progressBar.setLabel(QtWidgets.QLabel("Export complete")) progressBar.setValue(res[2]) msg = QtWidgets.QMessageBox() msg.setText("Export complete!") msg.setIcon(QtWidgets.QMessageBox.Information) msg.setStandardButtons(QtWidgets.QMessageBox.Ok) msg.exec_()
def onApplyButton(self): mvNode = self.outputSelector.currentNode() inputVolume= self.inputSelector.currentNode() """ Run the actual algorithm """ #se obtiene la escena y se obtiene el volumen 4D a partir del Volumen 4D de #entrada de la ventana desplegable escena = slicer.mrmlScene imagenvtk4D = inputVolume.GetImageData() #Se obtiene el número de volúmenes que tiene el volumen 4D numero_imagenes = inputVolume.GetNumberOfFrames() print('imagenes: ' + str(numero_imagenes)) #filtro vtk para descomponer un volumen 4D extract1 = vtk.vtkImageExtractComponents() extract1.SetInputData(imagenvtk4D) #matriz de transformación ras2ijk = vtk.vtkMatrix4x4() ijk2ras = vtk.vtkMatrix4x4() #le solicitamos al volumen original que nos devuelva sus matrices inputVolume.GetRASToIJKMatrix(ras2ijk) inputVolume.GetIJKToRASMatrix(ijk2ras) #creo un volumen nuevo volumenFijo = slicer.vtkMRMLScalarVolumeNode() volumenSalida = slicer.vtkMRMLMultiVolumeNode() #le asigno las transformaciones volumenFijo.SetRASToIJKMatrix(ras2ijk) volumenFijo.SetIJKToRASMatrix(ijk2ras) #le asigno el volumen 3D fijo imagen_fija = extract1.SetComponents(0) extract1.Update() volumenFijo.SetName('fijo') volumenFijo.SetAndObserveImageData(extract1.GetOutput()) #anado el nuevo volumen a la escena escena.AddNode(volumenFijo) #se crea un vector para guardar el número del volumen que tenga un #desplazamiento de mas de 4mm en cualquier dirección v=[] #se hace un ciclo for para registrar todos los demás volúmenes del volumen 4D #con el primer volumen que se definió como fijo frameLabelsAttr='' frames = [] volumeLabels = vtk.vtkDoubleArray() volumeLabels.SetNumberOfTuples(numero_imagenes) volumeLabels.SetNumberOfComponents(1) volumeLabels.Allocate(numero_imagenes) for i in range(numero_imagenes): # extraigo la imagen móvil en la posición i+1 ya que el primero es el fijo imagen_movil = extract1.SetComponents(i+1) #Seleccionar un volumen i+1 extract1.Update() #Creo el volumen móvil, y realizo el mismo procedimiento que con el fijo volumenMovil = slicer.vtkMRMLScalarVolumeNode(); volumenMovil.SetRASToIJKMatrix(ras2ijk) volumenMovil.SetIJKToRASMatrix(ijk2ras) volumenMovil.SetAndObserveImageData(extract1.GetOutput()) volumenMovil.SetName('movil '+str(i+1)) escena.AddNode(volumenMovil) #creamos la transformada para alinear los volúmenes transformadaSalida = slicer.vtkMRMLLinearTransformNode() transformadaSalida.SetName('Transformadaderegistro'+str(i+1)) slicer.mrmlScene.AddNode(transformadaSalida) #parámetros para la operación de registro parameters = {} #parameters['InitialTransform'] = transI.GetID() parameters['fixedVolume'] = volumenFijo.GetID() parameters['movingVolume'] = volumenMovil.GetID() parameters['transformType'] = 'Rigid' parameters['outputTransform'] = transformadaSalida.GetID() frames.append(volumenMovil) ## parameters['outputVolume']=volumenSalida.GetID() #Realizo el registro cliNode = slicer.cli.run( slicer.modules.brainsfit,None,parameters,wait_for_completion=True) #obtengo la transformada lineal que se usó en el registro transformada=escena.GetFirstNodeByName('Transformadaderegistro'+str(i+1)) #Obtengo la matriz de la transformada, esta matriz es de dimensiones 4x4 #en la cual estan todos los desplazamientos y rotaciones que se hicieron #en la transformada, a partir de ella se obtienen los volumenes que se #desplazaron mas de 4mm en cualquier direccion frameId = i; volumeLabels.SetComponent(i, 0, frameId) frameLabelsAttr += str(frameId)+',' Matriz=transformada.GetMatrixTransformToParent() LR=Matriz.GetElement(0,3)#dirección izquierda o derecha en la fila 1, columna 4 PA=Matriz.GetElement(1,3)#dirección anterior o posterior en la fila 2, columna 4 IS=Matriz.GetElement(2,3)#dirección inferior o superior en la fila 3, columna 4 #Se mira si el volumen "i" en alguna dirección tuvo un desplazamiento #mayor a 4mm, en caso de ser cierto se guarda en el vector "v" if abs(LR)>4: v.append(i+2) elif abs(PA)>4: v.append(i+2) elif abs(IS)>4: v.append(i+2) print("MovilExtent: "+str(volumenMovil.GetImageData().GetExtent())) ## print("valor de f: "+ str(volumenMovil)) frameLabelsAttr = frameLabelsAttr[:-1] mvImage = vtk.vtkImageData() mvImage.SetExtent(volumenMovil.GetImageData().GetExtent())##Se le asigna la dimensión del miltuvolumen mvImage.AllocateScalars(volumenMovil.GetImageData().GetScalarType(), numero_imagenes)##Se le asigna el tipo y número de cortes al multivolumen mvImageArray = vtk.util.numpy_support.vtk_to_numpy(mvImage.GetPointData().GetScalars())## Se crea la matriz de datos donde va a ir la imagen mat = vtk.vtkMatrix4x4() ##Se hace la conversión y se obtiene la matriz de transformación del nodo volumenMovil.GetRASToIJKMatrix(mat) mvNode.SetRASToIJKMatrix(mat) volumenMovil.GetIJKToRASMatrix(mat) mvNode.SetIJKToRASMatrix(mat) print("frameId: "+str(frameId)) print("# imag: "+str(numero_imagenes)) ## print("Long frame1: "+str(len(frame))) print("Long frames: "+str(len(frames))) ## for frameId in range(numero_imagenes): # TODO: check consistent size and orientation! frame = frames[frameId] frameImage = frame.GetImageData() frameImageArray = vtk.util.numpy_support.vtk_to_numpy(frameImage.GetPointData().GetScalars()) mvImageArray.T[frameId] = frameImageArray ##Se crea el nodo del multivolumen mvDisplayNode = slicer.mrmlScene.CreateNodeByClass('vtkMRMLMultiVolumeDisplayNode') mvDisplayNode.SetScene(slicer.mrmlScene) slicer.mrmlScene.AddNode(mvDisplayNode) mvDisplayNode.SetReferenceCount(mvDisplayNode.GetReferenceCount()-1) mvDisplayNode.SetDefaultColorMap() mvNode.SetAndObserveDisplayNodeID(mvDisplayNode.GetID()) mvNode.SetAndObserveImageData(mvImage) mvNode.SetNumberOfFrames(numero_imagenes) mvNode.SetLabelArray(volumeLabels) mvNode.SetLabelName('na') mvNode.SetAttribute('MultiVolume.FrameLabels',frameLabelsAttr) mvNode.SetAttribute('MultiVolume.NumberOfFrames',str(numero_imagenes)) mvNode.SetAttribute('MultiVolume.FrameIdentifyingDICOMTagName','NA') mvNode.SetAttribute('MultiVolume.FrameIdentifyingDICOMTagUnits','na') mvNode.SetName('MultiVolume Registrado') Helper.SetBgFgVolumes(mvNode.GetID(),None) print('Registro completo') #al terminar el ciclo for con todos los volúmenes registrados se genera una #ventana emergente con un mensaje("Registro completo!") y mostrando los #volúmenes que se desplazaron mas de 4mm qt.QMessageBox.information(slicer.util.mainWindow(),'Slicer Python','Registro completo!\nVolumenes con movimiento mayor a 4mm:\n'+str(v)) return True
def computeVesselnessVolume(self, currentVolumeNode, currentOutputVolumeNode, previewRegionCenterRAS=None, previewRegionSizeVoxel=-1, minimumDiameterMm=0, maximumDiameterMm=25, alpha=0.3, beta=0.3, contrastMeasure=150): logging.debug( "Vesselness filtering started: diameter min={0}, max={1}, alpha={2}, beta={3}, contrastMeasure={4}" .format(minimumDiameterMm, maximumDiameterMm, alpha, beta, contrastMeasure)) if not currentVolumeNode: raise ValueError("Output volume node is invalid") # this image will later hold the inputImage inImage = vtk.vtkImageData() # if we are in previewMode, we have to cut the ROI first for speed if previewRegionSizeVoxel > 0: # we extract the ROI of currentVolumeNode and save it to currentOutputVolumeNode # we work in RAS space imageclipper = vtk.vtkImageConstantPad() imageclipper.SetInputData(currentVolumeNode.GetImageData()) previewRegionCenterIJK = self.getIJKFromRAS( currentVolumeNode, previewRegionCenterRAS) previewRegionRadiusVoxel = int( round(previewRegionSizeVoxel / 2 + 0.5)) imageclipper.SetOutputWholeExtent( previewRegionCenterIJK[0] - previewRegionRadiusVoxel, previewRegionCenterIJK[0] + previewRegionRadiusVoxel, previewRegionCenterIJK[1] - previewRegionRadiusVoxel, previewRegionCenterIJK[1] + previewRegionRadiusVoxel, previewRegionCenterIJK[2] - previewRegionRadiusVoxel, previewRegionCenterIJK[2] + previewRegionRadiusVoxel) imageclipper.Update() currentOutputVolumeNode.SetAndObserveImageData( imageclipper.GetOutput()) currentOutputVolumeNode.CopyOrientation(currentVolumeNode) currentOutputVolumeNode.ShiftImageDataExtentToZeroStart() inImage.DeepCopy(currentOutputVolumeNode.GetImageData()) else: # there was no ROI extraction, so just clone the inputImage inImage.DeepCopy(currentVolumeNode.GetImageData()) currentOutputVolumeNode.CopyOrientation(currentVolumeNode) # temporarily set spacing to allow vesselness computation performed in physical space inImage.SetSpacing(currentVolumeNode.GetSpacing()) # we now compute the vesselness in RAS space, inImage has spacing and origin attached, the diameters are converted to mm # we use RAS space to support anisotropic datasets import vtkvmtkSegmentationPython as vtkvmtkSegmentation cast = vtk.vtkImageCast() cast.SetInputData(inImage) cast.SetOutputScalarTypeToFloat() cast.Update() inImage = cast.GetOutput() discretizationSteps = 5 v = vtkvmtkSegmentation.vtkvmtkVesselnessMeasureImageFilter() v.SetInputData(inImage) v.SetSigmaMin(minimumDiameterMm) v.SetSigmaMax(maximumDiameterMm) v.SetNumberOfSigmaSteps(discretizationSteps) v.SetAlpha(alpha) v.SetBeta(beta) v.SetGamma(contrastMeasure) v.Update() outImage = vtk.vtkImageData() outImage.DeepCopy(v.GetOutput()) outImage.GetPointData().GetScalars().Modified() # restore Slicer-compliant image spacing outImage.SetSpacing(1, 1, 1) # we set the outImage which has spacing 1,1,1. The ijkToRas matrix of the node will take care of that currentOutputVolumeNode.SetAndObserveImageData(outImage) # save which volume node vesselness filterint result was saved to currentVolumeNode.SetAndObserveNodeReferenceID( "Vesselness", currentOutputVolumeNode.GetID()) logging.debug("Vesselness filtering completed")
print("Major Version: ", rug.GetFileMajorVersion()) print("Minor Version: ", rug.GetFileMinorVersion()) print("File Version: ", rug.GetFileVersion()) # Compare the strings and make sure a version difference is published. if not "4.2" in legacyOutStr: print("Bad legacy writer output") sys.exit(1) if not "5.1" in outStr: print("Bad writer output") sys.exit(1) # vtkImageData print("\nI/O vtkStructuredPoints (aka vtkImageData)") img = vtk.vtkImageData() img.SetDimensions(3, 4, 5) img.AllocateScalars(4, 1) #array of shorts num = 3 * 4 * 5 s = img.GetPointData().GetScalars() for i in range(0, num): s.SetValue(i, i) iw = vtk.vtkStructuredPointsWriter() iw.SetInputData(img) iw.SetFileVersion(42) iw.WriteToOutputStringOn() iw.Write() legacyOutStr = iw.GetOutputString() #print(legacyOutStr)
def interpolateToVolume(mesh, kernel='shepard', radius=None, N=None, bounds=None, nullValue=None, dims=(25, 25, 25)): """ Generate a ``Volume`` by interpolating a scalar or vector field which is only known on a scattered set of points or mesh. Available interpolation kernels are: shepard, gaussian, or linear. :param str kernel: interpolation kernel type [shepard] :param float radius: radius of the local search :param list bounds: bounding box of the output Volume object :param list dims: dimensions of the output Volume object :param float nullValue: value to be assigned to invalid points |interpolateVolume| |interpolateVolume.py|_ """ if isinstance(mesh, vtk.vtkPolyData): output = mesh else: output = mesh.polydata() if radius is None and not N: colors.printc( "Error in interpolateToVolume(): please set either radius or N", c='r') raise RuntimeError # Create a probe volume probe = vtk.vtkImageData() probe.SetDimensions(dims) if bounds is None: bounds = output.GetBounds() probe.SetOrigin(bounds[0], bounds[2], bounds[4]) probe.SetSpacing((bounds[1] - bounds[0]) / dims[0], (bounds[3] - bounds[2]) / dims[1], (bounds[5] - bounds[4]) / dims[2]) # if radius is None: # radius = min(bounds[1]-bounds[0], bounds[3]-bounds[2], bounds[5]-bounds[4])/3 locator = vtk.vtkPointLocator() locator.SetDataSet(output) locator.BuildLocator() if kernel == 'shepard': kern = vtk.vtkShepardKernel() kern.SetPowerParameter(2) elif kernel == 'gaussian': kern = vtk.vtkGaussianKernel() elif kernel == 'linear': kern = vtk.vtkLinearKernel() else: print('Error in interpolateToVolume, available kernels are:') print(' [shepard, gaussian, linear]') raise RuntimeError() if radius: kern.SetRadius(radius) interpolator = vtk.vtkPointInterpolator() interpolator.SetInputData(probe) interpolator.SetSourceData(output) interpolator.SetKernel(kern) interpolator.SetLocator(locator) if N: kern.SetNumberOfPoints(N) kern.SetKernelFootprintToNClosest() else: kern.SetRadius(radius) if nullValue is not None: interpolator.SetNullValue(nullValue) else: interpolator.SetNullPointsStrategyToClosestPoint() interpolator.Update() return Volume(interpolator.GetOutput())
img = nib.load('../medical_files/pancreas_001.nii.gz') img_data = img.get_data() img_data_shape = img_data.shape dataImporter = vtk.vtkImageImport() dataImporter.SetDataScalarTypeToShort() data_string = img_data.tostring() dataImporter.SetNumberOfScalarComponents(1) dataImporter.CopyImportVoidPointer(data_string, len(data_string)) dataImporter.SetDataExtent(0, img_data_shape[0] - 1, 0, img_data_shape[1] - 1, 0, img_data_shape[2] - 1) dataImporter.SetWholeExtent(0, img_data_shape[0] - 1, 0, img_data_shape[1] - 1, 0, img_data_shape[2] - 1) dataImporter.Update() temp_data = dataImporter.GetOutput() new_data = vtk.vtkImageData() new_data.DeepCopy(temp_data) #outline outline = vtk.vtkOutlineFilter() outline.SetInputData(new_data) outlineMapper = vtk.vtkPolyDataMapper() outlineMapper.SetInputConnection(outline.GetOutputPort()) outlineActor = vtk.vtkActor() outlineActor.SetMapper(outlineMapper) #Picker picker = vtk.vtkCellPicker() picker.SetTolerance(0.005) #PlaneWidget
actor.GetProperty().SetPointSize(3) else: actor = vtk.vtkActor() actor.SetMapper(poly_mapper) actor.GetProperty().SetLineWidth(1) actor.GetProperty().SetOpacity(1) # ===T1w image of brain in three planes' visualization=== # ---set T1w data to vtkImageData--- n_components = 1 # only support 1 color channel at present T1_file = nib.load('../data/T1w_acpc_dc_restore_brain1.25.nii.gz') T1_data = T1_file.get_data() affine = T1_file.affine vol = np.interp(T1_data, xp=[T1_data.min(), T1_data.max()], fp=[0, 255]) vol = vol.astype(np.int8) im = vtk.vtkImageData() I, J, K = vol.shape im.SetDimensions(I, J, K) voxsz = (1., 1., 1.) im.SetSpacing(voxsz[2], voxsz[0], voxsz[1]) im.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, n_components) vol = np.swapaxes(vol, 0, 2) vol = np.ascontiguousarray(vol) vol = vol.ravel() uchar_array = ns.numpy_to_vtk(vol, deep=0) im.GetPointData().SetScalars(uchar_array) # ---set the transform (identity if none given)--- if affine is None: affine = np.eye(4)
def LevelSetEvolution(self): if self.LevelSetsType == "geodesic": levelSets = vtkvmtk.vtkvmtkGeodesicActiveContourLevelSetImageFilter( ) levelSets.SetFeatureImage(self.FeatureImage) levelSets.SetDerivativeSigma(self.FeatureDerivativeSigma) levelSets.SetAutoGenerateSpeedAdvection(1) levelSets.SetPropagationScaling(self.PropagationScaling) levelSets.SetCurvatureScaling(self.CurvatureScaling) levelSets.SetAdvectionScaling(self.AdvectionScaling) elif self.LevelSetsType == "curves": levelSets = vtkvmtk.vtkvmtkCurvesLevelSetImageFilter() levelSets.SetFeatureImage(self.FeatureImage) levelSets.SetDerivativeSigma(self.FeatureDerivativeSigma) levelSets.SetAutoGenerateSpeedAdvection(1) levelSets.SetPropagationScaling(self.PropagationScaling) levelSets.SetCurvatureScaling(self.CurvatureScaling) levelSets.SetAdvectionScaling(self.AdvectionScaling) elif self.LevelSetsType == "threshold": levelSets = vtkvmtk.vtkvmtkThresholdSegmentationLevelSetImageFilter( ) levelSets.SetFeatureImage(self.Image) queryString = "Please input lower threshold (\'n\' for none): " self.LowerThreshold = self.ThresholdInput(queryString) queryString = "Please input upper threshold (\'n\' for none): " self.UpperThreshold = self.ThresholdInput(queryString) scalarRange = self.Image.GetScalarRange() if self.LowerThreshold != None: levelSets.SetLowerThreshold(self.LowerThreshold) else: levelSets.SetLowerThreshold(scalarRange[0] - 1.0) if self.UpperThreshold != None: levelSets.SetUpperThreshold(self.UpperThreshold) else: levelSets.SetUpperThreshold(scalarRange[1] + 1.0) levelSets.SetEdgeWeight(self.EdgeWeight) levelSets.SetSmoothingIterations(self.SmoothingIterations) levelSets.SetSmoothingTimeStep(self.SmoothingTimeStep) levelSets.SetSmoothingConductance(self.SmoothingConductance) levelSets.SetPropagationScaling(self.PropagationScaling) levelSets.SetCurvatureScaling(self.CurvatureScaling) elif self.LevelSetsType == "laplacian": levelSets = vtkvmtk.vtkvmtkLaplacianSegmentationLevelSetImageFilter( ) levelSets.SetFeatureImage(self.Image) levelSets.SetPropagationScaling(-self.PropagationScaling) levelSets.SetCurvatureScaling(self.CurvatureScaling) else: self.PrintError('Unsupported LevelSetsType') levelSets.SetInputData(self.LevelSetsInput) levelSets.SetNumberOfIterations(self.NumberOfIterations) levelSets.SetIsoSurfaceValue(self.IsoSurfaceValue) levelSets.SetMaximumRMSError(self.MaximumRMSError) levelSets.SetInterpolateSurfaceLocation(1) levelSets.SetUseImageSpacing(1) levelSets.AddObserver("ProgressEvent", self.PrintProgress) levelSets.Update() self.EndProgress() self.LevelSetsOutput = vtk.vtkImageData() self.LevelSetsOutput.DeepCopy(levelSets.GetOutput())
def load(self, loadable): """Load the selection as a MultiVolume, if multivolume attribute is present """ mvNode = '' try: mvNode = loadable.multivolume except AttributeError: return None nFrames = int(mvNode.GetAttribute('MultiVolume.NumberOfFrames')) files = string.split(mvNode.GetAttribute('MultiVolume.FrameFileList'), ',') nFiles = len(files) filesPerFrame = nFiles / nFrames frames = [] baseName = loadable.name loadAsVolumeSequence = hasattr( loadable, 'loadAsVolumeSequence') and loadable.loadAsVolumeSequence if loadAsVolumeSequence: volumeSequenceNode = slicer.mrmlScene.AddNewNodeByClass( "vtkMRMLSequenceNode", slicer.mrmlScene.GenerateUniqueName(baseName)) volumeSequenceNode.SetIndexName("") volumeSequenceNode.SetIndexUnit("") else: mvImage = vtk.vtkImageData() mvImageArray = None scalarVolumePlugin = slicer.modules.dicomPlugins[ 'DICOMScalarVolumePlugin']() instanceUIDs = "" for file in files: uid = slicer.dicomDatabase.fileValue(file, self.tags['instanceUID']) if uid == "": uid = "Unknown" instanceUIDs += uid + " " instanceUIDs = instanceUIDs[:-1] mvNode.SetAttribute("DICOM.instanceUIDs", instanceUIDs) progressbar = slicer.util.createProgressDialog( labelText="Loading " + baseName, value=0, maximum=nFrames, windowModality=qt.Qt.WindowModal) try: # read each frame into scalar volume for frameNumber in range(nFrames): progressbar.value = frameNumber slicer.app.processEvents() if progressbar.wasCanceled: break sNode = slicer.vtkMRMLVolumeArchetypeStorageNode() sNode.ResetFileNameList() frameFileList = files[frameNumber * filesPerFrame:(frameNumber + 1) * filesPerFrame] # sv plugin will sort the filenames by geometric order svLoadables = scalarVolumePlugin.examine([frameFileList]) if len(svLoadables) == 0: raise IOError("volume frame %d is invalid" % frameNumber) frame = scalarVolumePlugin.load(svLoadables[0]) if frame.GetImageData() == None: raise IOError("volume frame %d is invalid" % frameNumber) if loadAsVolumeSequence: # Load into volume sequence # volumeSequenceNode.SetDataNodeAtValue would deep-copy the volume frame. # To avoid memory reallocation, add an empty node and shallow-copy the contents # of the volume frame. # Create an empty volume node in the sequence node proxyVolume = slicer.mrmlScene.AddNewNodeByClass( frame.GetClassName()) indexValue = str(frameNumber) volumeSequenceNode.SetDataNodeAtValue( proxyVolume, indexValue) slicer.mrmlScene.RemoveNode(proxyVolume) # Update the data node shallowCopy = True volumeSequenceNode.UpdateDataNodeAtValue( frame, indexValue, shallowCopy) else: # Load into multi-volume if frameNumber == 0: frameImage = frame.GetImageData() frameExtent = frameImage.GetExtent() frameSize = frameExtent[1] * frameExtent[ 3] * frameExtent[5] mvImage.SetExtent(frameExtent) if vtk.VTK_MAJOR_VERSION <= 5: mvImage.SetNumberOfScalarComponents(nFrames) mvImage.SetScalarType( frame.GetImageData().GetScalarType()) mvImage.AllocateScalars() else: mvImage.AllocateScalars( frame.GetImageData().GetScalarType(), nFrames) mvImageArray = vtk.util.numpy_support.vtk_to_numpy( mvImage.GetPointData().GetScalars()) mvNode.SetScene(slicer.mrmlScene) mat = vtk.vtkMatrix4x4() frame.GetRASToIJKMatrix(mat) mvNode.SetRASToIJKMatrix(mat) frame.GetIJKToRASMatrix(mat) mvNode.SetIJKToRASMatrix(mat) frameImage = frame.GetImageData() frameImageArray = vtk.util.numpy_support.vtk_to_numpy( frameImage.GetPointData().GetScalars()) mvImageArray.T[frameNumber] = frameImageArray # Remove temporary volume node if frame.GetDisplayNode(): slicer.mrmlScene.RemoveNode(frame.GetDisplayNode()) if frame.GetStorageNode(): slicer.mrmlScene.RemoveNode(frame.GetStorageNode()) slicer.mrmlScene.RemoveNode(frame) if loadAsVolumeSequence: # Finalize volume sequence import # For user convenience, add a browser node and show the volume in the slice viewer. # Add browser node sequenceBrowserNode = slicer.mrmlScene.AddNewNodeByClass( 'vtkMRMLSequenceBrowserNode', slicer.mrmlScene.GenerateUniqueName(baseName + " browser")) sequenceBrowserNode.SetAndObserveMasterSequenceNodeID( volumeSequenceNode.GetID()) # If save changes are allowed then proxy nodes are updated using shallow copy, which is much # faster for images. Images are usually not modified, so the risk of accidentally modifying # data in the sequence is low. sequenceBrowserNode.SetSaveChanges(volumeSequenceNode, True) # Show frame number in proxy volume node name sequenceBrowserNode.SetOverwriteProxyName( volumeSequenceNode, True) # Automatically select the volume to display imageProxyVolumeNode = sequenceBrowserNode.GetProxyNode( volumeSequenceNode) appLogic = slicer.app.applicationLogic() selNode = appLogic.GetSelectionNode() selNode.SetReferenceActiveVolumeID( imageProxyVolumeNode.GetID()) appLogic.PropagateVolumeSelection() # Show sequence browser toolbar sequenceBrowserModule = slicer.modules.sequencebrowser if sequenceBrowserModule.autoShowToolBar: sequenceBrowserModule.setToolBarActiveBrowserNode( sequenceBrowserNode) sequenceBrowserModule.setToolBarVisible(True) else: # Finalize multi-volume import mvDisplayNode = slicer.mrmlScene.AddNewNodeByClass( 'vtkMRMLMultiVolumeDisplayNode') mvDisplayNode.SetDefaultColorMap() mvNode.SetAndObserveDisplayNodeID(mvDisplayNode.GetID()) mvNode.SetAndObserveImageData(mvImage) mvNode.SetNumberOfFrames(nFrames) mvNode.SetName(loadable.name) slicer.mrmlScene.AddNode(mvNode) # # automatically select the volume to display # appLogic = slicer.app.applicationLogic() selNode = appLogic.GetSelectionNode() selNode.SetReferenceActiveVolumeID(mvNode.GetID()) appLogic.PropagateVolumeSelection() # file list is no longer needed - remove the attribute mvNode.RemoveAttribute('MultiVolume.FrameFileList') except Exception as e: logging.error("Failed to read a multivolume: {0}".format( e.message)) import traceback traceback.print_exc() mvNode = None finally: progressbar.close() return mvNode
def read_image(self, image_path=None, orientation="axial"): if image_path is None: # self.folder = "/Users/nandana/Downloads/image_ex" #NANDANA PATH image_folder = r"O:\personal\wasil\supervise\dluximon\miu_viewer\image_ex" else: # dicom_seri = os.path.join(image_path, "dicom.seri") # if os.path.exists(dicom_seri): # QIA version of loading self.image_folder = image_path self.load_image_dir(image_folder) ### Temporary to try to change the voxel values image = self.reader.GetOutput() VTK_DATA_ROOT = vtkGetDataRoot() # self.reader2.SetDirectoryName(dicom_dir) # self.reader.SetFilePrefix(VTK_DATA_ROOT + "/Data/headsq/quarter") # UNIX FRIENDLY # self.reader2.SetFilePrefix(VTK_DATA_ROOT + r"\Data\headsq\quarter") # WINDOWS FRIENDLY # self.reader2.SetDataExtent(0, 63, 0, 63, 1, 93) # self.reader2.SetDataSpacing(3.2, 3.2, 1.5) # self.reader2.SetDataOrigin(0.0, 0.0, 0.0) # self.reader2.SetDataScalarTypeToUnsignedShort() # self.reader2.UpdateWholeExtent() # self.reader2.Update() # image_temp = self.reader2.GetOutput() image2 = vtk.vtkImageData() # image2.CopyStructure(image) # image2.ShallowCopy(image_temp) # need this if i make from vtkimagedata image2.ShallowCopy(image) # need this if i make from vtkimagedata image2.SetSpacing(.6, .6, 1) image2.SetExtent(0, 100, 0, 100, 0, 100) # image2.SetOrigin(0, 0, 0) image2.SetDirectionMatrix(image.GetDirectionMatrix()) # hhmmmm extent = image2.GetExtent() imageData = vtk.vtkImageData() imageData.SetDimensions(100, 100, 100) if vtk.VTK_MAJOR_VERSION <= 5: imageData.SetNumberOfScalarComponents(1) imageData.SetScalarTypeToDouble() else: imageData.AllocateScalars(vtk.VTK_DOUBLE, 1) dims = imageData.GetDimensions() # Fill every entry of the image data with "2.0" for z in range(dims[2]): for y in range(dims[1]): for x in range(dims[0]): if image.GetScalarComponentAsDouble(x, y, z, 0) > -100: imageData.SetScalarComponentFromDouble( x, y, z, 0, 1000) else: imageData.SetScalarComponentFromDouble(x, y, z, 0, 0) imageData.SetSpacing(.6, .6, 1) imageData.SetExtent(0, 100, 0, 100, 0, 100) # imageData.SetOrigin(0, 0, 0) imageData.SetDirectionMatrix(image.GetDirectionMatrix()) # hhmmmm self.imageData = imageData self.img_reslice.SetInputData(0, self.imageData) self.img_reslice.SetOutputDimensionality(2) self.img_reslice.SetInterpolationModeToLinear() self.roi_reslice.SetInputData(0, self.reader.GetOutput()) self.roi_reslice.SetOutputDimensionality(2) self.roi_reslice.SetInterpolationModeToLinear() self.window.Render() self.center = self.calculate_center() self.update_view( orientation=orientation) #TODO: it is not update_view anymore if not self.image_loaded: self.interactor_style.AddObserver("MouseWheelForwardEvent", self.scroll_forward_callback) self.interactor_style.AddObserver("MouseWheelBackwardEvent", self.scroll_backward_callback) self.interactor_style.AddObserver("MouseMoveEvent", self.mouse_move_callback) self.interactor_style.AddObserver("KeyPressEvent", self.key_press_callback) self.interactor_style.AddObserver("LeftButtonPressEvent", self.left_press_callback) self.window.AddObserver("ModifiedEvent", self.window_mod_callback) self.image_loaded = True
def ReadITKIO(self): if self.InputFileName == '': self.PrintError('Error: no InputFileName.') reader = vtkvmtk.vtkvmtkITKArchetypeImageSeriesScalarReader() reader.SetArchetype(self.InputFileName) reader.SetOutputScalarTypeToNative() reader.SetDesiredCoordinateOrientationToNative() reader.SetSingleFile(0) reader.Update() self.Image = vtk.vtkImageData() self.Image.DeepCopy(reader.GetOutput()) matrix = reader.GetRasToIjkMatrix() self.RasToIjkMatrixCoefficients = [ matrix.GetElement(0, 0), matrix.GetElement(0, 1), matrix.GetElement(0, 2), matrix.GetElement(0, 3), matrix.GetElement(1, 0), matrix.GetElement(1, 1), matrix.GetElement(1, 2), matrix.GetElement(1, 3), matrix.GetElement(2, 0), matrix.GetElement(2, 1), matrix.GetElement(2, 2), matrix.GetElement(2, 3), matrix.GetElement(3, 0), matrix.GetElement(3, 1), matrix.GetElement(3, 2), matrix.GetElement(3, 3) ] matrix.Invert() origin = [ matrix.GetElement(0, 3), matrix.GetElement(1, 3), matrix.GetElement(2, 3) ] translationToOrigin = [-origin[0], -origin[1], -origin[2]] for i in range(3): direction = [ matrix.GetElement(0, i), matrix.GetElement(1, i), matrix.GetElement(2, i) ] vtk.vtkMath.Normalize(direction) matrix.SetElement(0, i, direction[0]) matrix.SetElement(1, i, direction[1]) matrix.SetElement(2, i, direction[2]) matrix.SetElement(0, 3, 0.0) matrix.SetElement(1, 3, 0.0) matrix.SetElement(2, 3, 0.0) transform = vtk.vtkTransform() transform.PostMultiply() transform.Translate(translationToOrigin) transform.Concatenate(matrix) transform.Translate(origin) matrix = transform.GetMatrix() self.XyzToRasMatrixCoefficients = [ matrix.GetElement(0, 0), matrix.GetElement(0, 1), matrix.GetElement(0, 2), matrix.GetElement(0, 3), matrix.GetElement(1, 0), matrix.GetElement(1, 1), matrix.GetElement(1, 2), matrix.GetElement(1, 3), matrix.GetElement(2, 0), matrix.GetElement(2, 1), matrix.GetElement(2, 2), matrix.GetElement(2, 3), matrix.GetElement(3, 0), matrix.GetElement(3, 1), matrix.GetElement(3, 2), matrix.GetElement(3, 3) ]
def __init__(self, *args, **kwargs): super(PyView2D, self).__init__(*args, **kwargs) self.block_signal = False self.reader = vtkDICOMImageReader() self.reader2 = vtkDICOMImageReader() self.window = self.GetRenderWindow() self.window.BordersOff( ) #attempt to remove imageactor borders, can remove self.center = [0, 0, 0] self.current_image = vtk.vtkImageData() self.viewer_id = "default" self.viewer_setup() # flexible for future self.image_loaded = False self.viewer_initialized = False # self.read_image(image_path=None, orientation="axial") # flexible for future self.window_level = vtkImageMapToWindowLevelColors() self.img = self.map_img() self.roi = self.map_roi() self.px_coord_text_prop = vtkTextProperty() self.px_coord_text_mapper = vtkTextMapper() self.px_coord_text_actor = vtkActor2D() self.world_coord_text_prop = vtkTextProperty() self.world_coord_text_mapper = vtkTextMapper() self.world_coord_text_actor = vtkActor2D() self.usage_text_prop = vtkTextProperty() self.usage_text_mapper = vtkTextMapper() self.usage_text_actor = vtkActor2D() self.renderer = vtkRenderer() # self.add_text() self.renderer.AddActor(self.img) # self.renderer.AddActor(self.roi) # self.renderer.SetBackground(0.2, 0.3, 0.4) # ### Wasil added ### #QVTKRenderWindowInteractor relays Qt events to VTK # self.frame = Qt.QFrame() # do i need this # self.vtkWidget = QVTKRenderWindowInteractor(self.frame) # miu_viewer = PyView2D() # vtkWidget has its own RenderWindow # self.ren = vtk.vtkRenderer() # or # self.ren = miu_viewer.renderer # should have the actors already # self.vtkWidget.GetRenderWindow().AddRenderer(self.renderer) # self.vtkWidget.GetRenderWindow().SetSize(1000, 1000) # miu_viewer.window.Render() # or # self.vtkWidget.GetRenderWindow().Render() ########################## # have vtkRenderWindow # add VTKrenderer # self.window = vtkRenderWindow() self.window.AddRenderer(self.renderer) # # self.window.SetSize(1000, 1000) self.window.SetSize(300, 300) self.interactor_style = vtkInteractorStyleImage() self.interactor_style.SetInteractionModeToImageSlicing() # self.interactor = vtkRenderWindowInteractor() # # self.iren is the interactor (also from RenderWindow) self.interactor = self.GetRenderWindow().GetInteractor() self.interactor.SetInteractorStyle(self.interactor_style) # self.window.SetInteractor(self.interactor) # self.window_level.SetWindow(1000) self.window_level.SetLevel(200) self.window_level.Update() self.window.Render() ### moved this down to after image is loaded # self.interactor_style.AddObserver("MouseWheelForwardEvent", self.scroll_forward_callback) # self.interactor_style.AddObserver("MouseWheelBackwardEvent", self.scroll_backward_callback) # self.interactor_style.AddObserver("MouseMoveEvent", self.mouse_move_callback) # self.interactor_style.AddObserver("KeyPressEvent", self.key_press_callback) # self.interactor_style.AddObserver("LeftButtonPressEvent", self.left_press_callback) # self.window.AddObserver("ModifiedEvent", self.window_mod_callback) self.actions = { "Slicing": 0, "Cursor": 0, "CurrentPos": -1, "LastPos": -1, "DoubleClick": 0 }
def smoothMultipleSegments(self): import vtkSegmentationCorePython as vtkSegmentationCore # Generate merged labelmap of all visible segments segmentationNode = self.scriptedEffect.parameterSetNode( ).GetSegmentationNode() visibleSegmentIds = vtk.vtkStringArray() segmentationNode.GetDisplayNode().GetVisibleSegmentIDs( visibleSegmentIds) if visibleSegmentIds.GetNumberOfValues() == 0: logging.info( "Smoothing operation skipped: there are no visible segments") return mergedImage = slicer.vtkOrientedImageData() if not segmentationNode.GenerateMergedLabelmapForAllSegments( mergedImage, vtkSegmentationCore.vtkSegmentation. EXTENT_UNION_OF_SEGMENTS_PADDED, None, visibleSegmentIds): logging.error( 'Failed to apply smoothing: cannot get list of visible segments' ) return segmentLabelValues = [] # list of [segmentId, labelValue] for i in range(visibleSegmentIds.GetNumberOfValues()): segmentId = visibleSegmentIds.GetValue(i) segmentLabelValues.append([segmentId, i + 1]) # Perform smoothing in voxel space ici = vtk.vtkImageChangeInformation() ici.SetInputData(mergedImage) ici.SetOutputSpacing(1, 1, 1) ici.SetOutputOrigin(0, 0, 0) # Convert labelmap to combined polydata # vtkDiscreteFlyingEdges3D cannot be used here, as in the output of that filter, # each labeled region is completely disconnected from neighboring regions, and # for joint smoothing it is essential for the points to move together. convertToPolyData = vtk.vtkDiscreteMarchingCubes() convertToPolyData.SetInputConnection(ici.GetOutputPort()) convertToPolyData.SetNumberOfContours(len(segmentLabelValues)) contourIndex = 0 for segmentId, labelValue in segmentLabelValues: convertToPolyData.SetValue(contourIndex, labelValue) contourIndex += 1 # Low-pass filtering using Taubin's method smoothingFactor = self.scriptedEffect.doubleParameter( "JointTaubinSmoothingFactor") smoothingIterations = 100 # according to VTK documentation 10-20 iterations could be enough but we use a higher value to reduce chance of shrinking passBand = pow( 10.0, -4.0 * smoothingFactor ) # gives a nice range of 1-0.0001 from a user input of 0-1 smoother = vtk.vtkWindowedSincPolyDataFilter() smoother.SetInputConnection(convertToPolyData.GetOutputPort()) smoother.SetNumberOfIterations(smoothingIterations) smoother.BoundarySmoothingOff() smoother.FeatureEdgeSmoothingOff() smoother.SetFeatureAngle(90.0) smoother.SetPassBand(passBand) smoother.NonManifoldSmoothingOn() smoother.NormalizeCoordinatesOn() # Extract a label threshold = vtk.vtkThreshold() threshold.SetInputConnection(smoother.GetOutputPort()) # Convert to polydata geometryFilter = vtk.vtkGeometryFilter() geometryFilter.SetInputConnection(threshold.GetOutputPort()) # Convert polydata to stencil polyDataToImageStencil = vtk.vtkPolyDataToImageStencil() polyDataToImageStencil.SetInputConnection( geometryFilter.GetOutputPort()) polyDataToImageStencil.SetOutputSpacing(1, 1, 1) polyDataToImageStencil.SetOutputOrigin(0, 0, 0) polyDataToImageStencil.SetOutputWholeExtent(mergedImage.GetExtent()) # Convert stencil to image stencil = vtk.vtkImageStencil() emptyBinaryLabelMap = vtk.vtkImageData() emptyBinaryLabelMap.SetExtent(mergedImage.GetExtent()) emptyBinaryLabelMap.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, 1) vtkSegmentationCore.vtkOrientedImageDataResample.FillImage( emptyBinaryLabelMap, 0) stencil.SetInputData(emptyBinaryLabelMap) stencil.SetStencilConnection(polyDataToImageStencil.GetOutputPort()) stencil.ReverseStencilOn() stencil.SetBackgroundValue( 1 ) # General foreground value is 1 (background value because of reverse stencil) imageToWorldMatrix = vtk.vtkMatrix4x4() mergedImage.GetImageToWorldMatrix(imageToWorldMatrix) for segmentId, labelValue in segmentLabelValues: threshold.ThresholdBetween(labelValue, labelValue) stencil.Update() smoothedBinaryLabelMap = slicer.vtkOrientedImageData() smoothedBinaryLabelMap.ShallowCopy(stencil.GetOutput()) smoothedBinaryLabelMap.SetImageToWorldMatrix(imageToWorldMatrix) # Write results to segments directly, bypassing masking slicer.vtkSlicerSegmentationsModuleLogic.SetBinaryLabelmapToSegment( smoothedBinaryLabelMap, segmentationNode, segmentId, slicer.vtkSlicerSegmentationsModuleLogic.MODE_REPLACE, smoothedBinaryLabelMap.GetExtent())
def straightenVolume(self, outputStraightenedVolume, curveNode, volumeNode, sliceSizeMm, outputSpacingMm, rotationAngleDeg=0.0): """ Compute straightened volume (useful for example for visualization of curved vessels) """ originalCurvePoints = curveNode.GetCurvePointsWorld() sampledPoints = vtk.vtkPoints() if not slicer.vtkMRMLMarkupsCurveNode.ResamplePoints( originalCurvePoints, sampledPoints, outputSpacingMm[2], False): return False sliceExtent = [ int(sliceSizeMm[0] / outputSpacingMm[0]), int(sliceSizeMm[1] / outputSpacingMm[1]) ] inputSpacing = volumeNode.GetSpacing() lines = vtk.vtkCellArray() lines.InsertNextCell(sampledPoints.GetNumberOfPoints()) for pointIndex in range(sampledPoints.GetNumberOfPoints()): lines.InsertCellPoint(pointIndex) sampledCurvePoly = vtk.vtkPolyData() sampledCurvePoly.SetPoints(sampledPoints) sampledCurvePoly.SetLines(lines) #print(sampledPoints.GetPoint(3)) # Get physical coordinates from voxel coordinates volumeRasToIjkTransformMatrix = vtk.vtkMatrix4x4() volumeNode.GetRASToIJKMatrix(volumeRasToIjkTransformMatrix) transformWorldToVolumeRas = vtk.vtkMatrix4x4() slicer.vtkMRMLTransformNode.GetMatrixTransformBetweenNodes( None, volumeNode.GetParentTransformNode(), transformWorldToVolumeRas) transformWorldToIjk = vtk.vtkTransform() transformWorldToIjk.Concatenate(transformWorldToVolumeRas) transformWorldToIjk.Scale(inputSpacing) transformWorldToIjk.Concatenate(volumeRasToIjkTransformMatrix) transformPolydataWorldToIjk = vtk.vtkTransformPolyDataFilter() transformPolydataWorldToIjk.SetInputData(sampledCurvePoly) transformPolydataWorldToIjk.SetTransform(transformWorldToIjk) reslicer = vtk.vtkSplineDrivenImageSlicer() append = vtk.vtkImageAppend() scaledImageData = vtk.vtkImageData() scaledImageData.ShallowCopy(volumeNode.GetImageData()) scaledImageData.SetSpacing(inputSpacing) reslicer.SetInputData(scaledImageData) reslicer.SetPathConnection(transformPolydataWorldToIjk.GetOutputPort()) reslicer.SetSliceExtent(*sliceExtent) reslicer.SetSliceSpacing(outputSpacingMm[0], outputSpacingMm[1]) reslicer.SetIncidence(vtk.vtkMath.RadiansFromDegrees(rotationAngleDeg)) nbPoints = sampledPoints.GetNumberOfPoints() for ptId in reversed(range(nbPoints)): reslicer.SetOffsetPoint(ptId) reslicer.Update() tempSlice = vtk.vtkImageData() tempSlice.DeepCopy(reslicer.GetOutput(0)) append.AddInputData(tempSlice) append.SetAppendAxis(2) append.Update() straightenedVolumeImageData = append.GetOutput() straightenedVolumeImageData.SetOrigin(0, 0, 0) straightenedVolumeImageData.SetSpacing(1.0, 1.0, 1.0) dims = straightenedVolumeImageData.GetDimensions() ijkToRas = vtk.vtkMatrix4x4() ijkToRas.SetElement(0, 0, 0.0) ijkToRas.SetElement(1, 0, 0.0) ijkToRas.SetElement(2, 0, -outputSpacingMm[0]) ijkToRas.SetElement(0, 1, 0.0) ijkToRas.SetElement(1, 1, outputSpacingMm[1]) ijkToRas.SetElement(2, 1, 0.0) ijkToRas.SetElement(0, 2, outputSpacingMm[2]) ijkToRas.SetElement(1, 2, 0.0) ijkToRas.SetElement(2, 2, 0.0) outputStraightenedVolume.SetIJKToRASMatrix(ijkToRas) outputStraightenedVolume.SetAndObserveImageData( straightenedVolumeImageData) outputStraightenedVolume.CreateDefaultDisplayNodes() return True
#------------ FILTER: CALCULATE VECTOR MAGNITUDE ---------------------- magnitudeCalcFilter = vtk.vtkArrayCalculator() magnitudeCalcFilter.SetInputConnection(rectGridReader.GetOutputPort()) magnitudeCalcFilter.Update() #------------END CALCULATE VECTOR MAGNITUDE ---------------------- #------------FILTER: RECTILINEAR GRID TO IMAGE DATA----------- bounds = rectGridReader.GetOutput().GetBounds() dimensions = rectGridReader.GetOutput().GetDimensions() origin = (bounds[0], bounds[2], bounds[4]) spacing = ((bounds[1] - bounds[0]) / dimensions[0], (bounds[3] - bounds[2]) / dimensions[1], (bounds[5] - bounds[4]) / dimensions[2]) imageData = vtk.vtkImageData() imageData.SetOrigin(origin) imageData.SetDimensions(dimensions) imageData.SetSpacing(spacing) probeFilter = vtk.vtkProbeFilter() probeFilter.SetInputData(imageData) probeFilter.SetSourceData(magnitudeCalcFilter.GetOutput()) probeFilter.Update() imageData2 = probeFilter.GetImageDataOutput() #------------END RECTILINEAR GRID TO IMAGE DATA----------- ##------------FILTER, MAPPER, AND ACTOR: VOLUME RENDERING ------------------- # Create transfer mapping scalar value to opacity opacityTransferFunction = vtk.vtkPiecewiseFunction()
if size > 1: if rank == 1: rtData3 = dsa.VTKCompositeDataArray([rtData2]) grad3 = dsa.VTKCompositeDataArray([grad2]) else: rtData3 = dsa.NoneArray grad3 = dsa.NoneArray testArrays(rtData3, rtData2, grad3, grad2, total_npts) # Test composite arrays with multiple blocks. # Split the local image to 2. datasets = [] for i in range(2): image = vtk.vtkImageData() image.ShallowCopy(w.GetOutput()) t = vtk.vtkExtentTranslator() wext = image.GetExtent() t.SetWholeExtent(wext) t.SetPiece(i) t.SetNumberOfPieces(2) t.PieceToExtent() ext = list(t.GetExtent()) # Crop the any ghost points out for i in range(3): if ext[2 * i] != wext[2 * i]: ext[2 * i] = ext[2 * i] + 1 if ext != list(org_ext): image.Crop(ext)
mapper.SetInputConnection(sphereSource.GetOutputPort()) actor = vtk.vtkActor() actor.SetMapper(mapper) # A renderer and render window renderer = vtk.vtkRenderer() renderWindow = vtk.vtkRenderWindow() renderWindow.AddRenderer(renderer) # An interactor renderWindowInteractor = vtk.vtkRenderWindowInteractor() renderWindowInteractor.SetRenderWindow(renderWindow) # Create two images for texture image1 = vtk.vtkImageData() image2 = vtk.vtkImageData() CreateButtonOff(image1) CreateButtonOn(image2) # Create the widget and its representation buttonRepresentation = vtk.vtkTexturedButtonRepresentation2D() buttonRepresentation.SetNumberOfStates(2) buttonRepresentation.SetButtonTexture(0, image1) buttonRepresentation.SetButtonTexture(1, image2) buttonWidget = vtk.vtkButtonWidget() buttonWidget.SetInteractor(renderWindowInteractor) buttonWidget.SetRepresentation(buttonRepresentation)
def polydata_to_volume(polydata): """ Parameters ---------- polydata : vtkPolyData input polydata Returns ------- (numpy arr, 3-tuple, vtkImageData) (volume, origin, imagedata) """ bounds = polydata.GetBounds() spacing = [1., 1., 1.] origin = [ bounds[0] + spacing[0] / 2, bounds[2] + spacing[1] / 2, bounds[4] + spacing[2] / 2 ] whiteImage = vtk.vtkImageData() whiteImage.SetSpacing(spacing) whiteImage.SetOrigin(origin) dim = np.array([ np.ceil(bounds[1] - bounds[0]) / spacing[0], np.ceil(bounds[3] - bounds[2]) / spacing[1], np.ceil(bounds[5] - bounds[4]) / spacing[2] ], np.int) whiteImage.SetDimensions(dim) whiteImage.SetExtent(0, dim[0] - 1, 0, dim[1] - 1, 0, dim[2] - 1) # whiteImage.AllocateScalars(vtk.VTK_UNSIGNED_CHAR, 1) n_pts = whiteImage.GetNumberOfPoints() # t = time.time() # inval = 255 # outval = 0 # for i in range(n_pts): # whiteImage.GetPointData().GetScalars().SetTuple1(i, inval) whiteImage.GetPointData().SetScalars( numpy_support.numpy_to_vtk( 255 * np.ones((n_pts, ), np.uint8), deep=True, array_type=vtk.VTK_UNSIGNED_CHAR)) # deep copy must be true # sys.stderr.write('time 1: %.2f\n' % (time.time() - t) ) # t = time.time() pol2stenc = vtk.vtkPolyDataToImageStencil() pol2stenc.SetInputData(polydata) pol2stenc.SetOutputOrigin(origin) pol2stenc.SetOutputSpacing(spacing) pol2stenc.SetOutputWholeExtent(whiteImage.GetExtent()) pol2stenc.Update() # sys.stderr.write('time 2: %.2f\n' % (time.time() - t) ) # t = time.time() # cut the corresponding white image and set the background: imgstenc = vtk.vtkImageStencil() imgstenc.SetInputData(whiteImage) imgstenc.SetStencilData(pol2stenc.GetOutput()) imgstenc.ReverseStencilOff() imgstenc.SetBackgroundValue(0) imgstenc.Update() # sys.stderr.write('time 3: %.2f\n' % (time.time() - t) ) # t = time.time() im = imgstenc.GetOutput() x, y, z = im.GetDimensions() sc = im.GetPointData().GetScalars() a = numpy_support.vtk_to_numpy(sc) b = a.reshape(z, y, x) b = np.transpose(b, [1, 2, 0]) # sys.stderr.write('time 4: %.2f\n' % (time.time() - t) ) return b, origin, im
def __init__(self, volume, level=None): self._surface_algorithm = None self._renderer = None self._actor = None self._mapper = None self._volume_array = None self._float_array = _vtk.vtkFloatArray() self._image_data = _vtk.vtkImageData() self._image_data.GetPointData().SetScalars(self._float_array) self._setup_data(_numpy.float32(volume)) self._surface_algorithm = _vtk.vtkMarchingCubes() self._surface_algorithm.SetInputData(self._image_data) self._surface_algorithm.ComputeNormalsOn() if level is not None: try: self.set_multiple_levels(iter(level)) except TypeError: self.set_level(0, level) self._mapper = _vtk.vtkPolyDataMapper() self._mapper.SetInputConnection(self._surface_algorithm.GetOutputPort()) self._mapper.ScalarVisibilityOn() # new self._actor = _vtk.vtkActor() self._actor.SetMapper(self._mapper)
def ApplyVED(self): vesselness = vtkvmtk.vtkvmtkVesselEnhancingDiffusionImageFilter() vesselness.SetInputData(self.Image) vesselness.SetSigmaMin(self.SigmaMin) vesselness.SetSigmaMax(self.SigmaMax) vesselness.SetNumberOfSigmaSteps(self.NumberOfSigmaSteps) vesselness.SetAlpha(self.Alpha) vesselness.SetBeta(self.Beta) vesselness.SetGamma(self.Gamma) vesselness.SetC(self.C) vesselness.SetTimeStep(self.TimeStep) vesselness.SetEpsilon(self.Epsilon) vesselness.SetWStrength(self.WStrength) vesselness.SetSensitivity(self.Sensitivity) vesselness.SetNumberOfIterations(self.NumberOfIterations) vesselness.SetNumberOfDiffusionSubIterations(self.NumberOfDiffusionSubIterations) if self.SigmaStepMethod == 'equispaced': vesselness.SetSigmaStepMethodToEquispaced() elif self.SigmaStepMethod == 'logarithmic': vesselness.SetSigmaStepMethodToLogarithmic() vesselness.Update() self.EnhancedImage = vtk.vtkImageData() self.EnhancedImage.DeepCopy(vesselness.GetOutput())