当前位置: 首页 > news >正文

【DICOM后处理】qt+vs 实现DICOM数据四视图显示

目录

  • 1、DICOM四视图
  • 2、vtkImageViewer2 实现二维平面图显示
  • 3、vtkVolume实现三维体数据显示
  • 4、实现界面图

1、DICOM四视图

DICOM四视图通常指同时显示医学影像的四个不同平面或视角,用于全面分析三维数据(如CT、MRI等)。

标准四视图布局:

  • 横截面(Axial)
    水平切面,从上向下观察(类似传统CT/MRI的横断面切片)。
    显示解剖结构的横向分布,常用于定位病变。
  • 矢状面(Sagittal)
    垂直切面,从身体左侧向右侧观察(将人体分为左右两部分)。
    适用于观察脊柱、脑部中线结构等。
  • 冠状面(Coronal)
    垂直切面,从前向后观察(将人体分为前后两部分)。
    常用于评估肺部、骨盆或对称性结构。
  • 3D重建/MPR(Multi-Planar Reconstruction)
    三维体积渲染或斜切面重建,提供任意角度的视角。
    用于复杂解剖(如血管、骨骼)的可视化。

2、vtkImageViewer2 实现二维平面图显示

vtkImageViewer2:

vtkSmartPointer<vtkImageViewer2> Viewer = vtkSmartPointer<vtkImageViewer2>::New();
vtkSmartPointer<vtkGenericOpenGLRenderWindow> RW = vtkSmartPointer<vtkGenericOpenGLRenderWindow>::New();
vtkSmartPointer<vtkGenericRenderWindowInteractor> RWInteractor = vtkSmartPointer<vtkGenericRenderWindowInteractor>::New();Viewer->SetRenderWindow(RW);
Viewer->SetupInteractor(RWInteractor);

设置图像数据和其他设置:

Viewer->SetInputData(inputData);Viewer->SetColorLevel(100);
Viewer->SetColorWindow(800);Viewer->SetSliceOrientationToXY();   //横断面
Viewer->SetSliceOrientationToXZ();   //冠状面
Viewer->SetSliceOrientationToYZ();   //矢状面

实现图像翻转:
SetViewUp() 方法用于 设置 2D 视图的“向上”方向,即定义图像在屏幕坐标系中的朝向。该方法直接影响影像的显示方向,尤其在多平面重建(MPR)或非标准切面显示时至关重要。
调整 ViewUp 可以旋转或翻转影像,使其符合解剖学标准(如医学影像的“头朝上”显示)。

标准化解剖视图

  • 轴向切面(Axial):
    默认 ViewUp = (0, -1, 0)(DICOM 标准,患者的“前”方向指向屏幕上方)。
    SetViewUp(0, -1, 0); // 屏幕 Y 轴向下(符合医学影像惯例)
  • 矢状切面(Sagittal):
    SetViewUp(0, 0, 1); // 屏幕 Y 轴朝向患者头部
  • 冠状切面(Coronal):
    SetViewUp(0, 0, 1); // 屏幕 Y 轴朝向患者头部

SetPosition:方法用于 设置渲染窗口在屏幕上的显示位置(以像素为单位)。它控制的是 VTK 渲染窗口的左上角在屏幕坐标系中的坐标位置。
默认朝向原点 (0, 0, 0)

2D 影像视图通常用 SetParallelProjection(1)(正交投影)。
3D 视图用默认的透视投影。

vtkCamera* camera = Viewer->GetRenderWindow()->GetRenderers()->GetFirstRenderer()->GetActiveCamera();
camera->SetViewUp(0, -1, 0);
camera->SetPosition(0, 0, -1); // 从 Z=Superior 方向看

把每个Viewer添加进对应的QtWidget:

ui->Widget->SetRenderWindow(RW);
ui->Widget->GetRenderWindow()->SetInteractor(RWInteractor);

渲染并交互

viewer->Render();
viewer->GetRenderWindow()->GetInteractor()->Start();

3、vtkVolume实现三维体数据显示

设置体数据:

vtkSmartPointer<vtkVolume> volume = vtkSmartPointer<vtkVolume>::New()
vtkSmartPointer<vtkRenderer> volumeRenderer = vtkSmartPointer<vtkRenderer>::New();

根据不同的应用平台,选择不用的RenderWindow类:

//常规应用
vtkSmartPointer<vtkRenderWindow> volumeRW = vtkSmartPointer<vtkRenderWindow>::New();
//跨平台应用
vtkSmartPointer<vtkGenericOpenGLRenderWindow> volumeRW = vtkSmartPointer<vtkGenericOpenGLRenderWindow>::New();
//Windows平台
vtkSmartPointer<vtkWin32OpenGLRenderWindow> volumeRW = vtkSmartPointer<vtkWin32OpenGLRenderWindow>::New();
//X11平台
vtkSmartPointer<vtkXOpenGLRenderWindow> volumeRW = vtkSmartPointer<vtkXOpenGLRenderWindow>::New();
//macOS平台
vtkSmartPointer<vtkCocoaRenderWindow> volumeRW = vtkSmartPointer<vtkCocoaRenderWindow>::New();

设置与RenderWindow匹配的Interactor:

vtkSmartPointer<vtkGenericRenderWindowInteractor> volumeRWInteractor = vtkSmartPointer<vtkGenericRenderWindowInteractor>::New();volumeRW->AddRenderer(volumeRenderer);
volumeRWInteractor->SetRenderWindow(volumeRW);

