参考:
http://blog.csdn.net/inter_peng/article/details/38173007
代码是在vtk560环境下写出来的。下面直接贴代码:
using vtk; namespace dicomorientationtest { public partial class Form1 : Form { #region 私有成员 private vtk.vtkFormsWindowControl vtkFormsWindowControl1 = null; private vtk.vtkDICOMImageReader _reader = null; private vtk.vtkVolume _vtkVolume = null; private vtk.vtkRenderer _render = null; private vtk.vtkGenericRenderWindowInteractor _iren = new vtk.vtkGenericRenderWindowInteractor(); private vtk.vtkRenderWindow _renwin = null; private vtk.vtkFollower textActor; #endregion #region 属性 public string FileDir { get; set; } #endregion public Form1() { InitializeComponent(); InitRenderWindow(); } private void InitRenderWindow() { this.vtkFormsWindowControl1 = new vtkFormsWindowControl(); this.SuspendLayout(); this.vtkFormsWindowControl1.Name = "vtkFormsWindowControl1"; this.vtkFormsWindowControl1.Size = new System.Drawing.Size(800, 800); this.vtkFormsWindowControl1.TabIndex = 0; this.Location = new System.Drawing.Point(10, 10); this.vtkFormsWindowControl1.Text = "vtkFormsWindowControl1"; this.Controls.Add(vtkFormsWindowControl1); } private void btn_Open_Click(object sender, EventArgs e) { FolderBrowserDialog dlg = new FolderBrowserDialog(); if (DialogResult.OK == dlg.ShowDialog()) { FileDir = dlg.SelectedPath; } } private void btn_render_Click(object sender, EventArgs e) { if (!String.IsNullOrEmpty(FileDir)) { _render = new vtkRenderer(); #region dicom _reader = new vtkDICOMImageReader(); _reader.SetDirectoryName(FileDir); _reader.SetDataByteOrderToLittleEndian(); _reader.Update(); int[] dimensions = _reader.GetOutput().GetDimensions(); #region opacity transfer vtkPiecewiseFunction compositeOpacity = new vtkPiecewiseFunction(); compositeOpacity.AddPoint(-2048, 0); compositeOpacity.AddPoint(128.643, 0); compositeOpacity.AddPoint(129.982, 0.0982143); compositeOpacity.AddPoint(173.636, 0.1); compositeOpacity.AddPoint(255.884, 0.1); compositeOpacity.AddPoint(3661, 1); //compositeOpacity.AddPoint(173.636, 0); //compositeOpacity.AddPoint(255.884, 0); //compositeOpacity.AddPoint(3661, 0); #endregion #region colortransfer vtkColorTransferFunction colorFun = new vtkColorTransferFunction(); colorFun.AddRGBPoint(-2048, 0, 0, 0); colorFun.AddRGBPoint(128.643, 0, 0, 0); colorFun.AddRGBPoint(129.982, 0.615686, 0, 0.0156863); colorFun.AddRGBPoint(173.636, 0.909804, 0.454902, 0); colorFun.AddRGBPoint(255.884, 0.886275, 0.886275, 0.886275); colorFun.AddRGBPoint(584.878, 0.968627, 0.968627, 0.968627); colorFun.AddRGBPoint(3661, 1, 1, 1); #endregion vtkVolumeProperty property = new vtkVolumeProperty(); property.ShadeOff(); property.SetInterpolationTypeToLinear(); property.SetColor(colorFun); property.SetScalarOpacity(compositeOpacity); property.SetDiffuse(0.9); property.SetAmbient(0.1); property.SetSpecular(0.2); property.SetSpecularPower(10.0); double[] range = _reader.GetOutput().GetScalarRange(); double min = range[0]; double max = range[1]; double diff = max - min; double slope = 4095.0 / diff;//斜率 double inter = -slope * min;//截距 double shift = inter / slope; vtkImageShiftScale vtkImageCast = new vtkImageShiftScale(); vtkImageCast.SetInput(_reader.GetOutput()); vtkImageCast.SetScale(slope); vtkImageCast.SetShift(shift); vtkImageCast.SetOutputScalarTypeToUnsignedShort(); vtkImageCast.Update(); vtkVolumeRayCastCompositeFunction compositefunction = new vtkVolumeRayCastCompositeFunction(); compositefunction.SetCompositeMethodToInterpolateFirst(); vtkVolumeRayCastMapper mapper = new vtkVolumeRayCastMapper(); mapper.SetVolumeRayCastFunction(compositefunction); mapper.SetInput(vtkImageCast.GetOutput()); mapper.SetSampleDistance(0.1); vtkVolume volume = new vtkVolume(); volume.SetMapper(mapper); volume.SetProperty(property); _render.AddViewProp(volume); #endregion #region axes double[] space = _reader.GetOutput().GetSpacing(); Console.WriteLine("spacing[0]={0},[1]={1},[2]={2}", space[0], space[1], space[2]); int[] extents = _reader.GetOutput().GetExtent(); Console.WriteLine("extents[0]={0},[1]={1},[2]={2},[3]={3},[4]={4},[5]={5}", extents[0], extents[1], extents[2], extents[3], extents[4], extents[5]); vtkTransform transform = new vtkTransform(); transform.Translate(0.0, 0.0, 0.0); transform.Scale((extents[1]) * (space[0]), (extents[3]) * (space[1]), (extents[5]) * (space[2])); vtkAxesActor axes = new vtkAxesActor(); axes.SetUserTransform(transform); _render.AddActor(axes); #endregion #region text double scalesize=(extents[1]) * (space[0])/20; //原点 vtkVectorText otext = new vtkVectorText(); otext.SetText("O"); vtkPolyDataMapper textMapper = new vtkOpenGLPolyDataMapper(); textMapper.SetInputConnection(otext.GetOutputPort()); textActor = new vtkFollower(); textActor.SetMapper(textMapper); textActor.SetScale(scalesize,scalesize,scalesize); textActor.AddPosition(0, -0.1, 0);//////////// textActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(textActor); //左 L vtkVectorText lText = new vtkVectorText(); lText.SetText("L"); vtkPolyDataMapper lMapper = new vtkOpenGLPolyDataMapper(); lMapper.SetInputConnection(lText.GetOutputPort()); vtkFollower lActor = new vtkFollower(); lActor.SetMapper(lMapper); lActor.SetScale(scalesize,scalesize,scalesize); lActor.GetProperty().SetColor(0,1,0); lActor.AddPosition((extents[1] * space[0])+10, (extents[3] * space[1]) / 2, (extents[5] * space[2]) / 2); lActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(lActor); //右 R vtkVectorText rText = new vtkVectorText(); rText.SetText("R"); vtkPolyDataMapper rMapper = new vtkOpenGLPolyDataMapper(); rMapper.SetInputConnection(rText.GetOutputPort()); vtkFollower rActor = new vtkFollower(); rActor.SetMapper(rMapper); rActor.SetScale(scalesize, scalesize, scalesize); rActor.GetProperty().SetColor(1, 0, 0); rActor.AddPosition(-10, (extents[3] * space[1]) / 2, (extents[5] * space[2]) / 2); rActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(rActor); //前 A vtkVectorText aText = new vtkVectorText(); aText.SetText("A"); vtkPolyDataMapper aMapper = new vtkOpenGLPolyDataMapper(); aMapper.SetInputConnection(aText.GetOutputPort()); vtkFollower aActor = new vtkFollower(); aActor.SetMapper(aMapper); aActor.SetScale(scalesize, scalesize, scalesize); aActor.GetProperty().SetColor(0, 1, 0); aActor.AddPosition((extents[1] * space[0]) / 2, (extents[3] * space[1])+10, (extents[5] * space[2]) / 2); aActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(aActor); //后 P vtkVectorText pText = new vtkVectorText(); pText.SetText("P"); vtkPolyDataMapper pMapper = new vtkOpenGLPolyDataMapper(); pMapper.SetInputConnection(pText.GetOutputPort()); vtkFollower pActor = new vtkFollower(); pActor.SetMapper(pMapper); pActor.SetScale(scalesize, scalesize, scalesize); pActor.GetProperty().SetColor(1, 0, 0); pActor.AddPosition((extents[1] * space[0]) / 2, -10, (extents[5] * space[2]) / 2); pActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(pActor); //头 H vtkVectorText hText = new vtkVectorText(); hText.SetText("H"); vtkPolyDataMapper hMapper = new vtkOpenGLPolyDataMapper(); hMapper.SetInputConnection(hText.GetOutputPort()); vtkFollower hActor = new vtkFollower(); hActor.SetMapper(hMapper); hActor.SetScale(scalesize, scalesize, scalesize); hActor.GetProperty().SetColor(0, 1, 0); hActor.AddPosition((extents[1] * space[0]) / 2,(extents[3] * space[1]) / 2,-10 ); hActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(hActor); //脚 F vtkVectorText fText = new vtkVectorText(); fText.SetText("F"); vtkPolyDataMapper fMapper = new vtkOpenGLPolyDataMapper(); fMapper.SetInputConnection(fText.GetOutputPort()); vtkFollower fActor = new vtkFollower(); fActor.SetMapper(fMapper); fActor.SetScale(scalesize, scalesize, scalesize); fActor.GetProperty().SetColor(0, 1, 0); fActor.AddPosition((extents[1] * space[0]) / 2, (extents[3] * space[1]) / 2, (extents[5] * space[2])+10); fActor.SetCamera(_render.GetActiveCamera()); _render.AddViewProp(fActor); #endregion _render.ResetCamera(); vtkFormsWindowControl1.GetRenderWindow().AddRenderer(_render); _renwin = vtkFormsWindowControl1.GetRenderWindow(); _renwin.AddRenderer(_render); _renwin.Render(); } else { MessageBox.Show("请先选定文件夹!"); } } } }
效果图: