CPR曲面重建代码

news2024/11/16 3:13:52

废话不说,直接上代码:

#include "vtkAutoInit.h"
#include "vtkPolyData.h"
#include "vtkProbeFilter.h"
#include "vtkParametricFunctionSource.h"
#include "vtkParametricSpline.h"
#include "vtkDICOMImageReader.h"
#include "vtkPoints.h"
#include "vtkCellArray.h"
#include "vtkWindowLevelLookupTable.h"
#include "vtkActor.h"
#include "vtkCamera.h"
#include "vtkNamedColors.h"
#include "vtkRenderer.h"
#include "vtkRenderWindow.h"
#include "vtkRenderWindowInteractor.h"
#include "vtkImageData.h"
#include "vtkDataSetMapper.h"

VTK_MODULE_INIT(vtkRenderingFreeType)
VTK_MODULE_INIT(vtkRenderingOpenGL2);
VTK_MODULE_INIT(vtkInteractionStyle);
VTK_MODULE_INIT(vtkRenderingVolumeOpenGL2);

// 由曲线生成曲面

vtkPolyData* SweepLine(vtkParametricFunctionSource* line, double direction[3], double distance, int cols)
{
    int rows = line->GetOutput()->GetNumberOfPoints(); //待生成的surface的行数为曲线上点的个数
    double spacing = distance / rows;           //列方向上的spacing
    vtkPolyData* surface = vtkPolyData::New();

    //生成点
    cols += 1;
    int numberOfPoints = rows * cols;       //surface内点的个数
    int numberOfPolys = (rows - 1) * (cols - 1);

    vtkPoints* points = vtkPoints::New();
    points->Allocate(numberOfPoints);
    vtkCellArray* polys = vtkCellArray::New();
    polys->Allocate(numberOfPolys);

    //生成每行每列的点坐标,
    double x[] = { 0.0, 0.0, 0.0 };
    int cnt = 0;

    for (int row = 0; row < rows; row++)
    {
        for (int col = 0; col < cols; col++) 
        {
            double p[3] = { 0.0,0.0,0.0 };
            line->GetOutput()->GetPoint(row, p);
            x[0] = p[0] + direction[0] * col * spacing;
            x[1] = p[1] + direction[1] * col * spacing;
            x[2] = p[2] + direction[2] * col * spacing;
            points->InsertPoint(cnt, x);
            cnt++;
        }
    }


    //生成四边形
    vtkIdType pts[4] = { 0,0,0,0 };
    for (int row = 0; row < rows - 1; row++)
    {
        for (int col = 0; col < cols - 1; col++)
        {
            pts[0] = col + row * cols;
            pts[1] = pts[0] + 1;
            pts[2] = pts[0] + cols + 1;
            pts[3] = pts[0] + cols;
         //   polys->InsertNextCell(4, pts);   //每临近的四个点构成一个单元
            polys->InsertNextCell(4, pts);
  
        }
    }

    surface->SetPoints(points);
    surface->SetPolys(polys);

    return surface;
}

int main(int argc, char* argv[])
{
    char szInputFile[] = { "D:/imgdata/2013-06-04_dcm" };
    
    vtkDICOMImageReader* reader = vtkDICOMImageReader::New();
    reader->SetDataByteOrderToLittleEndian();
    reader->SetDirectoryName(szInputFile);
    reader->Update();
    int resolution = 100;
    int extent[2] = { 255, 255 };
    double thickness = 1.0;
    double spacing[2] = { 1.0, 1.0 };

    //自定义折线顶点坐标
    vtkPoints* points = vtkPoints::New();
    //(a,b,c,d)其中a表示序号,(b,c,d)表示点的坐标
    points->InsertPoint(0, 1.0, 0.0, 0.0);
    points->InsertPoint(1, 200, 100, 0.0);
    points->InsertPoint(2, 100, 200, 0.0);
    points->InsertPoint(3, 200, 300, 0.0);

    //将点插值逆合成一条曲线
    vtkParametricSpline* spline = vtkParametricSpline::New();
    spline->SetPoints(points);
    vtkParametricFunctionSource* splineFilter = vtkParametricFunctionSource::New();
    splineFilter->SetParametricFunction(spline);
    splineFilter->Update();


    //有曲线生成曲面
    double direction[] = { 0.0, 0.0, 1.0 };
    int distance = 160;
    vtkPolyData* surface = SweepLine(splineFilter, direction, distance, resolution);
    vtkProbeFilter* sampleVolume = vtkProbeFilter::New();
    //这里只能填1,和0,否则曲面要么是一块,要么什么也没有;
    sampleVolume->SetInputConnection(1, reader->GetOutputPort());
    sampleVolume->SetInputData(0, surface);

    //根据数据源的数据范围设置映射表的窗宽窗位
    vtkWindowLevelLookupTable* wlLut = vtkWindowLevelLookupTable::New();
    double range = reader->GetOutput()->GetScalarRange()[1] - reader->GetOutput()->GetScalarRange()[0];
    double level = (reader->GetOutput()->GetScalarRange()[1] - reader->GetOutput()->GetScalarRange()[0]) / 2;
    wlLut->SetWindow(range);
    wlLut->SetLevel(level);

    //创建映射器和角色
    vtkDataSetMapper* mapper = vtkDataSetMapper::New();
    mapper->SetInputConnection(sampleVolume->GetOutputPort());
    mapper->SetLookupTable(wlLut);
    mapper->SetScalarRange(0, 255);

    vtkActor* actor = vtkActor::New();
    actor->SetMapper(mapper);

    //创建渲染器,渲染窗口和交互
    vtkRenderer* ren = vtkRenderer::New();
    vtkRenderWindow* renWin = vtkRenderWindow::New();
    renWin->AddRenderer(ren);
    renWin->SetWindowName("CurvedReformation");

    vtkRenderWindowInteractor* iren = vtkRenderWindowInteractor::New();
    iren->SetRenderWindow(renWin);

    //将角色添加到场景
    ren->AddActor(actor);
    vtkNamedColors* colors = vtkNamedColors::New();
   // ren->SetBackground(colors->GetColor3d("DarkSlateGray"));
    ren->SetBackground(0.4, 0.4, 0.4);

    //设置相机以查看图像
    ren->GetActiveCamera()->SetViewUp(0, 0, 1);
    ren->GetActiveCamera()->SetPosition(0, 0, 0);
    ren->GetActiveCamera()->SetFocalPoint(1, 0, 0);
    ren->ResetCamera();

    //渲染和交互
    renWin->Render();
    iren->Start();

    return 0;
}

