参考水灵大神的代码编写的,将其改为在C#下,用activiz实现。
大神的源码在这里:
http://blog.csdn.net/www_doling_net/article/details/8551523
在c#中,有些VTK的功能不支持,所以需要自己改一下:
namespace SliceMonitortest { /// <summary> /// 封装了4*4矩阵的乘法 /// 因为在Activiz中,vtkMatrix4x4的 MultiplyPoint 功能无法使用,所以自己封装了一个类来实现矩阵乘法。 /// </summary> public class Matrix4 { private double[,] vtkArray; public double[,] VtkArray { get { return vtkArray; } } public Matrix4(vtkMatrix4x4 vtkMatrix) { vtkArray=new double[4,4]; for (int i = 0; i < 4; i++) { //double[] temp = new double[4]; for (int j = 0; j < 4; j++) { vtkArray[i,j] = vtkMatrix.GetElement(i,j); } } } /// <summary> /// 矩阵乘法 /// </summary> /// <param name="inArray">输入矩阵</param> /// <param name="outArray">输出矩阵</param> public void MultiplyPoint(double[] inArray,double[] outArray) { for (int i = 0; i < 4; i++) { outArray[i] = 0.0; for (int j = 0; j < 4; j++) { outArray[i] += vtkArray[i, j] * inArray[j]; } } } } } namespace SliceMonitortest { public partial class Form1 : Form { private vtkDICOMImageReader _reader = null; private vtkRenderer _render = null; private vtkRenderWindow _renwin = null; private vtkRenderWindowInteractor _iren = null; private vtkImageReslice reslice = null; private vtkObject.vtkObjectEventHandler InteractorHandler = null; private int Slicing; public string FileDir { get; set; } public Form1() { InitializeComponent(); } private void renderWindowControl1_Load(object sender, EventArgs e) { _renwin = renderWindowControl1.RenderWindow; _render = _renwin.GetRenderers().GetFirstRenderer(); _iren = _renwin.GetInteractor(); InteractorHandler=new vtkObject.vtkObjectEventHandler(_iren_AnyEvt);//注册交互事件处理程序 _iren.AnyEvt += InteractorHandler; Slicing = 0; } void _iren_AnyEvt(vtkObject sender, vtkObjectEventArgs e) { int[] lastPos = _iren.GetLastEventPosition(); int[] currPos = _iren.GetEventPosition(); vtkCommand.EventIds eid = (vtkCommand.EventIds)e.EventId; if (eid == vtkCommand.EventIds.LeftButtonPressEvent) { this.Slicing = 1; } else if (eid == vtkCommand.EventIds.LeftButtonReleaseEvent) { this.Slicing = 0; } else if (eid == vtkCommand.EventIds.MouseMoveEvent) { if (this.Slicing==1) { int deltY = lastPos[1] - currPos[1];//计算鼠标移动 reslice.Update(); double sliceSpacing = reslice.GetOutput().GetSpacing()[2]; vtkMatrix4x4 matrix = reslice.GetResliceAxes();//获取转换矩阵 Matrix4 tempmatrix = new Matrix4(matrix); //因为vtkMatrix4x4的 MultiplyPoint 功能无法使用,所以自己封装了一个类实现矩阵乘法 // move the center point that we are slicing through double[] point=new double[4]{0.0,0.0,sliceSpacing*deltY,1.0}; double[] center = new double[4]{0.0,0.0,0.0,0.0}; tempmatrix.MultiplyPoint(point,center); //计算边界,当超出边界时不再移动 int[] extent = _reader.GetOutput().GetExtent(); double[] spacing = _reader.GetOutput().GetSpacing(); double[] origin = _reader.GetOutput().GetOrigin(); double[] Border=new double[3]; Border[0]= origin[0] + spacing[0] * (extent[0] + extent[1]); Border[1]= origin[1] + spacing[1] * (extent[2] + extent[3]); Border[2]= origin[2] + spacing[2] * (extent[4] + extent[5]); for (int i = 0; i < 3; i++) { if (center[i] < origin[i]) center[i] = origin[i]; } for (int i = 0; i < 3; i++) { if (center[i] > Border[i]) center[i] = Border[i]; } matrix.SetElement(0, 3, center[0]); matrix.SetElement(1, 3, center[1]); matrix.SetElement(2, 3, center[2]); //if((center[0]<0)||(center[0]>)) _iren.Render(); } else { vtkInteractorStyle style = vtkInteractorStyle.SafeDownCast(_iren.GetInteractorStyle()); if (style != null) { style.OnMouseMove(); } } } } private void btn_ReadFiles_Click(object sender, EventArgs e) { FolderBrowserDialog dlg = new FolderBrowserDialog(); if (dlg.ShowDialog() == DialogResult.OK) { FileDir = dlg.SelectedPath; } if (!String.IsNullOrEmpty(FileDir)) { _reader = new Kitware.VTK.vtkDICOMImageReader(); _reader.SetDirectoryName(FileDir); _reader.SetDataByteOrderToLittleEndian(); _reader.Update(); int[] extent = _reader.GetOutput().GetExtent(); double[] spacing = _reader.GetOutput().GetSpacing(); double[] origin = _reader.GetOutput().GetOrigin(); double[] center = new double[3]; center[0] = origin[0] + spacing[0] * 0.5 * (extent[0] + extent[1]); center[1] = origin[1] + spacing[1] * 0.5 * (extent[2] + extent[3]); center[2] = origin[2] + spacing[2] * 0.5 * (extent[4] + extent[5]); double[] axialElements ={ 1,0,0,0, 0,1,0,0, 0,0,1,0,//// 0,0,0,1 };//平行于XY平面,轴面 vtkMatrix4x4 resliceAxes = new vtkMatrix4x4(); for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++) resliceAxes.SetElement(i, j, axialElements[i * 4 + j]); } resliceAxes.SetElement(0, 3, center[0]); resliceAxes.SetElement(1, 3, center[1]); resliceAxes.SetElement(2, 3, center[2]); Console.WriteLine("center[0]:{0},center[1]:{1},center[2]:{2}",center[0],center[1],center[2]); reslice = new vtkImageReslice(); reslice.SetInputConnection(_reader.GetOutputPort()); reslice.SetOutputDimensionality(2); reslice.SetResliceAxes(resliceAxes); reslice.SetInterpolationModeToLinear(); vtkLookupTable colortable = new vtkLookupTable(); colortable.SetRange(0, 1000); colortable.SetValueRange(0.0, 1.0); colortable.SetSaturationRange(0.0, 0.0); colortable.SetRampToLinear(); colortable.Build(); vtkImageMapToColors colormap = new vtkImageMapToColors(); colormap.SetLookupTable(colortable); colormap.SetInputConnection(reslice.GetOutputPort()); vtkImageActor imgActor = new vtkImageActor(); imgActor.SetInput(colormap.GetOutput()); _render.AddActor(imgActor); _render.SetBackground(0.4, 0.5, 0.6); vtkInteractorStyle imagestyle = new vtkInteractorStyle(); _iren.SetInteractorStyle(imagestyle); _render.ResetCamera(); _renwin.Render(); _iren.Initialize(); _iren.Start(); } } private void Form1_FormClosed(object sender, FormClosedEventArgs e) { if (_iren != null) _iren.AnyEvt -= InteractorHandler; } } }