基于VTK实现面绘制(SR)和体绘制(VR)的基本代码

来源:互联网 发布:linux查询应用占用端口 编辑:程序博客网 时间:2024/06/05 11:57

本文由Markdown语法编辑器编辑完成。

1. 医学影像与三维可视化

2. 面绘制和体绘制的实现原理

2.1 面绘制 (Surface Rendering)

  VTK中基于面绘制实现三维重建,使用的是经典的Marching Cubes(移动立方体法)算法。
  
  面绘制是采用分割技术对一系列的二维图像进行轮廓识别、提取等操作,最终还原出被检测物体的三维模型,并以表面的方式显示出来。

  面绘制的数据流管道pipeline结构为:
读取器->提取等值面->数据处理->映射器->实例化角色->绘制器->绘制窗口->交互器->交换方式。

Marching Cubes算法简介:
首先,假定原始数据是离散的三维空间规则数据场;
其次,给出所求等值面的值;
最后,找出等值面经过的体元位置,求出该体元内的等值面并计算出相关参数(以便由常用的图形软件包或图形硬件提供的面绘制功能绘制等值面)。

VTK提供了两种提取等值面的类:
(1) vtkContourFilter
(2) vtkMarchingCubes.
VTK通过vtkPolyDataNormals在等值面上产生法向量;通过vtkStripper在等值面上产生纹理或三角面片。

由于vtk 从6.0版本后将管道连接的代码进行了修改。因此,如果是运用vtk 6.0以上版本的代码运行该例程,管道的连接函数为:SetInputConnection()和GetOutputPort().

/////////////////////////////////////////////////////////////////////////////////////////
//该代码在vtk 6.3,windows7操作系统上运行。

// VTK headers#include "vtkVolume16Reader.h"#include "vtkRenderWindowInteractor.h"#include "vtkRenderer.h"#include "vtkRenderWindow.h"#include "vtkMarchingCubes.h"#include "vtkStripper.h"#include "vtkActor.h"#include "vtkPolyDataMapper.h"#include "vtkProperty.h"#include "vtkCamera.h"//#include "vtkBoxWidget.h"#include <iostream>int main() {//读取二维切片数据序列vtkVolume16Reader *reader = vtkVolume16Reader::New();reader->SetDataDimensions(64, 64); //设置像素reader->SetDataByteOrderToLittleEndian();reader->SetFilePrefix("D:\\vtk\\vtkdata\\Data\\headsq\\quarter");//设置读取路径reader->SetImageRange(1, 93);reader->SetDataSpacing(3.2, 3.2, 1.5);//抽取等值面为骨头的信息vtkMarchingCubes *boneExtractor = vtkMarchingCubes::New();boneExtractor->SetInputConnection(reader->GetOutputPort());boneExtractor->SetValue(0,500); //设置提取的等值信息//剔除旧的或废除的数据单元,提高绘制速度vtkStripper *boneStripper = vtkStripper::New(); //三角带连接//注意:vtk6.0以后的版本,管道的连接函数修改为了SetInputConnection()和GetOutputPort().boneStripper->SetInputConnection(boneExtractor->GetOutputPort());//建立映射vtkPolyDataMapper *boneMapper = vtkPolyDataMapper::New();//注意:vtk6.0以后的版本,管道的连接函数修改为了SetInputConnection()和GetOutputPort().boneMapper->SetInputConnection(boneStripper->GetOutputPort());//建立角色vtkActor *bone = vtkActor::New();bone->SetMapper(boneMapper);bone->GetProperty()->SetDiffuseColor(.1,.94,.52);bone->GetProperty()->SetSpecular(.3);bone->GetProperty()->SetSpecularPower(20);//标准句子//定义绘制器vtkRenderer *aRenderer = vtkRenderer::New();//定义绘制窗口vtkRenderWindow *renWin = vtkRenderWindow::New();renWin->AddRenderer(aRenderer);//定义窗口交互器vtkRenderWindowInteractor *iren = vtkRenderWindowInteractor::New();iren->SetRenderWindow(renWin);//创建一个cameravtkCamera *aCamera = vtkCamera::New();aCamera->SetViewUp(0,0,-1);aCamera->SetPosition(0,1,0);aCamera->SetFocalPoint(0,0,0);aRenderer->AddActor(bone);aRenderer->SetActiveCamera(aCamera);aRenderer->ResetCamera();aCamera->Dolly(1.5);aRenderer->SetBackground(0,0,0);aRenderer->ResetCameraClippingRange();/*vtkBoxWidget *boxWidget = vtkBoxWidget::New();boxWidget->SetInteractor(iren);boxWidget->SetPlaceFactor(1.25);boxWidget->SetProp3D(bone);boxWidget->PlaceWidget();*/iren->Initialize();iren->Start();reader->Delete();iren->Delete();return 0;}

运行结果如下图所示:
这里写图片描述

2.2 体绘制(Volume Rendering)

