首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在CSHARP项目中将Simpleitk镜像转换为VTK?

如何在CSHARP项目中将Simpleitk镜像转换为VTK?
EN

Stack Overflow用户
提问于 2019-06-08 01:25:54
回答 2查看 271关注 0票数 2

我在我的程序中使用了Activiz(vtk的c#库)和SimpleITK,

我尝试使用SimpleITK加载dicom系列,然后将图像传输到Activiz,然后使用vtkVolumeRayCastMapper创建卷

代码语言:javascript
复制
ImageSeriesReader imageSeriesReader = new ImageSeriesReader();

VectorString dicomNames = ImageSeriesReader.GetGDCMSeriesFileNames(@"E:\VTK3d\王社教阅片端 - 复件\王社教阅片端\Data\PV");
imageSeriesReader.SetFileNames(dicomNames);
Image image = imageSeriesReader.Execute();

VectorDouble spacing= image.GetSpacing();
image = SimpleITK.Cast(image, PixelIDValueEnum.sitkVectorUInt8);
VectorUInt32 size = image.GetSize();
int len = 1;
for (int dim = 0; dim < image.GetDimension(); dim++)
{
    len *= (int)size[dim];
}


IntPtr ptr= image.GetBufferAsUInt8();

int[] bufferAsArray = new int[len];

//Marshal.Copy(ptr, bufferAsArray, 0, len);
int max = bufferAsArray.Max();
int min = bufferAsArray.Min();
vtkImageImport dataImporter = new vtkImageImport();
dataImporter.CopyImportVoidPointer(ptr, len);
dataImporter.SetDataScalarTypeToUnsignedChar();

dataImporter.SetDataExtent(0, (int)size[0], 0, (int)size[1], 0, 100);
dataImporter.SetWholeExtent(0, (int)size[0], 0, (int)size[1], 0, 100);
dataImporter.SetDataSpacing(spacing[0], spacing[1], spacing[2]);

vtkVolumeRayCastMapper volumeMapper = new vtkVolumeRayCastMapper();

vtkPiecewiseFunction volumeScalarOpacity = new vtkPiecewiseFunction();
volumeScalarOpacity.AddPoint(-260, 0.00);
//volumeScalarOpacity.AddPoint(500, 0.15);
//volumeScalarOpacity.AddPoint(1000, 0.15);
volumeScalarOpacity.AddPoint(340, 0.85);

vtkColorTransferFunction volumeColor = new vtkColorTransferFunction();
volumeColor.AddRGBPoint(-260, 0.0, 0.0, 0.0);
//volumeColor.AddRGBPoint(500, 1.0, 0.5, 0.3);
//volumeColor.AddRGBPoint(1000, 1.0, 0.5, 0.3);
volumeColor.AddRGBPoint(340, 1.0, 1.0, 0.9);

//vtkPiecewiseFunction volumeGradientOpacity = new vtkPiecewiseFunction();
//volumeGradientOpacity.AddPoint(0, 0.0);
//volumeGradientOpacity.AddPoint(90, 0.5);
//volumeGradientOpacity.AddPoint(100, 1.0);
vtkVolumeProperty volumeProperty = new vtkVolumeProperty();
volumeProperty.SetColor(volumeColor);
volumeProperty.SetScalarOpacity(volumeScalarOpacity);
// volumeProperty.SetGradientOpacity(volumeGradientOpacity);
//volumeProperty.SetInterpolationTypeToLinear();
//volumeProperty.ShadeOn();
//volumeProperty.SetAmbient(0.4);
//volumeProperty.SetDiffuse(0.6);
//volumeProperty.SetSpecular(0.2);
vtkVolumeRayCastCompositeFunction compositeFunction = new vtkVolumeRayCastCompositeFunction();
volumeMapper.SetVolumeRayCastFunction(compositeFunction);
volumeMapper.SetInputConnection(dataImporter.GetOutputPort());
vtkVolume volume = new vtkVolume();
volume.SetProperty(volumeProperty);
volume.SetMapper(volumeMapper);
volume.SetScale(0.3);
double[] c = new double[3];
c = volume.GetCenter();
renderer.AddVolume(volume);
renderer.Render();

我可以得到一个体积,但这个体积似乎已经变形,剪切,变形。

EN

回答 2

Stack Overflow用户

发布于 2019-06-08 03:09:23

我认为当您调用dataImporter.SetDataExtent和dataImporter.SetWholeExtent时,您会有一个off-1错误。最大值应为size-1、size1-1和99。

票数 0
EN

Stack Overflow用户

发布于 2021-06-08 17:54:48

您需要将dataImporter.SetDataExtentDataImporter.SetWholeExtent更改为:

代码语言:javascript
复制
dataImporter.SetDataExtent(1, (int)size[1], 1, (int)size[0], 0, 19);

dataImporter.SetWholeExtent(1, (int)size[1], 1, (int)size[0], 0, 19);

和原因Dicom类型,您必须删除行:

代码语言:javascript
复制
dataImporter.SetDataScalarTypeToUnsignedChar();

或将其更改为其他类型,如short、...与Dicom兼容。

代码语言:javascript
复制
 dataImporter.SetDataScalarTypeToShort();

也是Dicom镜像pixelType的原因,需要修改造型类型和GetBuffer类型为int16:

代码语言:javascript
复制
image = SimpleITK.Cast(image, PixelIDValueEnum.sitkInt16);

IntPtr ptr = image.GetBufferAsInt16();

此外,您还需要使用以下代码,而不是CopyImportVoidPointer

代码语言:javascript
复制
dataImporter.SetImportVoidPointer(ptr);

此方法设置从中导入图像数据的指针。VTK不会制作自己的数据副本,它将直接从提供的数组中访问数据。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/56498835

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档