ITK的数据流采用如图1所示流水线(pipeline)作业方式。遵循此方式,所处理的数据来龙去脉清晰明了。在图1中,数据流左边的ImageFile代表待处理的图像文件,而右边ImageFile则代表处理后的图像文件。ImageFileReade:将存贮图像文件读人到内存,形成Image,再调用所希望处理的Fileter算法(比如滤波、分割、配准等具体算法),将对读人的图像数据进行处理。最后,ImageFileWriter将处理的图像数据结果保存,或输人给图形显示系统(如VTK),进行数据可视化。

VTK是C++语言开发的、公开源码的、面向对象的数据可视化软件开发包,并不单纯用于医学图像数据的可视化。VTK支持跨平台的编译,可以应用于Windows,Linux等系统。VTK支持包括数量、向量、张量、结构和测定体积等方法一系列可视化算法,VTK还支持包括建模。VTK的数据流同样采用流水线作业方式,如图2所示。

vtkSource为整个可视化流的开始,比如读取、生成数据等。vtkFilte对输入源数据进行各种处理,与ITK的Fileter类似。原始数据经过各种Filte:的处理后,再由vtkMappe:转换(或映射)成可供其它算法模块直接使用的数据形式,比如为几何数据。vtkActor类用来描述绘制场景中一个实体,即绘制场景的某个角色(Actor)。通过SetMapper()方法,可以将几何数据的属性传递给Actor,再由vtkRenderer类将处理后的数据结果显示出来。
由于ITK和VTK的数据流都是采用流水线作业形式,比较方便地利用类库本身提供的类型转换类来实现,如图3所示。通过ITKtoVTKImageFilter类操作将ITK和VTK的图像数据连接了起来,VTK负责图像数据的显示,而ITK负责图像的处理,其中VTK的Image Viewe:是一个很方便实现的图像显示类,它在内部管理着vtkImageWindow, vtkRenderer, vtkActor2D和vtkImageMapper等图象类,实现图像查看、显示和可视化功能。

