def computeStatistics(self, segmentID): import vtkSegmentationCorePython as vtkSegmentationCore requestedKeys = self.getRequestedKeys() segmentationNode = slicer.mrmlScene.GetNodeByID( self.getParameterNode().GetParameter("Segmentation")) if len(requestedKeys) == 0: return {} containsLabelmapRepresentation = segmentationNode.GetSegmentation( ).ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return {} segmentLabelmap = slicer.vtkOrientedImageData() segmentationNode.GetBinaryLabelmapRepresentation( segmentID, segmentLabelmap) if (not segmentLabelmap or not segmentLabelmap.GetPointData() or not segmentLabelmap.GetPointData().GetScalars()): # No input label data return {} # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x, y: x * y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 stats = {} if "voxel_count" in requestedKeys: stats["voxel_count"] = stat.GetVoxelCount() if "volume_mm3" in requestedKeys: stats["volume_mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel if "volume_cm3" in requestedKeys: stats["volume_cm3"] = stat.GetVoxelCount( ) * cubicMMPerVoxel * ccPerCubicMM return stats
def __init__(self, module_manager): SimpleVTKClassModuleBase.__init__( self, module_manager, vtk.vtkImageToImageStencil(), 'Processing.', ('vtkImageData',), ('vtkImageStencilData',), replaceDoc=True, inputFunctions=None, outputFunctions=None)
def getLabelStats(self, image, roi, labelStats): # instantiate results dictionary labelStats["Image"].append(image.GetName()) # copied/modified from labelstatistics module # determine volume of a voxel and conversion factor to cubed centimeters cubicMMPerVoxel = reduce(lambda x, y: x * y, roi.GetSpacing()) ccPerCubicMM = 0.001 # calculate the min and max of the roi image stataccum = vtk.vtkImageAccumulate() stataccum.SetInputConnection(roi.GetImageDataConnection()) stataccum.Update() lo = int(stataccum.GetMin()[0]) hi = int(stataccum.GetMax()[0]) # iterate through all the labels in the image for i in xrange(lo, hi + 1): # threshold roi image thresholder = vtk.vtkImageThreshold() thresholder.SetInputConnection(roi.GetImageDataConnection()) thresholder.SetInValue(1) thresholder.SetOutValue(0) thresholder.ReplaceOutOn() thresholder.ThresholdBetween(i, i) thresholder.SetOutputScalarType( image.GetImageData().GetScalarType()) thresholder.Update() # use vtk's statistics class with the binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputConnection(thresholder.GetOutputPort()) stencil.ThresholdBetween(1, 1) stat1 = vtk.vtkImageAccumulate() stat1.SetInputConnection(image.GetImageDataConnection()) stencil.Update() stat1.SetStencilData(stencil.GetOutput()) stat1.Update() # gather stats if count is greater than zero if stat1.GetVoxelCount() > 0: # add an entry to the LabelStats list labelStats["Labels"].append(i) labelStats[image.GetName(), i, "Image"] = image.GetName() labelStats[image.GetName(), i, "Index"] = i labelStats[image.GetName(), i, "Count"] = stat1.GetVoxelCount() labelStats[image.GetName(), i, "Volume mm^3"] = labelStats[ image.GetName(), i, "Count"] * cubicMMPerVoxel labelStats[image.GetName(), i, "Volume cc"] = labelStats[ image.GetName(), i, "Volume mm^3"] * ccPerCubicMM labelStats[image.GetName(), i, "Min"] = stat1.GetMin()[0] labelStats[image.GetName(), i, "Max"] = stat1.GetMax()[0] labelStats[image.GetName(), i, "Mean"] = stat1.GetMean()[0] labelStats[image.GetName(), i, "StdDev"] = stat1.GetStandardDeviation()[0] return hi
def __init__(self, module_manager): SimpleVTKClassModuleBase.__init__(self, module_manager, vtk.vtkImageToImageStencil(), 'Processing.', ('vtkImageData', ), ('vtkImageStencilData', ), replaceDoc=True, inputFunctions=None, outputFunctions=None)
def computeStatistics(self, segmentID): import vtkSegmentationCorePython as vtkSegmentationCore requestedKeys = self.getRequestedKeys() segmentationNode = slicer.mrmlScene.GetNodeByID(self.getParameterNode().GetParameter("Segmentation")) if len(requestedKeys)==0: return {} containsLabelmapRepresentation = segmentationNode.GetSegmentation().ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return {} segment = segmentationNode.GetSegmentation().GetSegment(segmentID) segBinaryLabelName = vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName() segmentLabelmap = segment.GetRepresentation(segBinaryLabelName) if (not segmentLabelmap or not segmentLabelmap.GetPointData() or not segmentLabelmap.GetPointData().GetScalars()): # No input label data return {} # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x,y: x*y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 stats = {} if "voxel_count" in requestedKeys: stats["voxel_count"] = stat.GetVoxelCount() if "volume_mm3" in requestedKeys: stats["volume_mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel if "volume_cm3" in requestedKeys: stats["volume_cm3"] = stat.GetVoxelCount() * cubicMMPerVoxel * ccPerCubicMM return stats
def maskVolumeWithSegment(self, segmentationNode, segmentID, operationMode, fillValues, inputVolumeNode, outputVolumeNode): """ Fill voxels of the input volume inside/outside the masking model with the provided fill value """ segmentIDs = vtk.vtkStringArray() segmentIDs.InsertNextValue(segmentID) maskVolumeNode = slicer.modules.volumes.logic().CreateAndAddLabelVolume(inputVolumeNode, "TemporaryVolumeMask") if not maskVolumeNode: logging.error("maskVolumeWithSegment failed: invalid maskVolumeNode") return False if not slicer.vtkSlicerSegmentationsModuleLogic.ExportSegmentsToLabelmapNode(segmentationNode, segmentIDs, maskVolumeNode, inputVolumeNode): logging.error("maskVolumeWithSegment failed: ExportSegmentsToLabelmapNode error") slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode().GetColorNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode) return False maskToStencil = vtk.vtkImageToImageStencil() maskToStencil.ThresholdByLower(0) maskToStencil.SetInputData(maskVolumeNode.GetImageData()) stencil = vtk.vtkImageStencil() if operationMode == "FILL_INSIDE_AND_OUTSIDE": # Set input to constant value thresh = vtk.vtkImageThreshold() thresh.SetInputData(inputVolumeNode.GetImageData()) thresh.ThresholdByLower(0) thresh.SetInValue(fillValues[1]) thresh.SetOutValue(fillValues[1]) thresh.SetOutputScalarType(inputVolumeNode.GetImageData().GetScalarType()) thresh.Update() stencil.SetInputData(thresh.GetOutput()) else: stencil.SetInputData(inputVolumeNode.GetImageData()) stencil.SetStencilConnection(maskToStencil.GetOutputPort()) stencil.SetReverseStencil(operationMode == "FILL_OUTSIDE") stencil.SetBackgroundValue(fillValues[0]) stencil.Update() outputVolumeNode.SetAndObserveImageData(stencil.GetOutput()) # Set the same geometry and parent transform as the input volume ijkToRas = vtk.vtkMatrix4x4() inputVolumeNode.GetIJKToRASMatrix(ijkToRas) outputVolumeNode.SetIJKToRASMatrix(ijkToRas) inputVolumeNode.SetAndObserveTransformNodeID(inputVolumeNode.GetTransformNodeID()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode().GetColorNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode) return True
def addSegmentLabelmapStatistics(self): import vtkSegmentationCorePython as vtkSegmentationCore containsLabelmapRepresentation = self.segmentationNode.GetSegmentation( ).ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return for segmentID in self.statistics["SegmentIDs"]: segment = self.segmentationNode.GetSegmentation().GetSegment( segmentID) segmentLabelmap = segment.GetRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x, y: x * y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 self.statistics[segmentID, "LM voxel count"] = stat.GetVoxelCount() self.statistics[ segmentID, "LM volume mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel self.statistics[segmentID, "LM volume cc"] = stat.GetVoxelCount( ) * cubicMMPerVoxel * ccPerCubicMM
def AddSegmentNode(self, modelNode, volumeLabel): #This function creates a segmentation from the output model (ie cropped breast models) # and computed the volume of the segmentation, this is done to ensure the volume is computed correctly segmentationNode = slicer.vtkMRMLSegmentationNode() slicer.mrmlScene.AddNode(segmentationNode) displayNode = slicer.mrmlScene.GetNthNodeByClass(1, 'vtkMRMLScalarVolumeDisplayNode') if displayNode == None: displayNode = slicer.vtkMRMLScalarVolumeDisplayNode() segmentationNode.SetAndObserveDisplayNodeID(displayNode.GetID()) segmentationNode.SetName("Model Segmentation Node") slicer.modules.segmentations.logic().ImportModelToSegmentationNode(modelNode, segmentationNode) segment = segmentationNode.GetSegmentation().GetNthSegment(0) segBinaryLabelName = vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName() segmentLabelmap = segment.GetRepresentation(segBinaryLabelName) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x, y: x * y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 stats = {} volume = round(stat.GetVoxelCount() * cubicMMPerVoxel * ccPerCubicMM, 0) volumeLabel.setText(volume) slicer.mrmlScene.RemoveNode(segmentationNode) return volume
def mean(self, inputVolume, ROIVolume): "Executa a calculo da media dos volumes com a ROI" logging.info('Processing mean: ' + inputVolume.GetName()) if not self.isValidInputOutputData(inputVolume, ROIVolume): slicer.util.errorDisplay( 'Mean: Input volume is the same as output volume. Choose a different output volume.' ) return False stataccum = vtk.vtkImageAccumulate() stataccum.SetInputConnection(ROIVolume.GetImageDataConnection()) stataccum.Update() lo = int(stataccum.GetMin()[0]) hi = int(stataccum.GetMax()[0]) a = slicer.util.array(ROIVolume.GetName()) print a.max() labelValue = a.max() # Create the binary volume of the label thresholder = vtk.vtkImageThreshold() thresholder.SetInputConnection(ROIVolume.GetImageDataConnection()) thresholder.SetInValue(1) thresholder.SetOutValue(0) thresholder.ReplaceOutOn() thresholder.ThresholdBetween(labelValue, labelValue) thresholder.SetOutputScalarType( inputVolume.GetImageData().GetScalarType()) thresholder.Update() # use vtk's statistics class with the binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputConnection(thresholder.GetOutputPort()) stencil.ThresholdBetween(1, 1) stat1 = vtk.vtkImageAccumulate() stat1.SetInputConnection(inputVolume.GetImageDataConnection()) stencil.Update() stat1.SetStencilData(stencil.GetOutput()) stat1.Update() return stat1.GetMean()[0]
def addSegmentLabelmapStatistics(self): import vtkSegmentationCorePython as vtkSegmentationCore containsLabelmapRepresentation = self.segmentationNode.GetSegmentation().ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return for segmentID in self.statistics["SegmentIDs"]: segment = self.segmentationNode.GetSegmentation().GetSegment(segmentID) segmentLabelmap = segment.GetRepresentation(vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x,y: x*y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 self.statistics[segmentID,"LM voxel count"] = stat.GetVoxelCount() self.statistics[segmentID,"LM volume mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel self.statistics[segmentID,"LM volume cc"] = stat.GetVoxelCount() * cubicMMPerVoxel * ccPerCubicMM
def LoadROIObject(self, filename): reader = vtk.vtkXMLImageDataReader() try: reader.SetFileName(filename) except UnicodeEncodeError: reader.SetFileName( filename.encode(sys.getfilesystemencoding() or 'UTF-8')) try: reader.Update() except: self.log.error('error reading ROIObject from file') self._type = 'custom' dir, name = os.path.split(filename) root, ext = os.path.splitext(name) self._name = root f1 = vtk.vtkImageToImageStencil() f1.SetInput(reader.GetOutput()) f1.ThresholdByUpper(128) try: f1.Update() self.SetStencilData(f1.GetOutput()) except: self.log.error('error generating stencil on LoadROIObject')
def vortvelvolumei(args): #inputfile, outputfile, sx, ex, sy, ey, sz, ez, dataset): p = args[0] cubenum = args[1] print("Cube", cubenum) #Check for additonal parameters if (p["param1"] != ''): comptype = p["param1"] else: comptype = "q" #Default to q criterion if (p["param2"] != ''): thresh = float(p["param2"]) else: thresh = 783.3 #Default for q threshold on isotropic data inputfile = p["inputfile"] +str(cubenum) + ".npy" outputfile = p["outputfile"] + str(cubenum) + ".vti" #always VTK Image Data for this. sx = p["sx"] sy = p["sy"] sz = p["sz"] ex = p["ex"] ey = p["ey"] ez = p["ez"] print ("Loading file, %s" % inputfile) #Determine if file is h5 or numpy rs = timeit.default_timer() vel = np.load(inputfile) print ("File Loaded") re = timeit.default_timer() #convert numpy array to vtk cs = timeit.default_timer() #convert numpy array to vtk vtkdata = numpy_support.numpy_to_vtk(vel.flat, deep=True, array_type=vtk.VTK_FLOAT) vtkdata.SetNumberOfComponents(3) vtkdata.SetName("Velocity") image = vtk.vtkImageData() image.GetPointData().SetVectors(vtkdata) image.SetExtent(sx,ex,sy,ey,sz,ez) #NOTE: Hardcoding Spacing image.SetSpacing(.006135923, .006135923, .006135923) ce = timeit.default_timer() vs = timeit.default_timer() print ("Beginning computation: " + comptype) if (comptype == "v"): vorticity = vtk.vtkCellDerivatives() vorticity.SetVectorModeToComputeVorticity() vorticity.SetTensorModeToPassTensors() vorticity.SetInputData(image) vorticity.Update() elif (comptype == "q"): vorticity = vtk.vtkGradientFilter() vorticity.SetInputData(image) vorticity.SetInputScalars(image.FIELD_ASSOCIATION_POINTS,"Velocity") vorticity.ComputeQCriterionOn() vorticity.SetComputeGradient(0) vorticity.Update() ve = timeit.default_timer() print("Initial calculation done") ms = timeit.default_timer() if (comptype == "v"): mag = vtk.vtkImageMagnitude() cp = vtk.vtkCellDataToPointData() cp.SetInputData(vorticity.GetOutput()) cp.Update() image.GetPointData().SetScalars(cp.GetOutput().GetPointData().GetVectors()) mag.SetInputData(image) mag.Update() m = mag.GetOutput() m.GetPointData().RemoveArray("Velocity") else: image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) me = timeit.default_timer() print("Generating screenshot") c = vtk.vtkContourFilter() c.SetValue(0,thresh) c.SetInputData(image) c.Update() contour = c.GetOutput() mapper = vtk.vtkPolyDataMapper() mapper.SetInputData(contour) mapper.ScalarVisibilityOn() mapper.SetScalarRange(-1,1) mapper.SetScalarModeToUsePointFieldData() mapper.ColorByArrayComponent("Velocity", 0) actor = vtk.vtkActor() actor.SetMapper(mapper) ren = vtk.vtkRenderer() ren.AddActor(actor) ren.SetBackground(1,1,1) camera = vtk.vtkCamera() ren.SetActiveCamera(camera) ren.ResetCamera() camera.Zoom(1.5) #This reduces the whitespace around the image renWin = vtk.vtkRenderWindow() renWin.SetSize(1024,1024) renWin.AddRenderer(ren) renWin.SetOffScreenRendering(1) windowToImageFilter = vtk.vtkWindowToImageFilter() windowToImageFilter.SetInput(renWin) windowToImageFilter.Update() w = vtk.vtkPNGWriter() pngfilename = p["outputfile"] + str(cubenum) + ".png" w.SetFileName(pngfilename) w.SetInputConnection(windowToImageFilter.GetOutputPort()) w.Write() #Shift camera angle and take snapshots around the cube. for aznum in range(4): camera.Azimuth(90) windowToImageFilter = vtk.vtkWindowToImageFilter() windowToImageFilter.SetInput(renWin) windowToImageFilter.Update() pngfilename = p["outputfile"] + str(cubenum) + "-r" + str(aznum)+ ".png" w.SetFileName(pngfilename) w.SetInputConnection(windowToImageFilter.GetOutputPort()) w.Write() camera.Elevation(90) #Rotate camera to top windowToImageFilter = vtk.vtkWindowToImageFilter() windowToImageFilter.SetInput(renWin) windowToImageFilter.Update() pngfilename = p["outputfile"] + str(cubenum) + "-t1.png" w.SetFileName(pngfilename) w.SetInputConnection(windowToImageFilter.GetOutputPort()) w.Write() camera.Elevation(180) #Rotate camera to bottom windowToImageFilter = vtk.vtkWindowToImageFilter() windowToImageFilter.SetInput(renWin) windowToImageFilter.Update() pngfilename = p["outputfile"] + str(cubenum) + "-b1.png" w.SetFileName(pngfilename) w.SetInputConnection(windowToImageFilter.GetOutputPort()) w.Write() print ("Thresholding.") ts = timeit.default_timer() t = vtk.vtkImageThreshold() #Dense represenation (0's included, structured grid) #t = vtk.vtkThreshold() #sparse representation if (comptype == "q"): t.SetInputData(image) t.ThresholdByUpper(thresh) #.25*67.17^2 = 1127 #t.SetInputArrayToProcess(0,0,0, vorticity.GetOutput().FIELD_ASSOCIATION_POINTS, "Q-criterion") print("q criterion") else: t.SetInputData(m) t.SetInputArrayToProcess(0,0,0, mag.GetOutput().FIELD_ASSOCIATION_POINTS, "Magnitude") t.ThresholdByUpper(thresh) #44.79) #Set values in range to 1 and values out of range to 0 t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() #t.ReplaceOutOn() print("Update thresh") t.Update() #wt = vtk.vtkXMLImageDataWriter() #wt.SetInputData(t.GetOutput()) #wt.SetFileName("thresh.vti") #wt.Write() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(4,4,4) d.SetDilateValue(1) d.SetErodeValue(0) print ("Update dilate") d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) stencil.SetBackgroundValue(0) #image.GetPointData().RemoveArray("Vorticity") #Set scalars to velocity so it can be cut by the stencil image.GetPointData().SetScalars(image.GetPointData().GetVectors()) #if (comptype == "q"): #Use this to get just q-criterion data instead of velocity data. Do we need both? # image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetScalars("Q-criterion")) stencil.SetInputData(image) print ("Update stencil") stencil.Update() te = timeit.default_timer() print("Setting up write") ws = timeit.default_timer() #Make velocity a vector again velarray = stencil.GetOutput().GetPointData().GetScalars() image.GetPointData().RemoveArray("Velocity") image.GetPointData().SetVectors(velarray) w = vtk.vtkXMLImageDataWriter() w.SetCompressorTypeToZLib() #w.SetCompressorTypeToNone() Need to figure out why this fails. w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName(outputfile) w.SetInputData(image) if (0): w.SetCompressorTypeToZfp() w.GetCompressor().SetNx(ex-sx+1) w.GetCompressor().SetNy(ey-sy+1) w.GetCompressor().SetNz(ez-sz+1) w.GetCompressor().SetTolerance(1e-2) w.GetCompressor().SetNumComponents(3) #result = w.Write() result = 1 #don't write for benchmarking we = timeit.default_timer() print("Results:") print("Read time: %s" % str(re-rs)) print ("Convert to vtk: %s" % str(ce-cs)) if (comptype == "q"): print ("Q Computation: %s" % str(ve-vs)) print ("Q Magnitude: %s" % str(me-ms)) else: print ("Vorticity Computation: %s" % str(ve-vs)) print ("Vorticity Magnitude: %s" % str(me-ms)) print ("Threshold: %s" % str(te-ts)) print ("Write %s" % str(we-ws)) print ("Total time: %s" % str(we-rs)) if (result): p["message"] = "Success" p["computetime"] = str(we-rs) return p #return the packet
def __init__(self, grayscaleNode, labelNode, colorNode=None, nodeBaseName=None, fileName=None): #import numpy self.keys = ("Index", "Count", "Volume mm^3", "Volume cc", "Min", "Max", "Mean", "StdDev") cubicMMPerVoxel = reduce(lambda x,y: x*y, labelNode.GetSpacing()) ccPerCubicMM = 0.001 # TODO: progress and status updates # this->InvokeEvent(vtkLabelStatisticsLogic::StartLabelStats, (void*)"start label stats") self.labelNode = labelNode self.colorNode = colorNode self.nodeBaseName = nodeBaseName if not self.nodeBaseName: self.nodeBaseName = labelNode.GetName() if labelNode.GetName() else 'Labels' self.labelStats = {} self.labelStats['Labels'] = [] stataccum = vtk.vtkImageAccumulate() stataccum.SetInputConnection(labelNode.GetImageDataConnection()) stataccum.Update() lo = int(stataccum.GetMin()[0]) hi = int(stataccum.GetMax()[0]) for i in xrange(lo,hi+1): # this->SetProgress((float)i/hi); # std::string event_message = "Label "; std::stringstream s; s << i; event_message.append(s.str()); # this->InvokeEvent(vtkLabelStatisticsLogic::LabelStatsOuterLoop, (void*)event_message.c_str()); # logic copied from slicer3 LabelStatistics # to create the binary volume of the label # //logic copied from slicer2 LabelStatistics MaskStat # // create the binary volume of the label thresholder = vtk.vtkImageThreshold() thresholder.SetInputConnection(labelNode.GetImageDataConnection()) thresholder.SetInValue(1) thresholder.SetOutValue(0) thresholder.ReplaceOutOn() thresholder.ThresholdBetween(i,i) thresholder.SetOutputScalarType(grayscaleNode.GetImageData().GetScalarType()) thresholder.Update() # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.25"); # use vtk's statistics class with the binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputConnection(thresholder.GetOutputPort()) stencil.ThresholdBetween(1, 1) # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.5") stat1 = vtk.vtkImageAccumulate() stat1.SetInputConnection(grayscaleNode.GetImageDataConnection()) stencil.Update() stat1.SetStencilData(stencil.GetOutput()) stat1.Update() # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.75") if stat1.GetVoxelCount() > 0: # add an entry to the LabelStats list self.labelStats["Labels"].append(i) self.labelStats[i,"Index"] = i self.labelStats[i,"Count"] = stat1.GetVoxelCount() self.labelStats[i,"Volume mm^3"] = self.labelStats[i,"Count"] * cubicMMPerVoxel self.labelStats[i,"Volume cc"] = self.labelStats[i,"Volume mm^3"] * ccPerCubicMM self.labelStats[i,"Min"] = stat1.GetMin()[0] self.labelStats[i,"Max"] = stat1.GetMax()[0] self.labelStats[i,"Mean"] = stat1.GetMean()[0] self.labelStats[i,"StdDev"] = stat1.GetStandardDeviation()[0]
#t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() t.ReplaceOutOn() t.Update() rt = t.GetOutput() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(3, 3, 3) d.SetDilateValue(1) d.SetErodeValue(0) d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) image.GetPointData().RemoveArray("Vorticity") image.GetPointData().SetScalars(image.GetPointData().GetVectors()) stencil.SetInputData(image) stencil.Update() w = vtk.vtkXMLImageDataWriter() w.SetInputData(stencil.GetOutput()) w.SetCompressorTypeToZfp() w.GetCompressor().SetNumComponents(3) w.GetCompressor().SetNx(67)
def getthresh(args): inputfile = args[0] outputfile = args[1] sx = args[2] ex = args[3] sy = args[4] ey = args[5] sz = args[6] ez = args[7] dataset = args[8] comptype = args[9] print ("Loading file, %s" % inputfile) #Determine if file is h5 or numpy if (inputfile.split(".")[1] == "npy"): rs = timeit.default_timer() vel = np.load(inputfile) re = timeit.default_timer() else: #read in file rs = timeit.default_timer() data_file = h5py.File(inputfile, 'r') vel = np.array(data_file[dataset]) data_file.close() re = timeit.default_timer() cs = timeit.default_timer() #convert numpy array to vtk vtkdata = numpy_support.numpy_to_vtk(vel.flat, deep=True, array_type=vtk.VTK_FLOAT) vtkdata.SetNumberOfComponents(3) vtkdata.SetName("Velocity") image = vtk.vtkImageData() image.GetPointData().SetVectors(vtkdata) image.SetExtent(sx,ex,sy,ey,sz,ez) #NOTE: Hardcoding Spacing image.SetSpacing(.006135923, .006135923, .006135923) print ("Doing computation") ce = timeit.default_timer() vs = timeit.default_timer() if (comptype == "v"): vorticity = vtk.vtkCellDerivatives() vorticity.SetVectorModeToComputeVorticity() vorticity.SetTensorModeToPassTensors() vorticity.SetInputData(image) vorticity.Update() elif (comptype == "q"): vorticity = vtk.vtkGradientFilter() vorticity.SetInputData(image) vorticity.SetInputScalars(image.FIELD_ASSOCIATION_POINTS,"Velocity") vorticity.ComputeQCriterionOn() vorticity.SetComputeGradient(0) vorticity.Update() ve = timeit.default_timer() #Generate contour for comparison c = vtk.vtkContourFilter() c.SetValue(0,1128) if (comptype == "q"): image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) else: image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetVectors()) c.SetInputData(image) c.Update() w = vtk.vtkXMLPolyDataWriter() w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName("contour.vtp") w.SetInputData(c.GetOutput()) ws = timeit.default_timer() w.Write() ms = timeit.default_timer() if (comptype == "v"): mag = vtk.vtkImageMagnitude() cp = vtk.vtkCellDataToPointData() cp.SetInputData(vorticity.GetOutput()) cp.Update() image.GetPointData().SetScalars(cp.GetOutput().GetPointData().GetVectors()) mag.SetInputData(image) mag.Update() m = mag.GetOutput() m.GetPointData().RemoveArray("Velocity") else: image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) me = timeit.default_timer() print ("Thresholding.") ts = timeit.default_timer() t = vtk.vtkImageThreshold() #t = vtk.vtkThreshold() #sparse representation if (comptype == "q"): t.SetInputData(image) t.ThresholdByUpper(783.3) #.25*67.17^2 = 1127 #t.SetInputArrayToProcess(0,0,0, vorticity.GetOutput().FIELD_ASSOCIATION_POINTS, "Q-criterion") print("q criterion") else: t.SetInputData(m) t.SetInputArrayToProcess(0,0,0, mag.GetOutput().FIELD_ASSOCIATION_POINTS, "Magnitude") t.ThresholdByUpper(44.79) #44.79) #Set values in range to 1 and values out of range to 0 t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() #t.ReplaceOutOn() print("Update thresh") t.Update() #wt = vtk.vtkXMLImageDataWriter() #wt.SetInputData(t.GetOutput()) #wt.SetFileName("thresh.vti") #wt.Write() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(3,3,3) d.SetDilateValue(1) d.SetErodeValue(0) print ("Update dilate") d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) stencil.SetBackgroundValue(0) #image.GetPointData().RemoveArray("Vorticity") #Set scalars to velocity so it can be cut by the stencil image.GetPointData().SetScalars(image.GetPointData().GetVectors()) #if (comptype == "q"): #Use this to get just q-criterion data instead of velocity data. Do we need both? # image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetScalars("Q-criterion")) stencil.SetInputData(image) print ("Update stencil") stencil.Update() te = timeit.default_timer() print("Setting up write") ws = timeit.default_timer() #Make velocity a vector again velarray = stencil.GetOutput().GetPointData().GetScalars() image.GetPointData().RemoveArray("Velocity") image.GetPointData().SetVectors(velarray) w = vtk.vtkXMLImageDataWriter() w.SetCompressorTypeToZLib() #w.SetCompressorTypeToNone() Need to figure out why this fails. w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName(outputfile) w.SetInputData(image) if (0): w.SetCompressorTypeToZfp() w.GetCompressor().SetNx(ex-sx+1) w.GetCompressor().SetNy(ey-sy+1) w.GetCompressor().SetNz(ez-sz+1) w.GetCompressor().SetTolerance(1e-1) w.GetCompressor().SetNumComponents(3) w.Write() we = timeit.default_timer() print("Results:") print("Read time: %s" % str(re-rs)) print ("Convert to vtk: %s" % str(ce-cs)) if (comptype == "q"): print ("Q Computation: %s" % str(ve-vs)) print ("Q Magnitude: %s" % str(me-ms)) else: print ("Vorticity Computation: %s" % str(ve-vs)) print ("Vorticity Magnitude: %s" % str(me-ms)) print ("Threshold: %s" % str(te-ts)) print ("Write %s" % str(we-ws)) print ("Total time: %s" % str(we-rs))
def getStencilForVolume(self, segmentationNode, segmentID, grayscaleNode): import vtkSegmentationCorePython as vtkSegmentationCore containsLabelmapRepresentation = segmentationNode.GetSegmentation( ).ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return None if (not grayscaleNode or not grayscaleNode.GetImageData() or not grayscaleNode.GetImageData().GetPointData() or not grayscaleNode.GetImageData().GetPointData().GetScalars()): # Input grayscale node does not contain valid image data return None # Get geometry of grayscale volume node as oriented image data # reference geometry in reference node coordinate system referenceGeometry_Reference = vtkSegmentationCore.vtkOrientedImageData( ) referenceGeometry_Reference.SetExtent( grayscaleNode.GetImageData().GetExtent()) ijkToRasMatrix = vtk.vtkMatrix4x4() grayscaleNode.GetIJKToRASMatrix(ijkToRasMatrix) referenceGeometry_Reference.SetGeometryFromImageToWorldMatrix( ijkToRasMatrix) # Get transform between grayscale volume and segmentation segmentationToReferenceGeometryTransform = vtk.vtkGeneralTransform() slicer.vtkMRMLTransformNode.GetTransformBetweenNodes( segmentationNode.GetParentTransformNode(), grayscaleNode.GetParentTransformNode(), segmentationToReferenceGeometryTransform) segmentLabelmap = vtkSegmentationCore.vtkOrientedImageData() segmentationNode.GetBinaryLabelmapRepresentation( segmentID, segmentLabelmap) if (not segmentLabelmap or not segmentLabelmap.GetPointData() or not segmentLabelmap.GetPointData().GetScalars()): # No input label data return None segmentLabelmap_Reference = vtkSegmentationCore.vtkOrientedImageData() vtkSegmentationCore.vtkOrientedImageDataResample.ResampleOrientedImageToReferenceOrientedImage( segmentLabelmap, referenceGeometry_Reference, segmentLabelmap_Reference, False, # nearest neighbor interpolation False, # no padding segmentationToReferenceGeometryTransform) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap_Reference) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() return stencil
def vortvelvolume(args): #inputfile, outputfile, sx, ex, sy, ey, sz, ez, dataset): p = args[0] cubenum = args[1] print("Cube", cubenum) #Check for additonal parameters if (p["param1"] != ''): comptype = p["param1"] else: comptype = "q" #Default to q criterion if (p["param2"] != ''): thresh = float(p["param2"]) else: thresh = 783.3 #Default for q threshold on isotropic data #We use 0 for structured grid (vti) and 1 for unstructured grid (vtu) if (p["param3"] != ''): grid = 0 else: grid = 1 if (p["param4"] != ''): kernelsize = int(p["param4"]) else: kernelsize = 3 inputfile = p["inputfile"] +str(cubenum) + ".npy" outputfile = p["outputfile"] + str(cubenum) + ".vti" #always VTK Image Data for this. sx = p["sx"] sy = p["sy"] sz = p["sz"] ex = p["ex"] ey = p["ey"] ez = p["ez"] print ("Loading file, %s" % inputfile) #Determine if file is h5 or numpy rs = timeit.default_timer() vel = np.load(inputfile) re = timeit.default_timer() #convert numpy array to vtk cs = timeit.default_timer() #convert numpy array to vtk vtkdata = numpy_support.numpy_to_vtk(vel.flat, deep=True, array_type=vtk.VTK_FLOAT) vtkdata.SetNumberOfComponents(3) vtkdata.SetName("Velocity") image = vtk.vtkImageData() image.GetPointData().SetVectors(vtkdata) image.SetExtent(sx,ex,sy,ey,sz,ez) #NOTE: Hardcoding Spacing image.SetSpacing(.006135923, .006135923, .006135923) ce = timeit.default_timer() vs = timeit.default_timer() if (comptype == "v"): vorticity = vtk.vtkCellDerivatives() vorticity.SetVectorModeToComputeVorticity() vorticity.SetTensorModeToPassTensors() vorticity.SetInputData(image) vorticity.Update() elif (comptype == "q"): vorticity = vtk.vtkGradientFilter() vorticity.SetInputData(image) vorticity.SetInputScalars(image.FIELD_ASSOCIATION_POINTS,"Velocity") vorticity.ComputeQCriterionOn() vorticity.SetComputeGradient(0) vorticity.Update() ve = timeit.default_timer() ms = timeit.default_timer() if (comptype == "v"): mag = vtk.vtkImageMagnitude() cp = vtk.vtkCellDataToPointData() cp.SetInputData(vorticity.GetOutput()) cp.Update() image.GetPointData().SetScalars(cp.GetOutput().GetPointData().GetVectors()) mag.SetInputData(image) mag.Update() m = mag.GetOutput() m.GetPointData().RemoveArray("Velocity") else: image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) me = timeit.default_timer() print ("Thresholding.") ts = timeit.default_timer() t = vtk.vtkImageThreshold() #t = vtk.vtkThreshold() #sparse representation if (comptype == "q"): t.SetInputData(image) t.ThresholdByUpper(thresh) #.25*67.17^2 = 1127 #t.SetInputArrayToProcess(0,0,0, vorticity.GetOutput().FIELD_ASSOCIATION_POINTS, "Q-criterion") print("q criterion") else: t.SetInputData(m) t.SetInputArrayToProcess(0,0,0, mag.GetOutput().FIELD_ASSOCIATION_POINTS, "Magnitude") t.ThresholdByUpper(thresh) #44.79) #Set values in range to 1 and values out of range to 0 t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() #t.ReplaceOutOn() print("Update thresh") t.Update() #wt = vtk.vtkXMLImageDataWriter() #wt.SetInputData(t.GetOutput()) #wt.SetFileName("thresh.vti") #wt.Write() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(kernelsize,kernelsize,kernelsize) d.SetDilateValue(1) d.SetErodeValue(0) print ("Update dilate") d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) stencil.SetBackgroundValue(0) #image.GetPointData().RemoveArray("Vorticity") #Set scalars to velocity so it can be cut by the stencil image.GetPointData().SetScalars(image.GetPointData().GetVectors()) #if (comptype == "q"): #Use this to get just q-criterion data instead of velocity data. Do we need both? # image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetScalars("Q-criterion")) stencil.SetInputData(image) print ("Update stencil") stencil.Update() te = timeit.default_timer() print("Setting up write") ws = timeit.default_timer() #Make velocity a vector again velarray = stencil.GetOutput().GetPointData().GetScalars() image.GetPointData().RemoveArray("Velocity") image.GetPointData().SetVectors(velarray) if (grid == 0): w = vtk.vtkXMLImageDataWriter() else: w = vtk.vtkXMLUnstructuredGridWriter() w.SetCompressorTypeToZLib() #w.SetCompressorTypeToNone() Need to figure out why this fails. w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName(outputfile) w.SetInputData(image) if (0): w.SetCompressorTypeToZfp() w.GetCompressor().SetNx(ex-sx+1) w.GetCompressor().SetNy(ey-sy+1) w.GetCompressor().SetNz(ez-sz+1) w.GetCompressor().SetTolerance(1e-2) w.GetCompressor().SetNumComponents(3) result = w.Write() result = 1 #don't write for benchmarking we = timeit.default_timer() print("Results:") print("Read time: %s" % str(re-rs)) print ("Convert to vtk: %s" % str(ce-cs)) if (comptype == "q"): print ("Q Computation: %s" % str(ve-vs)) print ("Q Magnitude: %s" % str(me-ms)) else: print ("Vorticity Computation: %s" % str(ve-vs)) print ("Vorticity Magnitude: %s" % str(me-ms)) print ("Threshold: %s" % str(te-ts)) print ("Write %s" % str(we-ws)) print ("Total time: %s" % str(we-rs)) if (result): p["message"] = "Success" p["computetime"] = str(we-rs) return p #return the packet
def processInteractionEvents(self, callerInteractor, eventId, viewWidget): abortEvent = False # Only allow for slice views if viewWidget.className() != "qMRMLSliceWidget": return abortEvent if eventId == vtk.vtkCommand.LeftButtonPressEvent: self.scriptedEffect.saveStateForUndo() # Get master volume image data import vtkSegmentationCorePython as vtkSegmentationCore masterImageData = self.scriptedEffect.masterVolumeImageData() selectedSegmentLabelmap = self.scriptedEffect.selectedSegmentLabelmap( ) # Get modifier labelmap modifierLabelmap = self.scriptedEffect.defaultModifierLabelmap() xy = callerInteractor.GetEventPosition() ijk = self.xyToIjk(xy, viewWidget, masterImageData) pixelValue = masterImageData.GetScalarComponentAsFloat( ijk[0], ijk[1], ijk[2], 0) useSegmentationAsStencil = False try: # This can be a long operation - indicate it to the user qt.QApplication.setOverrideCursor(qt.Qt.WaitCursor) # Perform thresholding floodFillingFilter = vtk.vtkImageThresholdConnectivity() floodFillingFilter.SetInputData(masterImageData) seedPoints = vtk.vtkPoints() origin = masterImageData.GetOrigin() spacing = masterImageData.GetSpacing() seedPoints.InsertNextPoint(origin[0] + ijk[0] * spacing[0], origin[1] + ijk[1] * spacing[1], origin[2] + ijk[2] * spacing[2]) floodFillingFilter.SetSeedPoints(seedPoints) neighborhoodSizeMm = self.neighborhoodSizeMmSlider.value floodFillingFilter.SetNeighborhoodRadius( neighborhoodSizeMm, neighborhoodSizeMm, neighborhoodSizeMm) floodFillingFilter.SetNeighborhoodFraction(0.5) if useSegmentationAsStencil: stencilFilter = vtk.vtkImageToImageStencil() stencilFilter.SetInputData(selectedSegmentLabelmap) stencilFilter.ThresholdByLower(0) stencilFilter.Update() floodFillingFilter.SetStencilData( stencilFilter.GetOutput()) pixelValueTolerance = float( self.intensityToleranceSlider.value) floodFillingFilter.ThresholdBetween( pixelValue - pixelValueTolerance, pixelValue + pixelValueTolerance) floodFillingFilter.SetInValue(1) floodFillingFilter.SetOutValue(0) floodFillingFilter.Update() modifierLabelmap.DeepCopy(floodFillingFilter.GetOutput()) except IndexError: logging.error('apply: Failed to threshold master volume!') finally: qt.QApplication.restoreOverrideCursor() # Apply changes self.scriptedEffect.modifySelectedSegmentByLabelmap( modifierLabelmap, slicer.qSlicerSegmentEditorAbstractEffect.ModificationModeAdd) abortEvent = True return abortEvent
def addGrayscaleVolumeStatistics(self): import vtkSegmentationCorePython as vtkSegmentationCore containsLabelmapRepresentation = self.segmentationNode.GetSegmentation().ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return if self.grayscaleNode is None or self.grayscaleNode.GetImageData() is None: return # Get geometry of grayscale volume node as oriented image data referenceGeometry_Reference = vtkSegmentationCore.vtkOrientedImageData() # reference geometry in reference node coordinate system referenceGeometry_Reference.SetExtent(self.grayscaleNode.GetImageData().GetExtent()) ijkToRasMatrix = vtk.vtkMatrix4x4() self.grayscaleNode.GetIJKToRASMatrix(ijkToRasMatrix) referenceGeometry_Reference.SetGeometryFromImageToWorldMatrix(ijkToRasMatrix) # Get transform between grayscale volume and segmentation segmentationToReferenceGeometryTransform = vtk.vtkGeneralTransform() slicer.vtkMRMLTransformNode.GetTransformBetweenNodes(self.segmentationNode.GetParentTransformNode(), self.grayscaleNode.GetParentTransformNode(), segmentationToReferenceGeometryTransform) cubicMMPerVoxel = reduce(lambda x,y: x*y, referenceGeometry_Reference.GetSpacing()) ccPerCubicMM = 0.001 for segmentID in self.statistics["SegmentIDs"]: segment = self.segmentationNode.GetSegmentation().GetSegment(segmentID) segmentLabelmap = segment.GetRepresentation(vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) segmentLabelmap_Reference = vtkSegmentationCore.vtkOrientedImageData() vtkSegmentationCore.vtkOrientedImageDataResample.ResampleOrientedImageToReferenceOrientedImage( segmentLabelmap, referenceGeometry_Reference, segmentLabelmap_Reference, False, # nearest neighbor interpolation False, # no padding segmentationToReferenceGeometryTransform) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap_Reference) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(self.grayscaleNode.GetImageData()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list self.statistics[segmentID,"GS voxel count"] = stat.GetVoxelCount() self.statistics[segmentID,"GS volume mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel self.statistics[segmentID,"GS volume cc"] = stat.GetVoxelCount() * cubicMMPerVoxel * ccPerCubicMM if stat.GetVoxelCount()>0: self.statistics[segmentID,"GS min"] = stat.GetMin()[0] self.statistics[segmentID,"GS max"] = stat.GetMax()[0] self.statistics[segmentID,"GS mean"] = stat.GetMean()[0] self.statistics[segmentID,"GS stdev"] = stat.GetStandardDeviation()[0]
def __init__(self, labelNode, label=None, grayscaleNode=None): #self.keys = ("Index", "Count", "Volume mm^3", "DimX mm", "DimY mm", "DimZ mm", "COMX mm", "COMY mm", "COMZ mm", "Min", "Max", "Mean", "StdDev", "LabelNode", "ImageNode") cubicMMPerVoxel = reduce(lambda x,y: x*y, labelNode.GetSpacing()) self.labelStats = {} self.labelStats['Labels'] = [] # Set up VTK histogram statistics filter. stataccum = vtk.vtkImageAccumulate() stataccum.SetInputConnection(labelNode.GetImageDataConnection()) stataccum.Update() if not grayscaleNode: grayscaleNode = labelNode if label: lo = label hi = label else: lo = int(stataccum.GetMin()[0]) hi = int(stataccum.GetMax()[0]) if lo == 0: # Don't calculate statistics for the background. if hi == 0: # No label. return lo = 1 # Set up SimpleITK shape statistics filter for label node. voxDims = labelNode.GetSpacing() labelName = labelNode.GetName() labelImage = sitkUtils.PullFromSlicer(labelName) labelShapeStatisticsFilter = sitk.LabelShapeStatisticsImageFilter() outputImage = labelShapeStatisticsFilter.Execute(labelImage, 0, False, False) for i in xrange(lo, hi + 1): thresholder = vtk.vtkImageThreshold() thresholder.SetInputConnection(labelNode.GetImageDataConnection()) thresholder.SetInValue(1) thresholder.SetOutValue(0) thresholder.ReplaceOutOn() thresholder.ThresholdBetween(i, i) thresholder.SetOutputScalarType(grayscaleNode.GetImageData().GetScalarType()) thresholder.Update() stencil = vtk.vtkImageToImageStencil() stencil.SetInputConnection(thresholder.GetOutputPort()) stencil.ThresholdBetween(1, 1) stat1 = vtk.vtkImageAccumulate() stat1.SetInputConnection(grayscaleNode.GetImageDataConnection()) stencil.Update() stat1.SetStencilData(stencil.GetOutput()) stat1.Update() if stat1.GetVoxelCount() > 0: vol = labelShapeStatisticsFilter.GetPhysicalSize(i) dims = labelShapeStatisticsFilter.GetBoundingBox(i) # [x0, y0, z0, dx, dy, dz] com = labelShapeStatisticsFilter.GetCentroid(i) # add an entry to the LabelStats list self.labelStats["Labels"].append(i) self.labelStats[i,"Index"] = i self.labelStats[i,"Count"] = stat1.GetVoxelCount() self.labelStats[i,"Volume mm^3"] = "{0:.1f}".format(vol) self.labelStats[i,"DimX mm"] = "{0:.1f}".format(dims[3]*voxDims[0]) self.labelStats[i,"DimY mm"] = "{0:.1f}".format(dims[4]*voxDims[1]) self.labelStats[i,"DimZ mm"] = "{0:.1f}".format(dims[5]*voxDims[2]) self.labelStats[i,"COMX mm"] = "{0:.1f}".format(-com[0]) # Convert from LPS to RAS self.labelStats[i,"COMY mm"] = "{0:.1f}".format(-com[1]) # Convert from LPS to RAS self.labelStats[i,"COMZ mm"] = "{0:.1f}".format(com[2]) self.labelStats[i,"Min"] = stat1.GetMin()[0] self.labelStats[i,"Max"] = stat1.GetMax()[0] self.labelStats[i,"Mean"] = "{0:.1f}".format(stat1.GetMean()[0]) self.labelStats[i,"StdDev"] = "{0:.1f}".format(stat1.GetStandardDeviation()[0]) self.labelStats[i,"LabelNode"] = labelName self.labelStats[i,"ImageNode"] = grayscaleNode.GetName()
def __init__(self, grayscaleNode, labelNode, fileName=None): #import numpy self.keys = ("Index", "Count", "Volume mm^3", "Volume cc", "Min", "Max", "Mean", "StdDev") cubicMMPerVoxel = reduce(lambda x,y: x*y, labelNode.GetSpacing()) ccPerCubicMM = 0.001 # TODO: progress and status updates # this->InvokeEvent(vtkLabelStatisticsLogic::StartLabelStats, (void*)"start label stats") self.labelNode = labelNode self.labelStats = {} self.labelStats['Labels'] = [] stataccum = vtk.vtkImageAccumulate() if vtk.VTK_MAJOR_VERSION <= 5: stataccum.SetInput(labelNode.GetImageData()) else: stataccum.SetInputConnection(labelNode.GetImageDataConnection()) stataccum.Update() lo = int(stataccum.GetMin()[0]) hi = int(stataccum.GetMax()[0]) for i in xrange(lo,hi+1): # this->SetProgress((float)i/hi); # std::string event_message = "Label "; std::stringstream s; s << i; event_message.append(s.str()); # this->InvokeEvent(vtkLabelStatisticsLogic::LabelStatsOuterLoop, (void*)event_message.c_str()); # logic copied from slicer3 LabelStatistics # to create the binary volume of the label # //logic copied from slicer2 LabelStatistics MaskStat # // create the binary volume of the label thresholder = vtk.vtkImageThreshold() if vtk.VTK_MAJOR_VERSION <= 5: thresholder.SetInput(labelNode.GetImageData()) else: thresholder.SetInputConnection(labelNode.GetImageDataConnection()) thresholder.SetInValue(1) thresholder.SetOutValue(0) thresholder.ReplaceOutOn() thresholder.ThresholdBetween(i,i) thresholder.SetOutputScalarType(grayscaleNode.GetImageData().GetScalarType()) thresholder.Update() # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.25"); # use vtk's statistics class with the binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() if vtk.VTK_MAJOR_VERSION <= 5: stencil.SetInput(thresholder.GetOutput()) else: stencil.SetInputConnection(thresholder.GetOutputPort()) stencil.ThresholdBetween(1, 1) # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.5") stat1 = vtk.vtkImageAccumulate() if vtk.VTK_MAJOR_VERSION <= 5: stat1.SetInput(grayscaleNode.GetImageData()) stat1.SetStencil(stencil.GetOutput()) else: stat1.SetInputConnection(grayscaleNode.GetImageDataConnection()) stencil.Update() stat1.SetStencilData(stencil.GetOutput()) stat1.Update() # this.InvokeEvent(vtkLabelStatisticsLogic::LabelStatsInnerLoop, (void*)"0.75") if stat1.GetVoxelCount() > 0: # add an entry to the LabelStats list self.labelStats["Labels"].append(i) self.labelStats[i,"Index"] = i self.labelStats[i,"Count"] = stat1.GetVoxelCount() self.labelStats[i,"Volume mm^3"] = self.labelStats[i,"Count"] * cubicMMPerVoxel self.labelStats[i,"Volume cc"] = self.labelStats[i,"Volume mm^3"] * ccPerCubicMM self.labelStats[i,"Min"] = stat1.GetMin()[0] self.labelStats[i,"Max"] = stat1.GetMax()[0] self.labelStats[i,"Mean"] = stat1.GetMean()[0] self.labelStats[i,"StdDev"] = stat1.GetStandardDeviation()[0]
def maskVolumeWithSegment(segmentationNode, segmentID, operationMode, fillValues, inputVolumeNode, outputVolumeNode, maskExtent=None): """ Fill voxels of the input volume inside/outside the masking model with the provided fill value maskExtent: optional output to return computed mask extent (expected input is a 6-element list) fillValues: list containing one or two fill values. If fill mode is inside or outside then only one value is specified in the list. If fill mode is inside&outside then the list must contain two values: first is the inside fill, second is the outside fill value. """ segmentIDs = vtk.vtkStringArray() segmentIDs.InsertNextValue(segmentID) maskVolumeNode = slicer.modules.volumes.logic().CreateAndAddLabelVolume(inputVolumeNode, "TemporaryVolumeMask") if not maskVolumeNode: logging.error("maskVolumeWithSegment failed: invalid maskVolumeNode") return False if not slicer.vtkSlicerSegmentationsModuleLogic.ExportSegmentsToLabelmapNode(segmentationNode, segmentIDs, maskVolumeNode, inputVolumeNode): logging.error("maskVolumeWithSegment failed: ExportSegmentsToLabelmapNode error") slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode().GetColorNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode) return False if maskExtent: img = slicer.modules.segmentations.logic().CreateOrientedImageDataFromVolumeNode(maskVolumeNode) img.UnRegister(None) import vtkSegmentationCorePython as vtkSegmentationCore vtkSegmentationCore.vtkOrientedImageDataResample.CalculateEffectiveExtent(img, maskExtent, 0) maskToStencil = vtk.vtkImageToImageStencil() maskToStencil.ThresholdByLower(0) maskToStencil.SetInputData(maskVolumeNode.GetImageData()) stencil = vtk.vtkImageStencil() if operationMode == "FILL_INSIDE_AND_OUTSIDE": # Set input to constant value thresh = vtk.vtkImageThreshold() thresh.SetInputData(inputVolumeNode.GetImageData()) thresh.ThresholdByLower(0) thresh.SetInValue(fillValues[1]) thresh.SetOutValue(fillValues[1]) thresh.SetOutputScalarType(inputVolumeNode.GetImageData().GetScalarType()) thresh.Update() stencil.SetInputData(thresh.GetOutput()) else: stencil.SetInputData(inputVolumeNode.GetImageData()) stencil.SetStencilConnection(maskToStencil.GetOutputPort()) stencil.SetReverseStencil(operationMode == "FILL_OUTSIDE") stencil.SetBackgroundValue(fillValues[0]) stencil.Update() outputVolumeNode.SetAndObserveImageData(stencil.GetOutput()) # Set the same geometry and parent transform as the input volume ijkToRas = vtk.vtkMatrix4x4() inputVolumeNode.GetIJKToRASMatrix(ijkToRas) outputVolumeNode.SetIJKToRASMatrix(ijkToRas) inputVolumeNode.SetAndObserveTransformNodeID(inputVolumeNode.GetTransformNodeID()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode().GetColorNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode.GetDisplayNode()) slicer.mrmlScene.RemoveNode(maskVolumeNode) return True
import vtk from vtk.test import Testing from vtk.util.misc import vtkGetDataRoot VTK_DATA_ROOT = vtkGetDataRoot() # A script to test the stencil filter by using one image # to stencil another # Image pipeline reader1 = vtk.vtkBMPReader() reader1.SetFileName("" + str(VTK_DATA_ROOT) + "/Data/masonry.bmp") reader2 = vtk.vtkPNMReader() reader2.SetFileName("" + str(VTK_DATA_ROOT) + "/Data/B.pgm") translate = vtk.vtkImageTranslateExtent() translate.SetInputConnection(reader2.GetOutputPort()) translate.SetTranslation(60, 60, 0) imageToStencil = vtk.vtkImageToImageStencil() imageToStencil.SetInputConnection(translate.GetOutputPort()) imageToStencil.ThresholdBetween(0, 127) # silly stuff to increase coverage imageToStencil.SetUpperThreshold(imageToStencil.GetUpperThreshold()) imageToStencil.SetLowerThreshold(imageToStencil.GetLowerThreshold()) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(reader1.GetOutputPort()) stencil.SetBackgroundValue(0) stencil.ReverseStencilOn() stencil.SetStencilConnection(imageToStencil.GetOutputPort()) viewer = vtk.vtkImageViewer() viewer.SetInputConnection(stencil.GetOutputPort()) viewer.SetColorWindow(255.0) viewer.SetColorLevel(127.5) viewer.SetZSlice(0)
import vtk from vtk.test import Testing from vtk.util.misc import vtkGetDataRoot VTK_DATA_ROOT = vtkGetDataRoot() # A script to test the stencil filter by using one image # to stencil another # Image pipeline reader1 = vtk.vtkBMPReader() reader1.SetFileName("" + str(VTK_DATA_ROOT) + "/Data/masonry.bmp") reader2 = vtk.vtkPNMReader() reader2.SetFileName("" + str(VTK_DATA_ROOT) + "/Data/B.pgm") translate = vtk.vtkImageTranslateExtent() translate.SetInputConnection(reader2.GetOutputPort()) translate.SetTranslation(60,60,0) imageToStencil = vtk.vtkImageToImageStencil() imageToStencil.SetInputConnection(translate.GetOutputPort()) imageToStencil.ThresholdBetween(0,127) # silly stuff to increase coverage imageToStencil.SetUpperThreshold(imageToStencil.GetUpperThreshold()) imageToStencil.SetLowerThreshold(imageToStencil.GetLowerThreshold()) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(reader1.GetOutputPort()) stencil.SetBackgroundValue(0) stencil.ReverseStencilOn() stencil.SetStencilConnection(imageToStencil.GetOutputPort()) viewer = vtk.vtkImageViewer() viewer.SetInputConnection(stencil.GetOutputPort()) viewer.SetColorWindow(255.0) viewer.SetColorLevel(127.5) viewer.SetZSlice(0)
def addGrayscaleVolumeStatistics(self): import vtkSegmentationCorePython as vtkSegmentationCore containsLabelmapRepresentation = self.segmentationNode.GetSegmentation( ).ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return if self.grayscaleNode is None or self.grayscaleNode.GetImageData( ) is None: return # Get geometry of grayscale volume node as oriented image data referenceGeometry_Reference = vtkSegmentationCore.vtkOrientedImageData( ) # reference geometry in reference node coordinate system referenceGeometry_Reference.SetExtent( self.grayscaleNode.GetImageData().GetExtent()) ijkToRasMatrix = vtk.vtkMatrix4x4() self.grayscaleNode.GetIJKToRASMatrix(ijkToRasMatrix) referenceGeometry_Reference.SetGeometryFromImageToWorldMatrix( ijkToRasMatrix) # Get transform between grayscale volume and segmentation segmentationToReferenceGeometryTransform = vtk.vtkGeneralTransform() slicer.vtkMRMLTransformNode.GetTransformBetweenNodes( self.segmentationNode.GetParentTransformNode(), self.grayscaleNode.GetParentTransformNode(), segmentationToReferenceGeometryTransform) cubicMMPerVoxel = reduce(lambda x, y: x * y, referenceGeometry_Reference.GetSpacing()) ccPerCubicMM = 0.001 for segmentID in self.statistics["SegmentIDs"]: segment = self.segmentationNode.GetSegmentation().GetSegment( segmentID) segmentLabelmap = segment.GetRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) segmentLabelmap_Reference = vtkSegmentationCore.vtkOrientedImageData( ) vtkSegmentationCore.vtkOrientedImageDataResample.ResampleOrientedImageToReferenceOrientedImage( segmentLabelmap, referenceGeometry_Reference, segmentLabelmap_Reference, False, # nearest neighbor interpolation False, # no padding segmentationToReferenceGeometryTransform) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap_Reference) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(self.grayscaleNode.GetImageData()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list self.statistics[segmentID, "GS voxel count"] = stat.GetVoxelCount() self.statistics[ segmentID, "GS volume mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel self.statistics[segmentID, "GS volume cc"] = stat.GetVoxelCount( ) * cubicMMPerVoxel * ccPerCubicMM if stat.GetVoxelCount() > 0: self.statistics[segmentID, "GS min"] = stat.GetMin()[0] self.statistics[segmentID, "GS max"] = stat.GetMax()[0] self.statistics[segmentID, "GS mean"] = stat.GetMean()[0] self.statistics[segmentID, "GS stdev"] = stat.GetStandardDeviation()[0]
def __init__(self, parent=None): ScriptedLoadableModuleLogic.__init__(self, parent) self.resliceLogic = slicer.modulelogic.vtkSlicerVolumeResliceDriverLogic( ) # Find or create the 5DOFCalculatedTo6DOF transform self.FiveCalculatedToSixTransform = slicer.util.getNode( "FiveCalculatedToSixTransform") if self.FiveCalculatedToSixTransform == None: # Create the node self.FiveCalculatedToSixTransform = slicer.vtkMRMLLinearTransformNode( ) self.FiveCalculatedToSixTransform.SetName( "FiveCalculatedToSixTransform") self.FiveCalculatedToSixTransform.SetHideFromEditors(True) slicer.mrmlScene.AddNode(self.FiveCalculatedToSixTransform) self.base5DOFTo6DOFZOffset = 0.0 self.imageObserverTag = None self.sixDOFObserverTag = None self.iceVolumeNode = None self.maskedICEVolumeNode = None self.maskVolumeNode = None self.sixDOFTransformNode = None self.fiveDOFTransformNode = None self.sixDOFModelTo6DOFTransformNode = None self.fiveDOFModelTo5DOFCalculatedTransformNode = None self.jawModelNode = None self.noseModelNode = None self.guidanceOn = False self.imageToStencil = vtk.vtkImageToImageStencil() self.imageToStencil.ThresholdByUpper(254) self.imageStencil = vtk.vtkImageStencil() self.imageStencil.SetStencilConnection( self.imageToStencil.GetOutputPort()) self.imageStencil.SetBackgroundValue(0) self.teeConnectorNode = slicer.util.getNode(self.moduleName + 'TEEServerConnector') if self.teeConnectorNode == None: self.teeConnectorNode = slicer.vtkMRMLIGTLConnectorNode() slicer.mrmlScene.AddNode(self.teeConnectorNode) self.teeConnectorNode.SetName(self.moduleName + 'TEEServerConnector') self.teeConnectorNode.SetTypeClient("localhost", 18945) self.teeConnectorNode.Start() self.iceConnectorNode = slicer.util.getNode(self.moduleName + 'ICEServerConnector') if self.iceConnectorNode == None: self.iceConnectorNode = slicer.vtkMRMLIGTLConnectorNode() slicer.mrmlScene.AddNode(self.iceConnectorNode) self.iceConnectorNode.SetName(self.moduleName + 'ICEServerConnector') self.iceConnectorNode.SetTypeClient("localhost", 18944) self.iceConnectorNode.Start()
def getthresh(args): inputfile = args[0] outputfile = args[1] sx = args[2] ex = args[3] sy = args[4] ey = args[5] sz = args[6] ez = args[7] dataset = args[8] comptype = args[9] print("Loading file, %s" % inputfile) #Determine if file is h5 or numpy if (inputfile.split(".")[1] == "npy"): rs = timeit.default_timer() vel = np.load(inputfile) re = timeit.default_timer() else: #read in file rs = timeit.default_timer() data_file = h5py.File(inputfile, 'r') vel = np.array(data_file[dataset]) data_file.close() re = timeit.default_timer() cs = timeit.default_timer() #convert numpy array to vtk vtkdata = numpy_support.numpy_to_vtk(vel.flat, deep=True, array_type=vtk.VTK_FLOAT) vtkdata.SetNumberOfComponents(3) vtkdata.SetName("Velocity") image = vtk.vtkImageData() image.GetPointData().SetVectors(vtkdata) image.SetExtent(sx, ex, sy, ey, sz, ez) #NOTE: Hardcoding Spacing image.SetSpacing(.006135923, .006135923, .006135923) print("Doing computation") ce = timeit.default_timer() vs = timeit.default_timer() if (comptype == "v"): vorticity = vtk.vtkCellDerivatives() vorticity.SetVectorModeToComputeVorticity() vorticity.SetTensorModeToPassTensors() vorticity.SetInputData(image) vorticity.Update() elif (comptype == "q"): vorticity = vtk.vtkGradientFilter() vorticity.SetInputData(image) vorticity.SetInputScalars(image.FIELD_ASSOCIATION_POINTS, "Velocity") vorticity.ComputeQCriterionOn() vorticity.SetComputeGradient(0) vorticity.Update() ve = timeit.default_timer() #Generate contour for comparison c = vtk.vtkContourFilter() c.SetValue(0, 1128) if (comptype == "q"): image.GetPointData().SetScalars( vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) else: image.GetPointData().SetScalars( vorticity.GetOutput().GetPointData().GetVectors()) c.SetInputData(image) c.Update() w = vtk.vtkXMLPolyDataWriter() w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName("contour.vtp") w.SetInputData(c.GetOutput()) ws = timeit.default_timer() w.Write() ms = timeit.default_timer() if (comptype == "v"): mag = vtk.vtkImageMagnitude() cp = vtk.vtkCellDataToPointData() cp.SetInputData(vorticity.GetOutput()) cp.Update() image.GetPointData().SetScalars( cp.GetOutput().GetPointData().GetVectors()) mag.SetInputData(image) mag.Update() m = mag.GetOutput() m.GetPointData().RemoveArray("Velocity") else: image.GetPointData().SetScalars( vorticity.GetOutput().GetPointData().GetVectors("Q-criterion")) me = timeit.default_timer() print("Thresholding.") ts = timeit.default_timer() t = vtk.vtkImageThreshold() #t = vtk.vtkThreshold() #sparse representation if (comptype == "q"): t.SetInputData(image) t.ThresholdByUpper(783.3) #.25*67.17^2 = 1127 #t.SetInputArrayToProcess(0,0,0, vorticity.GetOutput().FIELD_ASSOCIATION_POINTS, "Q-criterion") print("q criterion") else: t.SetInputData(m) t.SetInputArrayToProcess(0, 0, 0, mag.GetOutput().FIELD_ASSOCIATION_POINTS, "Magnitude") t.ThresholdByUpper(44.79) #44.79) #Set values in range to 1 and values out of range to 0 t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() #t.ReplaceOutOn() print("Update thresh") t.Update() #wt = vtk.vtkXMLImageDataWriter() #wt.SetInputData(t.GetOutput()) #wt.SetFileName("thresh.vti") #wt.Write() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(3, 3, 3) d.SetDilateValue(1) d.SetErodeValue(0) print("Update dilate") d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) stencil.SetBackgroundValue(0) #image.GetPointData().RemoveArray("Vorticity") #Set scalars to velocity so it can be cut by the stencil image.GetPointData().SetScalars(image.GetPointData().GetVectors()) #if (comptype == "q"): #Use this to get just q-criterion data instead of velocity data. Do we need both? # image.GetPointData().SetScalars(vorticity.GetOutput().GetPointData().GetScalars("Q-criterion")) stencil.SetInputData(image) print("Update stencil") stencil.Update() te = timeit.default_timer() print("Setting up write") ws = timeit.default_timer() #Make velocity a vector again velarray = stencil.GetOutput().GetPointData().GetScalars() image.GetPointData().RemoveArray("Velocity") image.GetPointData().SetVectors(velarray) w = vtk.vtkXMLImageDataWriter() w.SetCompressorTypeToZLib() #w.SetCompressorTypeToNone() Need to figure out why this fails. w.SetEncodeAppendedData(0) #turn of base 64 encoding for fast write w.SetFileName(outputfile) w.SetInputData(image) if (0): w.SetCompressorTypeToZfp() w.GetCompressor().SetNx(ex - sx + 1) w.GetCompressor().SetNy(ey - sy + 1) w.GetCompressor().SetNz(ez - sz + 1) w.GetCompressor().SetTolerance(1e-1) w.GetCompressor().SetNumComponents(3) w.Write() we = timeit.default_timer() print("Results:") print("Read time: %s" % str(re - rs)) print("Convert to vtk: %s" % str(ce - cs)) if (comptype == "q"): print("Q Computation: %s" % str(ve - vs)) print("Q Magnitude: %s" % str(me - ms)) else: print("Vorticity Computation: %s" % str(ve - vs)) print("Vorticity Magnitude: %s" % str(me - ms)) print("Threshold: %s" % str(te - ts)) print("Write %s" % str(we - ws)) print("Total time: %s" % str(we - rs))
def computeStatistics(self, segmentID): import vtkSegmentationCorePython as vtkSegmentationCore requestedKeys = self.getRequestedKeys() segmentationNode = slicer.mrmlScene.GetNodeByID(self.getParameterNode().GetParameter("Segmentation")) grayscaleNode = slicer.mrmlScene.GetNodeByID(self.getParameterNode().GetParameter("ScalarVolume")) if len(requestedKeys)==0: return {} containsLabelmapRepresentation = segmentationNode.GetSegmentation().ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return {} if grayscaleNode is None or grayscaleNode.GetImageData() is None: return {} # Get geometry of grayscale volume node as oriented image data # reference geometry in reference node coordinate system referenceGeometry_Reference = vtkSegmentationCore.vtkOrientedImageData() referenceGeometry_Reference.SetExtent(grayscaleNode.GetImageData().GetExtent()) ijkToRasMatrix = vtk.vtkMatrix4x4() grayscaleNode.GetIJKToRASMatrix(ijkToRasMatrix) referenceGeometry_Reference.SetGeometryFromImageToWorldMatrix(ijkToRasMatrix) # Get transform between grayscale volume and segmentation segmentationToReferenceGeometryTransform = vtk.vtkGeneralTransform() slicer.vtkMRMLTransformNode.GetTransformBetweenNodes(segmentationNode.GetParentTransformNode(), grayscaleNode.GetParentTransformNode(), segmentationToReferenceGeometryTransform) cubicMMPerVoxel = reduce(lambda x,y: x*y, referenceGeometry_Reference.GetSpacing()) ccPerCubicMM = 0.001 segment = segmentationNode.GetSegmentation().GetSegment(segmentID) segBinaryLabelName = vtkSegmentationCore.vtkSegmentationConverter.GetSegmentationBinaryLabelmapRepresentationName() segmentLabelmap = segment.GetRepresentation(segBinaryLabelName) segmentLabelmap_Reference = vtkSegmentationCore.vtkOrientedImageData() vtkSegmentationCore.vtkOrientedImageDataResample.ResampleOrientedImageToReferenceOrientedImage( segmentLabelmap, referenceGeometry_Reference, segmentLabelmap_Reference, False, # nearest neighbor interpolation False, # no padding segmentationToReferenceGeometryTransform) # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap_Reference) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(grayscaleNode.GetImageData()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # create statistics list stats = {} if "voxel_count" in requestedKeys: stats["voxel_count"] = stat.GetVoxelCount() if "volume_mm3" in requestedKeys: stats["volume_mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel if "volume_cm3" in requestedKeys: stats["volume_cm3"] = stat.GetVoxelCount() * cubicMMPerVoxel * ccPerCubicMM if stat.GetVoxelCount()>0: if "min" in requestedKeys: stats["min"] = stat.GetMin()[0] if "max" in requestedKeys: stats["max"] = stat.GetMax()[0] if "mean" in requestedKeys: stats["mean"] = stat.GetMean()[0] if "stdev" in requestedKeys: stats["stdev"] = stat.GetStandardDeviation()[0] return stats
#t.SetInValue(1) t.SetOutValue(0) #t.ReplaceInOn() t.ReplaceOutOn() t.Update() rt = t.GetOutput() d = vtk.vtkImageDilateErode3D() d.SetInputData(t.GetOutput()) d.SetKernelSize(3,3,3) d.SetDilateValue(1) d.SetErodeValue(0) d.Update() iis = vtk.vtkImageToImageStencil() iis.SetInputData(d.GetOutput()) iis.ThresholdByUpper(1) stencil = vtk.vtkImageStencil() stencil.SetInputConnection(2, iis.GetOutputPort()) image.GetPointData().RemoveArray("Vorticity") image.GetPointData().SetScalars(image.GetPointData().GetVectors()) stencil.SetInputData(image) stencil.Update() w = vtk.vtkXMLImageDataWriter() w.SetInputData(stencil.GetOutput()) w.SetCompressorTypeToZfp() w.GetCompressor().SetNumComponents(3) w.GetCompressor().SetNx(67)
def computeStatistics(self, segmentID): import vtkSegmentationCorePython as vtkSegmentationCore requestedKeys = self.getRequestedKeys() segmentationNode = slicer.mrmlScene.GetNodeByID( self.getParameterNode().GetParameter("Segmentation")) if len(requestedKeys) == 0: return {} containsLabelmapRepresentation = segmentationNode.GetSegmentation( ).ContainsRepresentation( vtkSegmentationCore.vtkSegmentationConverter. GetSegmentationBinaryLabelmapRepresentationName()) if not containsLabelmapRepresentation: return {} segmentLabelmap = slicer.vtkOrientedImageData() segmentationNode.GetBinaryLabelmapRepresentation( segmentID, segmentLabelmap) if (not segmentLabelmap or not segmentLabelmap.GetPointData() or not segmentLabelmap.GetPointData().GetScalars()): # No input label data return {} # We need to know exactly the value of the segment voxels, apply threshold to make force the selected label value labelValue = 1 backgroundValue = 0 thresh = vtk.vtkImageThreshold() thresh.SetInputData(segmentLabelmap) thresh.ThresholdByLower(0) thresh.SetInValue(backgroundValue) thresh.SetOutValue(labelValue) thresh.SetOutputScalarType(vtk.VTK_UNSIGNED_CHAR) thresh.Update() # Use binary labelmap as a stencil stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(thresh.GetOutput()) stencil.ThresholdByUpper(labelValue) stencil.Update() stat = vtk.vtkImageAccumulate() stat.SetInputData(thresh.GetOutput()) stat.SetStencilData(stencil.GetOutput()) stat.Update() # Add data to statistics list cubicMMPerVoxel = reduce(lambda x, y: x * y, segmentLabelmap.GetSpacing()) ccPerCubicMM = 0.001 stats = {} if "voxel_count" in requestedKeys: stats["voxel_count"] = stat.GetVoxelCount() if "volume_mm3" in requestedKeys: stats["volume_mm3"] = stat.GetVoxelCount() * cubicMMPerVoxel if "volume_cm3" in requestedKeys: stats["volume_cm3"] = stat.GetVoxelCount( ) * cubicMMPerVoxel * ccPerCubicMM calculateShapeStats = False for shapeKey in self.shapeKeys: if shapeKey in requestedKeys: calculateShapeStats = True break if calculateShapeStats: directions = vtk.vtkMatrix4x4() segmentLabelmap.GetDirectionMatrix(directions) # Remove oriented bounding box from requested keys and replace with individual keys requestedOptions = requestedKeys statFilterOptions = self.shapeKeys calculateOBB = ("obb_diameter_mm" in requestedKeys or "obb_origin_ras" in requestedKeys or "obb_direction_ras_x" in requestedKeys or "obb_direction_ras_y" in requestedKeys or "obb_direction_ras_z" in requestedKeys) if calculateOBB: temp = statFilterOptions statFilterOptions = [] for option in temp: if not option in self.obbKeys: statFilterOptions.append(option) statFilterOptions.append("oriented_bounding_box") temp = requestedOptions requestedOptions = [] for option in temp: if not option in self.obbKeys: requestedOptions.append(option) requestedOptions.append("oriented_bounding_box") shapeStat = vtkITK.vtkITKLabelShapeStatistics() shapeStat.SetInputData(thresh.GetOutput()) shapeStat.SetDirections(directions) for shapeKey in statFilterOptions: shapeStat.SetComputeShapeStatistic( self.keyToShapeStatisticNames[shapeKey], shapeKey in requestedOptions) shapeStat.Update() # If segmentation node is transformed, apply that transform to get RAS coordinates transformSegmentToRas = vtk.vtkGeneralTransform() slicer.vtkMRMLTransformNode.GetTransformBetweenNodes( segmentationNode.GetParentTransformNode(), None, transformSegmentToRas) statTable = shapeStat.GetOutput() if "centroid_ras" in requestedKeys: centroidRAS = [0, 0, 0] centroidArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["centroid_ras"]) centroid = centroidArray.GetTuple(0) transformSegmentToRas.TransformPoint(centroid, centroidRAS) stats["centroid_ras"] = centroidRAS if "roundness" in requestedKeys: roundnessArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["roundness"]) roundness = roundnessArray.GetTuple(0)[0] stats["roundness"] = roundness if "flatness" in requestedKeys: flatnessArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["flatness"]) flatness = flatnessArray.GetTuple(0)[0] stats["flatness"] = flatness if "feret_diameter_mm" in requestedKeys: feretDiameterArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["feret_diameter_mm"]) feretDiameter = feretDiameterArray.GetTuple(0)[0] stats["feret_diameter_mm"] = feretDiameter if "surface_area_mm2" in requestedKeys: perimeterArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["surface_area_mm2"]) perimeter = perimeterArray.GetTuple(0)[0] stats["surface_area_mm2"] = perimeter if "obb_origin_ras" in requestedKeys: obbOriginRAS = [0, 0, 0] obbOriginArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_origin_ras"]) obbOrigin = obbOriginArray.GetTuple(0) transformSegmentToRas.TransformPoint(obbOrigin, obbOriginRAS) stats["obb_origin_ras"] = obbOriginRAS if "obb_diameter_mm" in requestedKeys: obbDiameterArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_diameter_mm"]) obbDiameterMM = list(obbDiameterArray.GetTuple(0)) stats["obb_diameter_mm"] = obbDiameterMM if "obb_direction_ras_x" in requestedKeys: obbOriginArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_origin_ras"]) obbOrigin = obbOriginArray.GetTuple(0) obbDirectionXArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_direction_ras_x"]) obbDirectionX = list(obbDirectionXArray.GetTuple(0)) transformSegmentToRas.TransformVectorAtPoint( obbOrigin, obbDirectionX, obbDirectionX) stats["obb_direction_ras_x"] = obbDirectionX if "obb_direction_ras_y" in requestedKeys: obbOriginArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_origin_ras"]) obbOrigin = obbOriginArray.GetTuple(0) obbDirectionYArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_direction_ras_y"]) obbDirectionY = list(obbDirectionYArray.GetTuple(0)) transformSegmentToRas.TransformVectorAtPoint( obbOrigin, obbDirectionY, obbDirectionY) stats["obb_direction_ras_y"] = obbDirectionY if "obb_direction_ras_z" in requestedKeys: obbOriginArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_origin_ras"]) obbOrigin = obbOriginArray.GetTuple(0) obbDirectionZArray = statTable.GetColumnByName( self.keyToShapeStatisticNames["obb_direction_ras_z"]) obbDirectionZ = list(obbDirectionZArray.GetTuple(0)) transformSegmentToRas.TransformVectorAtPoint( obbOrigin, obbDirectionZ, obbDirectionZ) stats["obb_direction_ras_z"] = obbDirectionZ return stats
def floodFillFromPoint(self, ijk): """Fills the segment taking based on the current master volume. Input IJK position is voxel coordinates of master volume. """ self.scriptedEffect.saveStateForUndo() # Get master volume image data import vtkSegmentationCorePython as vtkSegmentationCore masterImageData = self.getClippedMasterImageData() selectedSegmentLabelmap = self.scriptedEffect.selectedSegmentLabelmap() # Get modifier labelmap modifierLabelmap = self.scriptedEffect.defaultModifierLabelmap() pixelValue = masterImageData.GetScalarComponentAsFloat( ijk[0], ijk[1], ijk[2], 0) useSegmentationAsStencil = False # Perform thresholding floodFillingFilter = vtk.vtkImageThresholdConnectivity() floodFillingFilter.SetInputData(masterImageData) seedPoints = vtk.vtkPoints() origin = masterImageData.GetOrigin() spacing = masterImageData.GetSpacing() seedPoints.InsertNextPoint(origin[0] + ijk[0] * spacing[0], origin[1] + ijk[1] * spacing[1], origin[2] + ijk[2] * spacing[2]) floodFillingFilter.SetSeedPoints(seedPoints) maskImageData = vtkSegmentationCore.vtkOrientedImageData() intensityBasedMasking = self.scriptedEffect.parameterSetNode( ).GetMasterVolumeIntensityMask() segmentationNode = self.scriptedEffect.parameterSetNode( ).GetSegmentationNode() success = segmentationNode.GenerateEditMask( maskImageData, self.scriptedEffect.parameterSetNode().GetMaskMode(), masterImageData, # reference geometry self.scriptedEffect.parameterSetNode().GetSelectedSegmentID(), self.scriptedEffect.parameterSetNode().GetMaskSegmentID() if self.scriptedEffect.parameterSetNode().GetMaskSegmentID() else "", masterImageData if intensityBasedMasking else None, self.scriptedEffect.parameterSetNode( ).GetMasterVolumeIntensityMaskRange() if intensityBasedMasking else None) if success: stencil = vtk.vtkImageToImageStencil() stencil.SetInputData(maskImageData) stencil.ThresholdByLower(0) stencil.Update() floodFillingFilter.SetStencilData(stencil.GetOutput()) else: logging.error("Failed to create edit mask") neighborhoodSizeMm = self.neighborhoodSizeMmSlider.value floodFillingFilter.SetNeighborhoodRadius(neighborhoodSizeMm, neighborhoodSizeMm, neighborhoodSizeMm) floodFillingFilter.SetNeighborhoodFraction(0.5) if useSegmentationAsStencil: stencilFilter = vtk.vtkImageToImageStencil() stencilFilter.SetInputData(selectedSegmentLabelmap) stencilFilter.ThresholdByLower(0) stencilFilter.Update() floodFillingFilter.SetStencilData(stencilFilter.GetOutput()) pixelValueTolerance = float(self.intensityToleranceSlider.value) floodFillingFilter.ThresholdBetween(pixelValue - pixelValueTolerance, pixelValue + pixelValueTolerance) floodFillingFilter.SetInValue(1) floodFillingFilter.SetOutValue(0) floodFillingFilter.Update() modifierLabelmap.DeepCopy(floodFillingFilter.GetOutput()) # Apply changes self.scriptedEffect.modifySelectedSegmentByLabelmap( modifierLabelmap, slicer.qSlicerSegmentEditorAbstractEffect.ModificationModeAdd)