VTK中基于体绘制实现三维重建,使用的是光线投射法(Ray-casting)。

体绘制的原理和面绘制完全不相同。面绘制需要生成中间图元,而体绘制则是直接在原图上进行绘制,内容需求较面绘制小。每切换一个视角需要重新对所有的像素点进行颜色和透明度计算,需要时间比面绘制长。

VTK的管道结构实现体绘制需要的类有:
vtkRenderWindow, vtkRenderer, vtkLight, vtkCamera, vtkActor, vtkProperty, vtkTransform.

dataset->filter->mapper.

#include "vtkRenderWindowInteractor.h"#include "vtkDICOMImageReader.h"#include "vtkRenderWindow.h"#include "vtkCamera.h"#include "vtkActor.h"#include "vtkRenderer.h"#include "vtkProperty.h"#include "vtkPolyDataNormals.h"#include "vtkImageShiftScale.h"#include "vtkVolumeRayCastMapper.h"#include "vtkPiecewiseFunction.h"#include "vtkColorTransferFunction.h"#include "vtkVolumeProperty.h"#include "vtkVolumeRayCastCompositeFunction.h"#include <iostream>int main() {//标准句子//定义绘制器vtkRenderer *aRenderer = vtkRenderer::New();//定义绘制窗口vtkRenderWindow *renWin = vtkRenderWindow::New();renWin->AddRenderer(aRenderer);//定义窗口交互器vtkRenderWindowInteractor *iren = vtkRenderWindowInteractor::New();iren->SetRenderWindow(renWin);//CT格式数据读取类vtkDICOMImageReader *reader = vtkDICOMImageReader::New();//这里输入Dicom数据的文件夹的路径,读者需要根据数据在本机上的位置进行修改。reader->SetDirectoryName("D:\\TestData\\Brain");//图像数据预处理。常见两种操作。一种是类型转换,通过 vtkImageShiftScale 将不同类型的数据集转换为 VTK 可以处理的数据;//另一种是剔除冗余数据,通过 vtkStripper 放置无效的旧单元的存在,提高绘制速度。vtkImageShiftScale *shiftScale = vtkImageShiftScale::New();shiftScale->SetInputConnection(reader->GetOutputPort());shiftScale->SetOutputScalarTypeToUnsignedChar();//数据分类,找出数据与不同物质之间的对应关系,同时也为了在最终图像中以不同颜色表示单一物质的不同属性。//此处省略//………………//透明度映射函数定义//给数据点赋不透明值。体绘制中,需要显示三维数据场的内部结构,因而需要生成具有透明度的图像。vtkPiecewiseFunction *opacityTransferFunction = vtkPiecewiseFunction::New();opacityTransferFunction->AddPoint(20, 0.0);opacityTransferFunction->AddPoint(255, 0.2);//颜色映射函数定义//给数据点赋颜色值,将分类后的组织信息分别予以不同的颜色,便于图像分析。vtkColorTransferFunction *colorTransferFunction = vtkColorTransferFunction::New();colorTransferFunction->AddRGBPoint(0.0, 0.0, 0.0, 0.0);colorTransferFunction->AddRGBPoint(64.0, 1.0, 0.0, 0.0);colorTransferFunction->AddRGBPoint(128.0, 0.0, 0.0, 1.0);colorTransferFunction->AddRGBPoint(192.0, 0.0, 1.0, 0.0);colorTransferFunction->AddRGBPoint(255.0, 0.0, 0.2, 0.0);//体数据属性vtkVolumeProperty *volumeProperty = vtkVolumeProperty::New();volumeProperty->SetColor(colorTransferFunction);volumeProperty->SetScalarOpacity(opacityTransferFunction);volumeProperty->ShadeOn();volumeProperty->SetInterpolationTypeToLinear();//体绘制惯用语句://计算光照效应。采用光线类 vtkVolumeRayCastCompositeFunction 进行投射,//最终用 vtkVolumeRayCastMapper类进行光效应计算。vtkVolumeRayCastCompositeFunction *compositeFunction = vtkVolumeRayCastCompositeFunction::New();vtkVolumeRayCastMapper *volumeMapper = vtkVolumeRayCastMapper::New();volumeMapper->SetVolumeRayCastFunction(compositeFunction);volumeMapper->SetInput(shiftScale->GetOutput());vtkVolume *volume = vtkVolume::New();volume->SetMapper(volumeMapper);volume->SetProperty(volumeProperty);aRenderer->AddVolume(volume);aRenderer->SetBackground(1,1,1);renWin->SetSize(600, 600);renWin->Render();iren->Initialize();iren->Start();return 0;}

这里写图片描述

参考链接:

  1. VTK实现面绘制
    http://blog.sina.com.cn/s/blog_76e94d21010106gk.html
  2. VTK实现体绘制
    http://blog.sina.com.cn/s/blog_76e94d21010106gf.html
0 0