修改3D视图的投影方式:透视投影or正交(即平行)投影:

	volumeRenderer->GetActiveCamera()->ParallelProjectionOn();  //正交视图volumeRenderer->GetActiveCamera()->ParallelProjectionOff();  //投影视图//或者://flag = 1 或 true:启用平行投影(正交投影)//flag = 0 或 false:禁用平行投影(恢复为透视投影)volumeRenderer->GetActiveCamera()->SetParallelProjection(int flag);

添加至页面的QtWidget窗口:

ui->Widget->SetRenderWindow(volumeRW);
ui->Widget->GetRenderWindow()->SetInteractor(volumeRWInteractor);

设置映射器(Mapper):

//GPU
vtkSmartPointer<vtkGPUVolumeRayCastMapper> volumeMapper = vtkSmartPointer<vtkGPUVolumeRayCastMapper>::New();
//CPU
vtkSmartPointer<vtkFixedPointVolumeRayCastMapper> volumeMapper = vtkSmartPointer<vtkFixedPointVolumeRayCastMapper>::New();
volumeMapper->SetInputData(InputData);
volumeMapper->Update();

定义了体数据(如 CT、MRI 或其他 3D 体数据)的 颜色、不透明度、光照、梯度 等属性,直接影响最终渲染效果:

vtkSmartPointer<vtkVolumeProperty> volumeProperty = vtkSmartPointer<vtkVolumeProperty>::New();
volumeProperty->SetInterpolationTypeToLinear();
volumeProperty->ShadeOff();                     //Off/On:Turn Off/On Shadow Test

vtkVolumeProperty::SetScalarOpacity:基于 标量值 设置不透明度(控制不同组织的显示),显示骨骼or显示高密度流体等
vtkVolumeProperty::SetGradientOpacity:基于 梯度值 设置不透明度(突出边缘或界面),突出软组织边界or锐化流体界面等

//Set Opacity
vtkSmartPointer<vtkPiecewiseFunction> compositeOpacity = vtkSmartPointer<vtkPiecewiseFunction>::New();
compositeOpacity->AddPoint(0.0, 0.00);   //标量值 0 → 不透明度 0(完全透明)
compositeOpacity->AddPoint(125, 0.50);   //标量值 125 → 不透明度 0.5
compositeOpacity->AddPoint(256, 1.00);   //标量值 256 → 不透明度 1(完全不透明)volumeProperty->SetScalarOpacity(compositeOpacity);vtkSmartPointer<vtkPiecewiseFunction> volumeGradientOpacity = vtkSmartPointer<vtkPiecewiseFunction>::New();
volumeGradientOpacity->AddPoint(0.0, 0.0);     // 低梯度(均匀区域)→ 透明
volumeGradientOpacity->AddPoint(100, 0.4);     // 中梯度(边界)→ 半透明
volumeGradientOpacity->AddPoint(200, 1.0);     // 高梯度(锐利边缘)→ 不透明volumeProperty->SetGradientOpacity(volumeGradientOpacity);

定义体数据的颜色映射,将标量值转换为可视化的颜色:

vtkSmartPointer<vtkColorTransferFunction> color = vtkSmartPointer<vtkColorTransferFunction>::New();
color->AddRGBPoint(0, 0., 0., 0.);
color->AddRGBPoint(125, 0.0, 1.0, 0.0);
color->AddRGBPoint(256, 1.0, 0.0, 0.0);volumeProperty->SetColor(color);

更新设置到volume:

volume->SetMapper(m_volumeMapper);
volume->SetProperty(volumeProperty);
volume->Update();

渲染:

volumeRenderer->AddVolume(volume);
volumeRenderer->ResetCamera();
volumeRW->Render();

4、实现界面图

在这里插入图片描述

http://www.dtcms.com/a/264807.html

相关文章:

  • LeetCode--39.组合总和
  • Oracle 数据塑形:行列转换与集合运算
  • QT记事本3——下拉框comboBox、下拉框编码值传给QTextStream类
  • 【BERT_Pretrain】Wikipedia_Bookcorpus数据预处理(二)
  • Electron 快速上手
  • vscode vim插件示例json意义
  • C++ 第四阶段 文件IO - 第一节:ifstream/ofstream操作
  • JavaScript---查询数组符合条件的元素
  • 解决 npm install canvas@2.11.2 失败的问题
  • 【公司环境下发布个人NPM包完整教程】
  • SPI、I2C和UART三种串行通信协议的--------简单总结
  • NLP:文本张量表示方法
  • 【安全工具】SQLMap 使用详解:从基础到高级技巧
  • 【字节跳动】数据挖掘面试题0001:打车场景下POI与ODR空间关联查询
  • C++实现状态机
  • 20250703|Leetcodehot100之739【】今天计划
  • Linux环境下使用 C++ 与 OpenCV 实现 ONNX 分类模型推理
  • 洛谷P2119 [NOIP 2016 普及组] 魔法阵【题解】【前缀和优化】
  • Java 大视界 -- Java 大数据在智能医疗健康管理中的慢性病风险预测与个性化干预(330)
  • Javaee 多线程 --进程和线程之间的区别和联系
  • nvm:NodeJs版本管理工具下载安装与使用教程
  • macOS挂载iOS应用沙盒文件夹
  • 飞算 JavaAI 智控引擎:全链路开发自动化新图景
  • 【字节跳动】数据挖掘面试题0003:有一个文件,每一行是一个数字,如何用 MapReduce 进行排序和求每个用户每个页面停留时间
  • 橡胶硬度计在不同领域中的应用
  • mybatis考试
  • 无人机一机多控技术的核心要点
  • 亿级物联网MQTT集群:OpenResty深度优化实践
  • Docker for Windows 设置国内镜像源教程
  • 基于spark的航班价格分析预测及可视化