效果:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1860993.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

jenkins api部署时,一直提示pending-Finished waiting

问题&#xff1a; 调用jenkins api部署时&#xff0c;一直提示pending-Finished waiting 解决方案&#xff1a; 这个问题困扰了很久&#xff0c;一直没有思路&#xff0c;后面看到调用jenkinsAPI本身会出现一段提示&#xff0c;pending in the quiet period&#xff0c;通过搜…

智慧仓储的秘密武器:数据可视化的应用

智慧仓储中数据可视化是如何应用的&#xff1f;在现代物流和供应链管理中&#xff0c;智慧仓储已成为企业提升效率、降低成本和优化运营的重要手段。而数据可视化作为智慧仓储的重要工具&#xff0c;通过将复杂的数据转化为直观、易理解的图表和图形&#xff0c;极大地提升了仓…

js实现blockly后台解释器,可以单步执行,可以调用c/c++函数

实现原理 解析blockly语法树,使用js管理状态,实际使用lua执行,c/c++函数调用使用lua调用c/c++函数的能力 可以单行执行 已实现if功能 TODO for循环功能 函数功能 单步执行效果图 直接执行效果图 源代码 //0 暂停 1 单步执行 2 断点 //创建枚举 var AstStatus = {PAUS…

5、双足机器人mpc动力学模型

为计算机器人的当前实际状态x,需要建立双足质心动力学模型。 速度模型由控制输入变量推导速度公式: x向速度νx :当前机器人x方向的前进速度,初始值由速度传感器实时测量得到。y向速度νy :机器人y方向的平移速度。z向速度νz :垂直方向的速度,对于双足机器人行走时为0:…

吉利前端、AI面试

诸葛耘墒的在线视频面试 1、小程序端AI视频面试 虚拟人面试官提问 视频口述回答 1、最近的两份工作经历&#xff0c;以及上一份离职原因2、在过往的工作或生活中&#xff0c;需要学习掌握一项与工作有关的技能或兴趣爱好时&#xff0c;你会运用哪些方法和诀窍&#xff0c;投入…

项目实训-vue(十二)

项目实训-vue&#xff08;十二&#xff09; 文章目录 项目实训-vue&#xff08;十二&#xff09;1.概述2.处理进度可视化 1.概述 本篇博客将记录我在图片上传页面中的工作。 2.处理进度可视化 除了导航栏之外&#xff0c;我们还需要对上传图片以及图片处理的过程以及流程进行…

职业技能大赛引领下大数据专业实训教学的改革研究

随着信息化时代的加速发展&#xff0c;大数据专业作为新兴的热门领域&#xff0c;正日益成为高等职业教育体系中不可或缺的一部分&#xff0c;其承担着为社会培养大批具有高素质应用技能的大数据技术人才的重任。职业技能大赛作为检验和提升学生技能水平的有效平台&#xff0c;…

数据库中的事务、undo log、redo log、binlog都是干啥的?

文章目录 关于事务ACID 特性undo logredo logredo log 的写入过程事务的执行过程binlog细节总结 数据迁移数据备份工具innodb_autoinc_lock_mode 关于事务 事务&#xff08;transaction&#xff09;是作为一个单元的一组有序的数据库操作。如果组中的所有操作都成功&#xff0…

基于PHP+MySQL组合开发的在线客服小程序源码系统 带完整的安装代码包以及搭建教程

