测试的三维模型为bunny,即斯坦福兔子
代码示例:
#include <vtkOBJReader.h>
#include <vtkSmartPointer.h>
#include <vtkCutter.h>
#include <vtkPolyDataMapper.h>
#include <vtkPlane.h>
#include <vtkProperty.h>
#include <vtkActor.h>
#include <vtkRenderer.h>
#include <vtkRenderWindow.h>
#include <vtkRenderWindowInteractor.h>
#include <vtkSphereSource.h>
#include <vtkPolyDataWriter.h>
#include <vtkPolyData.h>
#include <vtkStripper.h>
#include <vtkContourFilter.h>
#include <vtkPoints.h>
#include <iostream>
using namespace std;
double Distance(double *a,double *b)
{
double o=(a[0]-b[0])*(a[0]-b[0]);
double p=(a[1]-b[1])*(a[1]-b[1]);
double q=(a[2]-b[2])*(a[2]-b[2]);
return o+p+q;
}
int main()
{
//读取obj文件
vtkSmartPointer<vtkOBJReader> reader =vtkSmartPointer<vtkOBJReader>::New();
reader->SetFileName("C:\\Users\\HuangWang\\Desktop\\bunny-chuli.obj");
reader->Update();
vtkSmartPointer<vtkPolyData> inputPolyData=vtkSmartPointer<vtkPolyData>::New();
inputPolyData = reader->GetOutput();
vtkSmartPointer<vtkPolyDataMapper> inputMapper =vtkSmartPointer<vtkPolyDataMapper>::New();
inputMapper->SetInput(inputPolyData);
//创建切割平面
vtkSmartPointer<vtkPlane> plane =vtkSmartPointer<vtkPlane>::New();
plane->SetOrigin(inputPolyData->GetCenter());//设置切割平面起点
plane->SetNormal(1,0,0);//设置切割方向为X方向
//得到输入的obj模型的最小坐标
double minBound[3];
minBound[0] = inputPolyData->GetBounds()[0];
minBound[1] = inputPolyData->GetBounds()[2];
minBound[2] = inputPolyData->GetBounds()[4];
//得到输入的obj模型的最小大坐标
double maxBound[3];
maxBound[0] = inputPolyData->GetBounds()[1];
maxBound[1] = inputPolyData->GetBounds()[3];
maxBound[2] = inputPolyData->GetBounds()[5];
//得到输入的obj模型的中心坐标
double center[3];
center[0] = inputPolyData->GetCenter()[0];
center[1] = inputPolyData->GetCenter()[1];
center[2] = inputPolyData->GetCenter()[2];
double distanceMin=sqrt(Distance(minBound,center));
double distanceMax=sqrt(Distance(maxBound,center));
//创建模型切割器
vtkSmartPointer<vtkCutter> cutter =vtkSmartPointer<vtkCutter>::New();
cutter->SetCutFunction(plane);//设置切割平面
cutter->SetInput(inputPolyData);//设置模型
cutter->GenerateValues(30, -distanceMin, distanceMax);//在模型的最大最小范围内等间距创建30个切面,得到轮廓线
//将切线结果输出为vtk文件格式
vtkSmartPointer<vtkPolyData> ResultPoly=cutter->GetOutput();//输出为polydata
vtkSmartPointer<vtkPolyDataWriter> vtkWriter = vtkSmartPointer<vtkPolyDataWriter>::New();
vtkWriter->SetInput(cutter->GetOutput());
vtkWriter->SetFileName("C:\\Users\\HuangWang\\Desktop\\result.vtk");
vtkWriter->Write();
vtkSmartPointer<vtkPolyDataMapper> cutterMapper =
vtkSmartPointer<vtkPolyDataMapper>::New();
cutterMapper->SetInputConnection( cutter->GetOutputPort());
cutterMapper->ScalarVisibilityOff();
vtkSmartPointer<vtkActor> planeActor =
vtkSmartPointer<vtkActor>::New();
planeActor->GetProperty()->SetColor(1,0,0);
planeActor->GetProperty()->SetLineWidth(5);
planeActor->SetMapper(cutterMapper);
vtkSmartPointer<vtkActor> inputActor =
vtkSmartPointer<vtkActor>::New();
inputActor->GetProperty()->SetColor(0,1,0);
inputActor->SetMapper(inputMapper);
vtkSmartPointer<vtkRenderer> renderer =
vtkSmartPointer<vtkRenderer>::New();
renderer->AddActor(planeActor);
renderer->AddActor(inputActor);
vtkSmartPointer<vtkRenderWindow> renderWindow =
vtkSmartPointer<vtkRenderWindow>::New();
renderWindow->AddRenderer(renderer);
renderWindow->SetSize(600, 600);
vtkSmartPointer<vtkRenderWindowInteractor> interactor =
vtkSmartPointer<vtkRenderWindowInteractor>::New();
interactor->SetRenderWindow(renderWindow);
renderer->SetBackground(0,0,0);
renderWindow->Render();
interactor->Start();
return 0;
}
结果示例:
最后输出的结果VTK文件包含了每一条轮廓线的点数据
如果您觉得这篇博文有用,请访问我的个人站:http://www.stubbornhuang.com,更多博文干货等着您。