def LoadVolumeData(self, data_set): if data_set.endswith('nii') or data_set.endswith('nii.gz'): try: from nifti import NiftiImage except ImportError: print "Apparently you don't have PyNIfTI installed, see http://www.siafoo.net/snippet/310 for instructions" exit(1) nim = NiftiImage(data_set) img_data = nim.data elif data_set.endswith('hdr'): # Use the header to figure out the shape of the data # then load the raw data and reshape the array shape = [int(x) for x in open(data_set).readline().split()] img_data = numpy.frombuffer(open(data_set.replace('.hdr', '.dat'), 'rb').read(), numpy.uint8)\ .reshape((shape[2], shape[1], shape[0])) img = vtkImageImportFromArray() img.SetArray(img_data) return img
def __init__(self, parent, data_set): wxVTKRenderWindowInteractor.__init__(self, parent, -1, size=parent.GetSize()) ren = vtk.vtkRenderer() self.GetRenderWindow().AddRenderer(ren) # prob should allow a string as data_set also, but for now assume it's a python or numpy array #img = self.LoadVolumeData(data_set) # load from filename img = vtkImageImportFromArray() img.SetArray(data_set) pix_diag = 5.0 # volMapper = vtk.vtkVolumeTextureMapper3D() volMapper = vtk.vtkVolumeRayCastMapper() compositeFunction = vtk.vtkVolumeRayCastCompositeFunction() compositeFunction.SetCompositeMethodToInterpolateFirst() volMapper.SetVolumeRayCastFunction(compositeFunction) volMapper.SetSampleDistance(pix_diag / 5.0) volMapper.SetInputConnection(img.GetOutputPort()) # Transfer Functions self.opacity_tf = vtk.vtkPiecewiseFunction() self.color_tf = vtk.vtkColorTransferFunction() # The property describes how the data will look self.volProperty = volProperty = vtk.vtkVolumeProperty() volProperty.SetColor(self.color_tf) volProperty.SetScalarOpacity(self.opacity_tf) volProperty.ShadeOn() volProperty.SetInterpolationTypeToLinear() volProperty.SetScalarOpacityUnitDistance(pix_diag) vol = vtk.vtkVolume() vol.SetMapper(volMapper) vol.SetProperty(volProperty) ren.AddVolume(vol) boxWidget = vtk.vtkBoxWidget() boxWidget.SetInteractor(self) boxWidget.SetPlaceFactor(1.0) # The implicit function vtkPlanes is used in conjunction with the # volume ray cast mapper to limit which portion of the volume is # volume rendered. planes = vtk.vtkPlanes() def ClipVolumeRender(obj, event): obj.GetPlanes(planes) volMapper.SetClippingPlanes(planes) # Place the interactor initially. The output of the reader is used to # place the box widget. boxWidget.SetInput(img.GetOutput()) boxWidget.PlaceWidget() boxWidget.InsideOutOn() boxWidget.AddObserver("InteractionEvent", ClipVolumeRender) outline = vtk.vtkOutlineFilter() outline.SetInputConnection(img.GetOutputPort()) outlineMapper = vtk.vtkPolyDataMapper() outlineMapper.SetInputConnection(outline.GetOutputPort()) outlineActor = vtk.vtkActor() outlineActor.SetMapper(outlineMapper) outlineProperty = boxWidget.GetOutlineProperty() outlineProperty.SetRepresentationToWireframe() outlineProperty.SetAmbient(1.0) outlineProperty.SetAmbientColor(1, 1, 1) outlineProperty.SetLineWidth(3) selectedOutlineProperty = boxWidget.GetSelectedOutlineProperty() selectedOutlineProperty.SetRepresentationToWireframe() selectedOutlineProperty.SetAmbient(1.0) selectedOutlineProperty.SetAmbientColor(1, 0, 0) selectedOutlineProperty.SetLineWidth(3) ren.AddActor(outlineActor) style = vtk.vtkInteractorStyleTrackballCamera() self.SetInteractorStyle(style) self.t_graph = TransferGraph(self) self.SetFocus() # So we know when new values are added / changed on the tgraph self.t_graph.Connect(-1, -1, wx.wxEVT_COMMAND_SLIDER_UPDATED, self.OnTGraphUpdate) self.OnTGraphUpdate(None) self.lighting = True # This is the transfer graph self.t_graph.Show()