GDCM
2.2.3
|
/*========================================================================= Program: GDCM (Grassroots DICOM). A DICOM library Copyright (c) 2006-2011 Mathieu Malaterre All rights reserved. See Copyright.txt or http://gdcm.sourceforge.net/Copyright.html for details. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the above copyright notice for more information. =========================================================================*/ import vtk.*; import gdcm.*; import java.io.File; import java.awt.Canvas; /* * Compilation: * CLASSPATH=vtkgdcm.jar:/usr/share/java/vtk.jar javac MIPViewer.java * * Usage: * LD_LIBRARY_PATH=/usr/lib/jvm/java-6-openjdk/jre/lib/amd64/xawt:/usr/lib/jni:. CLASSPATH=/usr/share/java/vtk.jar:vtkgdcm.jar:gdcm.jar:. java MIPViewer BRAINX * */ public class MIPViewer extends Canvas { static { // VTK System.loadLibrary("vtkCommonJava"); System.loadLibrary("vtkFilteringJava"); System.loadLibrary("vtkIOJava"); System.loadLibrary("vtkImagingJava"); System.loadLibrary("vtkGraphicsJava"); System.loadLibrary("vtkRenderingJava"); System.loadLibrary("vtkVolumeRenderingJava"); // vtkSmartVolumeMapper System.loadLibrary("vtkWidgetsJava"); // vtkBoxWidget // VTK-GDCM System.loadLibrary("vtkgdcmJava"); } static FilenamesType fns = new FilenamesType(); protected native int Lock(); protected native int UnLock(); public static void process(String path) { fns.add( path ); } // Process only files under dir public static void visitAllFiles(File dir) { if (dir.isDirectory()) { String[] children = dir.list(); for (int i=0; i<children.length; i++) { visitAllFiles(new File(dir, children[i])); } } else { process(dir.getPath()); } } public static void main(String[] args) throws Exception { String dirname = args[0]; if( !PosixEmulation.FileIsDirectory( dirname ) ) { return; } File dir = new File(dirname); visitAllFiles(dir); IPPSorter ipp = new IPPSorter(); ipp.SetComputeZSpacing( true ); ipp.SetZSpacingTolerance( 1e-3 ); boolean b = ipp.Sort( fns ); if(!b) { throw new Exception("Could not scan"); } double ippzspacing = ipp.GetZSpacing(); FilenamesType sorted = ipp.GetFilenames(); vtkStringArray files = new vtkStringArray(); long nfiles = sorted.size(); //for( String f : sorted ) for (int i = 0; i < nfiles; i++) { String f = sorted.get(i); files.InsertNextValue( f ); } vtkGDCMImageReader reader = new vtkGDCMImageReader(); reader.SetFileNames( files ); reader.Update(); // get spacing value double[] spacing = reader.GetOutput().GetSpacing(); vtkImageChangeInformation change = new vtkImageChangeInformation(); change.SetInputConnection( reader.GetOutputPort() ); change.SetOutputSpacing( spacing[0], spacing[1], ippzspacing ); // Create our volume and mapper vtkVolume volume = new vtkVolume(); vtkSmartVolumeMapper mapper = new vtkSmartVolumeMapper(); vtkRenderWindowInteractor iren = new vtkRenderWindowInteractor(); // Add a box widget if the clip option was selected vtkBoxWidget box = new vtkBoxWidget(); box.SetInteractor(iren); box.SetPlaceFactor(1.01); box.SetInput(change.GetOutput()); //box.SetDefaultRenderer(renderer); box.InsideOutOn(); box.PlaceWidget(); //vtkBoxWidgetCallback callback = vtkBoxWidgetCallback::New(); //callback.SetMapper(mapper); //box.AddObserver(vtkCommand::InteractionEvent, callback); //callback.Delete(); // Lock(); // box.EnabledOn(); // UnLock(); box.GetSelectedFaceProperty().SetOpacity(0.0); mapper.SetInputConnection( change.GetOutputPort() ); // Create our transfer function vtkColorTransferFunction colorFun = new vtkColorTransferFunction(); vtkPiecewiseFunction opacityFun = new vtkPiecewiseFunction(); // Create the property and attach the transfer functions vtkVolumeProperty property = new vtkVolumeProperty(); property.IndependentComponentsOn(); property.SetColor( colorFun ); property.SetScalarOpacity( opacityFun ); property.SetInterpolationTypeToLinear(); // connect up the volume to the property and the mapper volume.SetProperty( property ); volume.SetMapper( mapper ); vtkMedicalImageProperties medprop = reader.GetMedicalImageProperties(); int n = medprop.GetNumberOfWindowLevelPresets(); double opacityWindow = 4096; double opacityLevel = 2048; // Override default with value from DICOM files: for( int i = 0; i < n; ++i ) { double wl[] = medprop.GetNthWindowLevelPreset(i); //System.out.println( "W/L: " + wl[0] + " " + wl[1] ); opacityWindow = wl[0]; opacityLevel = wl[1]; } colorFun.AddRGBSegment(0.0, 1.0, 1.0, 1.0, 255.0, 1.0, 1.0, 1.0 ); opacityFun.AddSegment( opacityLevel - 0.5*opacityWindow, 0.0, opacityLevel + 0.5*opacityWindow, 1.0 ); mapper.SetBlendModeToMaximumIntensity(); // Create the RenderWindow, Renderer vtkRenderer ren1 = new vtkRenderer(); vtkRenderWindow renWin = new vtkRenderWindow(); renWin.AddRenderer(ren1); // Set the default window size renWin.SetSize(600,600); // Add the volume to the scene ren1.AddVolume( volume ); ren1.ResetCamera(); iren.SetRenderWindow( renWin ); // interact with data renWin.Render(); iren.Start(); } }