Skip to content
Snippets Groups Projects
Commit bf331469 authored by Andrew Maclean's avatar Andrew Maclean
Browse files

Added GenerateModelsFromLabels and some minor fixes

parent 8f2d3838
No related branches found
No related tags found
1 merge request!343Classes in python not in pythonic api 05
......@@ -235,6 +235,7 @@ This section includes ?vtkUnstructuredGrid?.
| Example Name | Description | Image |
| -------------- | ------------- | ------- |
[GenerateModelsFromLabels](/PythonicAPI/Medical/GenerateModelsFromLabels) | Create models from labeled volume data.
[MedicalDemo1](/PythonicAPI/Medical/MedicalDemo1) | Create a skin surface from volume data.
### Surface reconstruction
......
### Description
Sometimes it is helpful to view the results of a segmentation without any post processing. This example converts the point data from a labeled volume into cell data. The surfaces are displayed as vtkPolydata. If you want to created smoothed polydata models from your segmented volumes, see the example [GenerateModelsFromLabels](../GenerateModelsFromLabels). The input volume must be in [MetaIO format](http://www.vtk.org/Wiki/MetaIO/Documentation).
``` text
Usage: GenerateCubesFromLabels InputVolume.mhd StartLabel EndLabel
where
InputVolume is a meta file containing a 3 volume of discrete labels.
StartLabel is the first label to be processed
EndLabel is the last label to be processed
NOTE: There can be gaps in the labeling. If a label does not exist in the volume, it will be skipped.
```
!!! note
This original source code for this example is [here](https://gitlab.kitware.com/vtk/vtk/blob/395857190c8453508d283958383bc38c9c2999bf/Examples/Medical/Cxx/GenerateCubesFromLabels.cxx).
#!/usr/bin/env python3
from dataclasses import dataclass
# noinspection PyUnresolvedReferences
import vtkmodules.vtkInteractionStyle
# noinspection PyUnresolvedReferences
import vtkmodules.vtkRenderingOpenGL2
from vtkmodules.vtkCommonColor import vtkNamedColors
from vtkmodules.vtkCommonDataModel import (
vtkDataObject,
vtkDataSetAttributes
)
from vtkmodules.vtkCommonTransforms import vtkTransform
from vtkmodules.vtkFiltersCore import vtkThreshold
from vtkmodules.vtkFiltersGeneral import vtkTransformFilter
from vtkmodules.vtkFiltersGeometry import vtkGeometryFilter
from vtkmodules.vtkIOImage import vtkMetaImageReader
from vtkmodules.vtkImagingCore import vtkImageWrapPad
from vtkmodules.vtkInteractionWidgets import vtkCameraOrientationWidget
from vtkmodules.vtkRenderingCore import (
vtkActor,
vtkPolyDataMapper,
vtkRenderWindow,
vtkRenderWindowInteractor,
vtkRenderer
)
def main():
colors = vtkNamedColors()
file_name, start_label, end_label = get_program_parameters()
if start_label > end_label:
end_label, start_label = start_label, end_label
# Generate cubes from labels
# 1) Read the meta file
# 2) Convert point data to cell data
# 3) Convert to geometry and display
reader = vtkMetaImageReader(file_name=file_name)
reader.update()
# Pad the volume so that we can change the point data into cell
# data.
extent = reader.output.extent
padded_extent = (extent[0], extent[1] + 1, extent[2], extent[3] + 1, extent[4], extent[5] + 1)
pad = vtkImageWrapPad(output_whole_extent=padded_extent)
(reader >> pad).update()
# Copy the scalar point data of the volume into the scalar cell data
pad.output.cell_data.SetScalars(reader.output.point_data.scalars)
selector = vtkThreshold(input_array_to_process=(0, 0, 0,
vtkDataObject.FIELD_ASSOCIATION_CELLS,
vtkDataSetAttributes.SCALARS),
lower_threshold=start_label, upper_threshold=end_label)
# Shift the geometry by 1/2
transform = vtkTransform()
transform.Translate(-0.5, -0.5, -0.5)
transform_model = vtkTransformFilter(transform=transform)
geometry = vtkGeometryFilter()
mapper = vtkPolyDataMapper(scalar_range=(start_label, end_label),
scalar_mode=Mapper.ScalarMode.VTK_SCALAR_MODE_USE_CELL_DATA,
color_mode=Mapper.ColorMode.VTK_COLOR_MODE_MAP_SCALARS)
pad >> selector >> transform_model >> geometry >> mapper
actor = vtkActor(mapper=mapper)
renderer = vtkRenderer(background=colors.GetColor3d('DarkSlateBlue'))
render_window = vtkRenderWindow(size=(640, 480), window_name='GenerateCubesFromLabels')
render_window.AddRenderer(renderer)
render_window_interactor = vtkRenderWindowInteractor()
render_window_interactor.render_window = render_window
renderer.AddActor(actor)
render_window.Render()
camera = renderer.GetActiveCamera()
camera.position = (130.171200, 942.438334, -262.344068)
camera.focal_point = (279.491372, 262.325784, 172.209964)
camera.view_up = (0.235239, -0.486113, -0.841639)
camera.distance = 820.784260
camera.clipping_range = (224.710879, 1514.926115)
omw = vtkCameraOrientationWidget(parent_renderer=renderer)
# Enable the widget.
omw.On()
render_window_interactor.Start()
def get_program_parameters():
import argparse
description = 'Convert the point data from a labeled volume into cell data.'
epilogue = '''
The surfaces are displayed as vtkPolydata.
'''
parser = argparse.ArgumentParser(description=description, epilog=epilogue,
formatter_class=argparse.RawDescriptionHelpFormatter)
parser.add_argument('filename', help='Input volume e.g. Frog/frogtissue.mhd.')
parser.add_argument('startlabel', type=int, help='The starting label in the input volume, e,g, 1.')
parser.add_argument('endlabel', type=int, help='The ending label in the input volume e.g. 29')
args = parser.parse_args()
return args.filename, args.startlabel, args.endlabel
@dataclass(frozen=True)
class Mapper:
@dataclass(frozen=True)
class ColorMode:
VTK_COLOR_MODE_DEFAULT: int = 0
VTK_COLOR_MODE_MAP_SCALARS: int = 1
VTK_COLOR_MODE_DIRECT_SCALARS: int = 2
@dataclass(frozen=True)
class ResolveCoincidentTopology:
VTK_RESOLVE_OFF: int = 0
VTK_RESOLVE_POLYGON_OFFSET: int = 1
VTK_RESOLVE_SHIFT_ZBUFFER: int = 2
@dataclass(frozen=True)
class ScalarMode:
VTK_SCALAR_MODE_DEFAULT: int = 0
VTK_SCALAR_MODE_USE_POINT_DATA: int = 1
VTK_SCALAR_MODE_USE_CELL_DATA: int = 2
VTK_SCALAR_MODE_USE_POINT_FIELD_DATA: int = 3
VTK_SCALAR_MODE_USE_CELL_FIELD_DATA: int = 4
VTK_SCALAR_MODE_USE_FIELD_DATA: int = 5
if __name__ == '__main__':
main()
......@@ -7,7 +7,7 @@ Snippets are chunks of code that can be cut (*snipped*) and pasted into examples
| Snippet | Description | |
| -------------- | ------------- | ------- |
[CameraPosition](/PythonicAPI/Snippets/CameraPosition.md) | Read all VTK polydata file types.
[CameraPosition](/PythonicAPI/Snippets/CameraPosition.md) | Get the camera position and focal point.
[CheckVTKVersion](/PythonicAPI/Snippets/CheckVTKVersion.md) | Check the VTK version returning `True` if the requested VTK version is >= the current version.
[DrawViewportBorder](/PythonicAPI/Snippets/DrawViewportBorder.md) | Draw a border around a renderer's viewport.
[GetProgramParameters](/PythonicAPI/Snippets/GetProgramParameters.md) | Get the program parameters.
......
......@@ -21,7 +21,7 @@ def camera_modified_callback(caller, event):
res += f'\tcamera.position = ({", ".join(map("{0:0.6f}".format, caller.position))})\n'
res += f'\tcamera.focal_point = ({", ".join(map("{0:0.6f}".format, caller.focal_point))})\n'
res += f'\tcamera.view_up = ({", ".join(map("{0:0.6f}".format, caller.view_up))})\n'
res += f'\tcamera.distance = ({"{0:0.6f}".format(caller.GetDistance())})\n'
res += f'\tcamera.distance = {"{0:0.6f}".format(caller.GetDistance())}\n'
res += f'\tcamera.clipping_range = ({", ".join(map("{0:0.6f}".format, caller.clipping_range))})\n'
print(res)
......
src/Testing/Baseline/PythonicAPI/Medical/TestGenerateCubesFromLabels.png

131 B

0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment