1 /*=========================================================================
2 
3   Program:   Visualization Toolkit
4   Module:    TestGPURayCastCompositeMask.cxx
5 
6   Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7   All rights reserved.
8   See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9 
10      This software is distributed WITHOUT ANY WARRANTY; without even
11      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12      PURPOSE.  See the above copyright notice for more information.
13 
14 =========================================================================*/
15 #include "vtkTestUtilities.h"
16 #include "vtkRegressionTestImage.h"
17 #include "vtkVolume16Reader.h"
18 #include "vtkImageData.h"
19 #include "vtkGPUVolumeRayCastMapper.h"
20 #include "vtkVolume.h"
21 #include "vtkVolumeProperty.h"
22 #include "vtkColorTransferFunction.h"
23 #include "vtkPiecewiseFunction.h"
24 #include "vtkRenderWindowInteractor.h"
25 #include "vtkRenderWindow.h"
26 #include "vtkRenderer.h"
27 #include "vtkCamera.h"
28 #include "vtkSmartPointer.h"
29 #include "vtkTesting.h"
30 
TestGPURayCastMIPBinaryMask(int argc,char * argv[])31 int TestGPURayCastMIPBinaryMask(int argc, char *argv[])
32 {
33   cout << "CTEST_FULL_OUTPUT (Avoid ctest truncation of output)" << endl;
34 
35   char* fname = vtkTestUtilities::ExpandDataFileName(argc, argv, "Data/headsq/quarter");
36 
37   vtkSmartPointer<vtkVolume16Reader> reader =
38     vtkSmartPointer<vtkVolume16Reader>::New();
39   reader->SetDataDimensions( 64, 64);
40   reader->SetDataByteOrderToLittleEndian();
41   reader->SetImageRange( 1, 93);
42   reader->SetDataSpacing( 3.2, 3.2, 1.5);
43   reader->SetFilePrefix( fname );
44   reader->SetDataMask( 0x7fff);
45   reader->Update();
46 
47   delete[] fname;
48 
49   vtkImageData *input=reader->GetOutput();
50 
51   int dim[3];
52   double spacing[3], center[3], origin[3];
53   input->GetSpacing(spacing);
54   input->GetDimensions(dim);
55   input->GetCenter(center);
56   input->GetOrigin(origin);
57 
58   vtkSmartPointer< vtkGPUVolumeRayCastMapper > mapper
59     = vtkSmartPointer< vtkGPUVolumeRayCastMapper >::New();
60   vtkSmartPointer< vtkVolume > volume
61     = vtkSmartPointer< vtkVolume >::New();
62   mapper->SetInputConnection(reader->GetOutputPort());
63   mapper->SetMaskTypeToBinary();
64   mapper->SetAutoAdjustSampleDistances(0);
65 
66    // assume the scalar field is a set of samples taken from a
67   // contiguous band-limited volumetric field.
68   // assume max frequency is present:
69   // min spacing divided by 2. Nyquist-Shannon theorem says so.
70   // sample distance could be bigger if we compute the actual max frequency
71   // in the data.
72   double distance=spacing[0];
73   if(distance>spacing[1])
74     {
75     distance=spacing[1];
76     }
77   if(distance>spacing[2])
78     {
79     distance=spacing[2];
80     }
81   distance=distance/2.0;
82 
83   // This does not take the screen size of a cell into account.
84   // distance has to be smaller: min(nyquis,screensize)
85 
86   mapper->SetSampleDistance(static_cast<float>(distance));
87 
88   vtkSmartPointer< vtkColorTransferFunction > colorFun
89     = vtkSmartPointer< vtkColorTransferFunction >::New();
90   vtkSmartPointer< vtkPiecewiseFunction > opacityFun
91     = vtkSmartPointer< vtkPiecewiseFunction >::New();
92 
93   // Create the property and attach the transfer functions
94   vtkSmartPointer< vtkVolumeProperty > property
95     = vtkSmartPointer< vtkVolumeProperty >::New();
96   property->SetIndependentComponents(true);
97   property->SetColor(colorFun);
98   property->SetScalarOpacity(opacityFun);
99   property->SetInterpolationTypeToLinear();
100 
101   // connect up the volume to the property and the mapper
102   volume->SetProperty(property);
103   volume->SetMapper(mapper);
104 
105   colorFun->AddRGBPoint(    0.0, 0.0 , 0.0 , 0.0);
106   colorFun->AddRGBPoint( 4095.0, 1 , 1 , 1);
107 
108   opacityFun->AddPoint(    0.0,  0.0);
109   opacityFun->AddPoint( 4095.0,  1.0);
110 
111   mapper->SetBlendModeToMaximumIntensity();
112 
113 
114   // Make the mask
115   vtkSmartPointer< vtkImageData > mask
116     = vtkSmartPointer< vtkImageData >::New();
117   mask->SetExtent(input->GetExtent());
118   mask->SetSpacing(input->GetSpacing());
119   mask->SetOrigin(input->GetOrigin());
120   mask->AllocateScalars(VTK_UNSIGNED_CHAR, 1);
121 
122   // Create a simple mask that's split along the X axis
123   unsigned char *ptr = static_cast< unsigned char * >(mask->GetScalarPointer());
124   const double radiusSq = 70*70; // 7cm spherical mask
125   center[0] -= origin[0];
126   center[1] -= origin[1];
127   center[2] -= origin[2];
128   for (int z = 0; z < dim[2]; z++)
129     {
130     for (int y = 0; y < dim[1]; y++)
131       {
132       for (int x = 0; x < dim[0]; x++)
133         {
134         const double distanceSq =
135           ((double)x*spacing[0]-center[0]) * ((double)x*spacing[0]-center[0]) +
136           ((double)y*spacing[1]-center[1]) * ((double)y*spacing[1]-center[1]) +
137           ((double)z*spacing[2]-center[2]) * ((double)z*spacing[2]-center[2]);
138         *ptr = (distanceSq < radiusSq ? 255 : 0);
139         ++ptr;
140         }
141       }
142     }
143 
144   mapper->SetMaskInput(mask);
145 
146 
147   vtkSmartPointer< vtkRenderWindowInteractor > iren
148     = vtkSmartPointer< vtkRenderWindowInteractor >::New();
149   vtkSmartPointer< vtkRenderWindow > renWin
150     = vtkSmartPointer< vtkRenderWindow >::New();
151   renWin->SetSize(300,300);
152   iren->SetRenderWindow(renWin);
153 
154   vtkSmartPointer< vtkRenderer > ren =
155     vtkSmartPointer< vtkRenderer >::New();
156   renWin->AddRenderer(ren);
157   renWin->Render();
158 
159   if (!mapper->IsRenderSupported(renWin,property))
160     {
161     cout << "Required extensions not supported." << endl;
162     return EXIT_SUCCESS;
163     }
164 
165   ren->AddViewProp(volume);
166   iren->Initialize();
167   ren->GetActiveCamera()->SetPosition(-484.648, 261.986, 144.52);
168   ren->GetActiveCamera()->SetViewUp(-0.078112, 0.176042, -0.981279);
169   ren->ResetCamera();
170   ren->GetActiveCamera()->Zoom(1.5);
171   renWin->Render();
172 
173   return vtkTesting::InteractorEventLoop( argc, argv, iren );
174 }
175