**下面具体解释下ITK对象到VTK对象的两种转换方式:**
**第一种**方式是使用**itkImageToVTKImageFilter**类
通过例子来说明:
#include "itkImage.h"
#include "itkImageFileReader.h"
#include "itkImageToVTKImageFilter.h"
#include "vtkImageViewer.h"
#include "vtkRenderWindowInteractor.h"
int main( int argc, char **argv )
{
typedef itk::Image< unsigned short, 2 > ImageType;
typedef itk::ImageFileReader<ImageType> ReaderType;
typedef itk::ImageToVTKImageFilter< ImageType> FilterType;
ReaderType::Pointer reader = ReaderType::New();
FilterType::Pointer connector = FilterType::New();
reader->SetFileName( "d:\\1.png");
connector->SetInput( reader->GetOutput() );
vtkImageViewer * viewer = vtkImageViewer::New();
vtkRenderWindowInteractor * renderWindowInteractor = vtkRenderWindowInteractor::New();
viewer->SetupInteractor( renderWindowInteractor );
viewer->SetInput( connector->GetOutput() );
viewer->Render();
viewer->SetColorWindow( 255 );
viewer->SetColorLevel( 128 );
renderWindowInteractor->Start();
return 0;
}
例子如下:
#include "itkCommand.h"
#include "itkImage.h"
#include "itkVTKImageExport.h"
#include "itkVTKImageImport.h"
#include "itkCurvatureFlowImageFilter.h"
#include "itkCastImageFilter.h"
#include "itkRGBPixel.h"
#include "itkImageFileReader.h"
#include "itkImageFileWriter.h"
#include "vtkImageData.h"
#include "vtkImageImport.h"
#include "vtkImageExport.h"
#include "vtkImageActor.h"
#include "vtkRenderer.h"
#include "vtkRenderWindow.h"
#include "vtkRenderWindowInteractor.h"
#include "vtkInteractorStyleImage.h"
#include "itkPNGImageIO.h"
/**
* This will be setup as a callback for a progress event on an ITK
* filter.
*/
struct ProgressDisplay
{
ProgressDisplay(itk::ProcessObject* process): m_Process(process) {}
void Display()
{
float progress = m_Process->GetProgress()*100.0;
std::cout << "Progress " << progress << " percent." << std::endl;
}
itk::ProcessObject::Pointer m_Process;
};
/**
* This function will connect the given itk::VTKImageExport filter to
* the given vtkImageImport filter.
*/
template <typename ITK_Exporter, typename VTK_Importer> void ConnectPipelines(ITK_Exporter exporter, VTK_Importer* importer) { importer->SetUpdateInformationCallback(exporter->GetUpdateInformationCallback()); importer->SetPipelineModifiedCallback(exporter->GetPipelineModifiedCallback()); importer->SetWholeExtentCallback(exporter->GetWholeExtentCallback()); importer->SetSpacingCallback(exporter->GetSpacingCallback()); importer->SetOriginCallback(exporter->GetOriginCallback()); importer->SetScalarTypeCallback(exporter->GetScalarTypeCallback()); importer->SetNumberOfComponentsCallback(exporter->GetNumberOfComponentsCallback()); importer->SetPropagateUpdateExtentCallback(exporter->GetPropagateUpdateExtentCallback()); importer->SetUpdateDataCallback(exporter->GetUpdateDataCallback()); importer->SetDataExtentCallback(exporter->GetDataExtentCallback()); importer->SetBufferPointerCallback(exporter->GetBufferPointerCallback()); importer->SetCallbackUserData(exporter->GetCallbackUserData()); }
/**
* This function will connect the given vtkImageExport filter to
* the given itk::VTKImageImport filter.
*/
template <typename VTK_Exporter, typename ITK_Importer> void ConnectPipelines(VTK_Exporter* exporter, ITK_Importer importer) { importer->SetUpdateInformationCallback(exporter->GetUpdateInformationCallback()); importer->SetPipelineModifiedCallback(exporter->GetPipelineModifiedCallback()); importer->SetWholeExtentCallback(exporter->GetWholeExtentCallback()); importer->SetSpacingCallback(exporter->GetSpacingCallback()); importer->SetOriginCallback(exporter->GetOriginCallback()); importer->SetScalarTypeCallback(exporter->GetScalarTypeCallback()); importer->SetNumberOfComponentsCallback(exporter->GetNumberOfComponentsCallback()); importer->SetPropagateUpdateExtentCallback(exporter->GetPropagateUpdateExtentCallback()); importer->SetUpdateDataCallback(exporter->GetUpdateDataCallback()); importer->SetDataExtentCallback(exporter->GetDataExtentCallback()); importer->SetBufferPointerCallback(exporter->GetBufferPointerCallback()); importer->SetCallbackUserData(exporter->GetCallbackUserData()); }
/**
* This program implements an example connection between ITK and VTK
* pipelines. The combined pipeline flows as follows:
*
* itkImageFileReader ==> itkVTKImageExport ==>
* vtkImageImport ==> vtkImageActor
*
* The resulting vtkImageActor is displayed in a vtkRenderWindow.
* Whenever the VTK pipeline executes, information is propagated
* through the ITK pipeline. If the ITK pipeline is out of date, it
* will re-execute and cause the VTK pipeline to update properly as
* well.
*/
int main(int argc, char * argv [] )
{
// Load a color image using ITK and display it with VTK
try
{
typedef itk::RGBPixel< unsigned char > PixelType;
typedef itk::Image< PixelType, 2 > ImageType;
typedef itk::ImageFileReader< ImageType > ReaderType;
ReaderType::Pointer reader = ReaderType::New();
reader->SetFileName("d:\\1.png");
reader->Update();
typedef itk::VTKImageExport< ImageType > ExportFilterType; ExportFilterType::Pointer itkExporter = ExportFilterType::New(); itkExporter->SetInput( reader->GetOutput() );
// Create the vtkImageImport and connect it to the
// itk::VTKImageExport instance.
vtkImageImport* vtkImporter = vtkImageImport::New();
ConnectPipelines(itkExporter, vtkImporter);
// Just for double checking export it from VTK back into ITK
// and save it into a file.
typedef itk::VTKImageImport< ImageType > ImportFilterType; ImportFilterType::Pointer itkImporter = ImportFilterType::New(); vtkImageExport* vtkExporter = vtkImageExport::New(); ConnectPipelines(vtkExporter, itkImporter);
vtkExporter->SetInput( vtkImporter->GetOutput() );
typedef itk::ImageFileWriter< ImageType > WriterType;
WriterType::Pointer itkWriter = WriterType::New();
itkWriter->SetInput( itkImporter->GetOutput() );
const char * filename = "d:\\2.png";
std::cout << "Writing file " << filename << std::endl;
itkWriter->SetFileName( filename );
itkWriter->Update();
//------------------------------------------------------------------------
// VTK pipeline.
//------------------------------------------------------------------------
// Create a vtkImageActor to help render the image. Connect it to
// the vtkImporter instance.
vtkImageActor* actor = vtkImageActor::New();
actor->SetInput(vtkImporter->GetOutput());
vtkInteractorStyleImage * interactorStyle = vtkInteractorStyleImage::New();
// Create a renderer, render window, and render window interactor to
// display the results.
vtkRenderer* renderer = vtkRenderer::New();
vtkRenderWindow* renWin = vtkRenderWindow::New();
vtkRenderWindowInteractor* iren = vtkRenderWindowInteractor::New();
renWin->SetSize(500, 500);
renWin->AddRenderer(renderer);
iren->SetRenderWindow(renWin);
iren->SetInteractorStyle( interactorStyle );
// Add the vtkImageActor to the renderer for display.
renderer->AddActor(actor);
renderer->SetBackground(0.4392, 0.5020, 0.5647);
// Bring up the render window and begin interaction.
renWin->Render();
iren->Start();
// Release all VTK components
actor->Delete();
interactorStyle->Delete();
vtkImporter->Delete();
vtkExporter->Delete();
renWin->Delete();
renderer->Delete();
iren->Delete();
}
catch( itk::ExceptionObject & e )
{
std::cerr << "Exception catched !! " << e << std::endl;
}
return 0;
}
【参考来源】:http://image.szpt.edu.cn/cn/Article_content.asp?id=311