系统概述 源码系统是专门为满足企业在线客服需求而设计的&#xff0c;它集成了多种功能&#xff0c;能够帮助企业实现与用户的实时沟通、问题解答、信息反馈等。通过该系统&#xff0c;企业可以更好地了解用户需求&#xff0c;提升用户体验&#xff0c;增强用户对企业的信任感…

Clark 克拉克变换与克拉克逆变换

一、无刷电机控制原理 如上图所示&#xff0c;通过多个mos管的捷联去控制电机运动&#xff0c;即在电机的ABC三相中都会形成相应的电流变化&#xff0c;每相相差120。 二、Clark变换 但如果通过上面这种改变电流波形的方式去控制电机会变得非常复杂&#xff0c;则Clark变换是…

牛了,LSTM+Transformer王炸结合创新,荣登Nature,精度高达95.65%

【LSTM结合Transformer】的研究方向探索了如何利用Transformer模型处理序列数据的能力以及LSTM在捕捉时间序列依赖性方面的优势。这一方向的意义在于通过融合两种模型的特点&#xff0c;提高了对复杂时空数据的预测准确性&#xff0c;尤其是在智能电网攻击检测、多变量时间序列…

2024三掌柜赠书活动第二十五期:Rust 游戏开发实战

目录 目录 前言 Rust语言概念 关于《Rust 游戏开发实战》 Rust系统编程的核心点 Rust开发的关键技术和工具 内容简介 作者简介 书中前言/序言 内容介绍 《Rust 游戏开发实战》全书速览 图书目录 结束语 前言 技术圈最近的编程语言新秀当属Rust莫属&#xff0c;Rus…

如何与ISSI建立EDI连接?

ISSI是一家总部位于美国的半导体公司&#xff0c;主要设计和销售高性能集成电路 (IC)&#xff0c;其产品包括DRAM、SRAM、闪存和模拟电路&#xff0c;广泛应用于汽车、通信、工业和医疗等领域。 和其他半导体行业的企业一样&#xff0c;ISSI通过EDI与其全球合作伙伴传输业务单据…

经典神经网络(12)Transformer代码详解及其在Multi30k数据集上的训练

经典神经网络(12)Transformer代码详解及其在Multi30k数据集上的训练 论文链接&#xff1a;https://arxiv.org/pdf/1706.03762v2 原理可以参考&#xff1a;Self-Attention和Transformer 网络架构图如下&#xff1a; 1 Transformer编码器模块 1.1 Embedding位置编码 在实际…

游戏AI的创造思路-技术基础-机器学习(1)

大坑从此开始~~~~ 目录 1. 定义 2.发展历程和典型事件 2.1. 发展历程 2.2. 典型事件 3. 学习类型 3.1. 监督学习 3.2. 无监督学习 3.3. 半监督学习 3.3.1.定义与基本思想 3.3.2. 发展历程与应用场景 3.3.3. 核心算法与优势 3.3.4. 实际应用案例 3.4. 游戏AI的半监…

高校新生如何选择最优手机流量卡?

一年一度的高考已经结束了&#xff0c;愿广大学子金榜题名&#xff0c;家长们都给孩子准备好了手机&#xff0c;那么手机流量卡应该如何选择呢&#xff1f; 高校新生在选择手机流量卡时&#xff0c;需要综合考量流量套餐、费用、网络覆盖、售后服务等多方面因素&#xff0c;以下…

在Visual Studio Code中使用Phi-3模型

更多数字生产力内容&#xff0c;欢迎关注我的公众号“ONE生产力”。 先前的文章中&#xff0c;我们已经介绍使用LM Studio在本地环境中运行Phi-3。LM Studio是一款革命性的桌面应用程序&#xff0c;它允许用户在自己的计算机上本地运行、管理和部署大型语言模型&#xff0c;但有…

新书速览|Linux C与C++一线开发实践

《Linux C与C一线开发实践》 本书内容 Linux C/C编程在Linux应用程序开发中占有重要的地位&#xff0c;掌握这项技术将在就业竞争中立于不败之地。《Linux C与C一线开发实践》内容针对初中级读者&#xff0c;贴近软件公司一线开发实践。全书厚达620多页&#xff0c;知识点丰富…

Go语言JSON-RPC 实战: `net/rpc/jsonrpc` 包的高效使用指南

Go语言JSON-RPC 实战&#xff1a; net/rpc/jsonrpc 包的高效使用指南 简介jsonrpc 包的基础客户端&#xff08;Client&#xff09;创建客户端调用方法 服务器&#xff08;Server&#xff09;配置服务器数据类型和错误处理 搭建基础的 JSON-RPC 服务服务端的实现客户端的实现 进…

不懂电路搭建可以学嵌入式编程开发吗?

当然可以学嵌入式编程开发&#xff01;虽然电路搭建是嵌入式开发中的一部分&#xff0c;但即使你对电路搭建不太了解&#xff0c;也可以从嵌入式编程开发入手。刚好我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「嵌入式的资料从专业入门到高级教程」&#xff0…