5.VTK 可视化管线
第三阶段 VTK可视化管线实战:Source、Filter、材质渲染模式
前面已经懂管线整体流程、vtkPolyData数据结构。本阶段重点:Source、Filter怎么串联,常用过滤器,修改物体外观(颜色、线框、透明度)。
回顾管线核心链条: Source → Filter(可0个或多个) → Mapper → Actor → Renderer
3.1 Source 数据源
Source的作用:生成/读取原始vtkDataSet数据,输出数据集,不需要输入。 分为两类:
- 几何生成Source(程序造几何体)
vtkSphereSource球体、vtkCubeSource立方体、vtkCylinderSource圆柱体、vtkConeSource圆锥 - 文件读取Source(读磁盘文件)
vtkSTLReader读取stl、vtkOBJReader读取obj
示例:立方体Source,只看关键片段
vtkSmartPointer<vtkCubeSource> cubeSource = vtkSmartPointer<vtkCubeSource>::New();
cubeSource->SetXLength(4); //X方向长度
cubeSource->SetYLength(4);
cubeSource->SetZLength(4);
cubeSource->Update(); //触发生成网格
Source统一行为:
- 一堆SetXXX设置参数
- 调用
Update()真正计算生成数据 GetOutput()拿到输出数据集(vtkPolyData)
3.2 Filter 过滤器(管线最重要的数据处理环节)
Filter:接收一份输入数据集,处理之后输出一份新的数据集。 可以多个Filter首尾串联:
source → filterA → filterB → mapper
核心接口
filter->SetInputData(输入数据集); //设置输入
filter->Update(); //执行处理算法
filter->GetOutput(); //拿到处理后的结果
注意:
SetInputData()接收的是数据集(vtkPolyData等)。 你可以直接拿source/上一个filter的GetOutput()传进去。
示例1:vtkCleanPolyData 清理冗余点过滤器
场景:模型有大量重复重合点,占用内存、渲染异常,用这个过滤器清理合并重合点。
// sphereSource是球体数据源
vtkSmartPointer<vtkCleanPolyData> cleanFilter = vtkSmartPointer<vtkCleanPolyData>::New();
cleanFilter->SetInputData(sphereSource->GetOutput()); //接入球体输出
cleanFilter->SetTolerance(0.001); //距离小于这个阈值就判定为重合点,进行合并
cleanFilter->Update();
// 把filter输出交给mapper,而不是直接用sphereSource输出
mapper->SetInputData(cleanFilter->GetOutput());
管线链路:sphereSource → cleanFilter → mapper
示例2:串联多个Filter
球体 → 清理点 → 坐标变换
sphereSource → cleanFilter → transformFilter → mapper
vtkSmartPointer<vtkTransform> transform = vtkSmartPointer<vtkTransform>::New();
transform->Translate(2,0,0); //整体沿X轴平移2个单位
vtkSmartPointer<vtkTransformFilter> transformFilter = vtkSmartPointer<vtkTransformFilter>::New();
transformFilter->SetInputData(cleanFilter->GetOutput());
transformFilter->SetTransform(transform);
transformFilter->Update();
mapper->SetInputData(transformFilter->GetOutput());
✨小白铁律:
- 每一个Filter都要
Update()才会执行算法; - 串联的时候,后一个Filter的输入 = 前一个Filter的
GetOutput(); - Filter不会修改原始输入数据,输出是新生成一份数据。原始数据不受破坏。
几个高频入门Filter清单(记住名字,后面会反复用)
| Filter类名 | 功能 |
|---|---|
| vtkCleanPolyData | 合并重复点,清理无效面片 |
| vtkTransformFilter | 平移、旋转、缩放模型 |
| vtkClipPolyData | 按平面裁剪模型,切掉一部分 |
| vtkSmoothPolyDataFilter | 网格平滑 |
| vtkAppendPolyData | 把多个PolyData合并成一个 |
| vtkPolyDataNormals | 计算面片、点法向量,解决模型发黑 |
3.3 Actor Property:修改物体外观(材质、线框、透明度)
actor->GetProperty() 返回 vtkProperty 对象,控制物体显示模样,不改动底层网格数据,只改渲染表现。
常用接口示例:
vtkProperty* prop = actor->GetProperty();
prop->SetColor(1,0.3,0.3); // RGB颜色 0~1
prop->SetOpacity(0.5); // 透明度,0完全透明,1不透明
prop->SetRepresentationToSurface(); // 实体面渲染(默认)
prop->SetRepresentationToWireframe();// 只渲染线框,看不到面片填充
prop->SetRepresentationToPoints(); // 只渲染顶点点云
prop->SetEdgeVisibility(true); // 实体模式下,把面片边线显示出来
prop->SetEdgeColor(1,1,1); // 边线颜色白色
prop->SetPointSize(3); // 点模式下点的大小
prop->SetLineWidth(2); // 线框模式线宽
关键点:Representation 三种模式,只是渲染模式切换,不会修改vtkPolyData内部数据。比如切到线框模式,Points、Polys数据还完整保存在内存里。
完整可阅读Demo:球体经过Clean+平移Filter,线框显示
整合Source+两级Filter+修改渲染属性,完整代码,只看逻辑。
#include <vtkSmartPointer.h>
#include <vtkSphereSource.h>
#include <vtkCleanPolyData.h>
#include <vtkTransform.h>
#include <vtkTransformFilter.h>
#include <vtkPolyDataMapper.h>
#include <vtkActor.h>
#include <vtkRenderer.h>
#include <vtkRenderWindow.h>
#include <vtkRenderWindowInteractor.h>
int main()
{
//1.Source 球体
vtkSmartPointer<vtkSphereSource> sphereSource = vtkSmartPointer<vtkSphereSource>::New();
sphereSource->SetRadius(3);
sphereSource->SetThetaResolution(20);
sphereSource->SetPhiResolution(20);
sphereSource->Update();
//2.Filter1:清理重复点
vtkSmartPointer<vtkCleanPolyData> cleanFilter = vtkSmartPointer<vtkCleanPolyData>::New();
cleanFilter->SetInputData(sphereSource->GetOutput());
cleanFilter->SetTolerance(0.001);
cleanFilter->Update();
//3.Filter2:X轴平移
vtkSmartPointer<vtkTransform> trans = vtkSmartPointer<vtkTransform>::New();
trans->Translate(1.5,0,0);
vtkSmartPointer<vtkTransformFilter> transFilter = vtkSmartPointer<vtkTransformFilter>::New();
transFilter->SetInputData(cleanFilter->GetOutput());
transFilter->SetTransform(trans);
transFilter->Update();
//4.Mapper 接收最后一个filter输出
vtkSmartPointer<vtkPolyDataMapper> mapper = vtkSmartPointer<vtkPolyDataMapper>::New();
mapper->SetInputData(transFilter->GetOutput());
//5.Actor 设置外观:线框模式,红色
vtkSmartPointer<vtkActor> actor = vtkSmartPointer<vtkActor>::New();
actor->SetMapper(mapper.Get());
actor->GetProperty()->SetColor(1,0.2,0.2);
actor->GetProperty()->SetRepresentationToWireframe(); //线框渲染
//渲染交互部分不变
vtkSmartPointer<vtkRenderer> renderer = vtkSmartPointer<vtkRenderer>::New();
renderer->AddActor(actor);
renderer->SetBackground(0,0,0);
vtkSmartPointer<vtkRenderWindow> renderWindow = vtkSmartPointer<vtkRenderWindow>::New();
renderWindow->AddRenderer(renderer);
renderWindow->SetSize(800,600);
vtkSmartPointer<vtkRenderWindowInteractor> interactor = vtkSmartPointer<vtkRenderWindowInteractor>::New();
interactor->SetRenderWindow(renderWindow);
interactor->Initialize();
interactor->Start();
return 0;
}
管线链路: sphereSource → cleanFilter → transFilter → mapper → actor
运行效果:窗口显示一个向右偏移的红色线框球体。
本阶段重点小结
- Source只输出数据,无输入;Filter有输入有输出,可以串联;
SetInputData()连接管线,Update()触发计算,GetOutput()拿结果;- Filter处理会输出新数据集,原始输入数据不会被修改;
vtkProperty控制外观:颜色、透明度、实体/线框/点模式,只改渲染,不改网格数据。
新手高频坑
- Filter串联,Mapper错误的拿最开头source的输出,Filter完全没生效;
- 忘记Filter的
Update(),拿到空数据; - 混淆:SetRepresentationToWireframe只是渲染模式,不是把模型变成线几何。

浙公网安备 33010602011771号