Medical Imaging Interaction Toolkit  2016.11.0
Medical Imaging Interaction Toolkit
mitkHotspotMaskGenerator.cpp
Go to the documentation of this file.
3 #include <mitkImageCast.h>
4 #include <mitkPoint.h>
5 #include <itkImageRegionIterator.h>
6 #include "mitkImageAccessByItk.h"
7 #include <itkImageDuplicator.h>
8 #include <itkFFTConvolutionImageFilter.h>
9 #include <mitkITKImageImport.h>
10 
11 namespace mitk
12 {
14  m_HotspotRadiusinMM(6.2035049089940), // radius of a 1cm3 sphere in mm
15  m_HotspotMustBeCompletelyInsideImage(true),
16  m_Label(1)
17  {
18  m_TimeStep = 0;
20  m_InternalMaskUpdateTime = 0;
21  }
22 
24  {
25  if (inputImage != m_inputImage)
26  {
27  m_inputImage = inputImage;
28  m_ConvolutionImageMaxIndex.set_size(inputImage->GetDimension());
29  m_ConvolutionImageMinIndex.set_size(inputImage->GetDimension());
30  this->Modified();
31  }
32  }
33 
35  {
36  if (mask != m_Mask)
37  {
38  m_Mask = mask;
39  this->Modified();
40  }
41  }
42 
44  {
45  }
46 
47  void HotspotMaskGenerator::SetHotspotRadiusInMM(double radiusInMillimeter)
48  {
49  if(radiusInMillimeter != m_HotspotRadiusinMM)
50  {
51  m_HotspotRadiusinMM = radiusInMillimeter;
52  this->Modified();
53  }
54  }
55 
57  {
58  return m_HotspotRadiusinMM;
59  }
60 
62  {
63  return m_HotspotMustBeCompletelyInsideImage;
64  }
65 
67  {
68  if (m_HotspotMustBeCompletelyInsideImage != mustBeCompletelyInImage)
69  {
70  m_HotspotMustBeCompletelyInsideImage = mustBeCompletelyInImage;
71  this->Modified();
72  }
73  }
74 
75 
77  {
78  if (IsUpdateRequired())
79  {
80  if ( m_inputImage.IsNull() )
81  {
82  throw std::runtime_error( "Error: image empty!" );
83  }
84 
85  if ( m_TimeStep >= m_inputImage->GetTimeSteps() )
86  {
87  throw std::runtime_error( "Error: invalid time step!" );
88  }
89 
91  imageTimeSelector->SetInput( m_inputImage );
92  imageTimeSelector->SetTimeNr( m_TimeStep );
93  imageTimeSelector->UpdateLargestPossibleRegion();
94  mitk::Image::Pointer timeSliceImage = imageTimeSelector->GetOutput();
95 
96  m_internalImage = timeSliceImage;
97  m_internalMask2D = nullptr; // is this correct when this variable holds a smart pointer?
98  m_internalMask3D = nullptr;
99 
100  if ( m_Mask != nullptr )
101  {
102  m_Mask->SetTimeStep(m_TimeStep);
103  mitk::Image::Pointer timeSliceMask = m_Mask->GetMask();
104 
105  if ( m_internalImage->GetDimension() == 3 )
106  {
107  CastToItkImage(timeSliceMask, m_internalMask3D);
108  AccessFixedDimensionByItk_2(m_internalImage, CalculateHotspotMask, 3, m_internalMask3D, m_Label);
109  }
110  else if ( m_internalImage->GetDimension() == 2 )
111  {
112  CastToItkImage(timeSliceMask, m_internalMask2D);
113  AccessFixedDimensionByItk_2(m_internalImage, CalculateHotspotMask, 2, m_internalMask2D, m_Label);
114  }
115  else
116  {
117  throw std::runtime_error( "Error: invalid image dimension" );
118  }
119  }
120  else
121  {
122 
123  if ( m_internalImage->GetDimension() == 3 )
124  {
125  AccessFixedDimensionByItk_2(m_internalImage, CalculateHotspotMask, 3, m_internalMask3D, m_Label);
126  }
127  else if ( m_internalImage->GetDimension() == 2 )
128  {
129  AccessFixedDimensionByItk_2(m_internalImage, CalculateHotspotMask, 2, m_internalMask2D, m_Label);
130  }
131  else
132  {
133  throw std::runtime_error( "Error: invalid image dimension" );
134  }
135  }
136  this->Modified();
137  }
138 
139  m_InternalMaskUpdateTime = m_InternalMask->GetMTime();
140  return m_InternalMask;
141  }
142 
143  void HotspotMaskGenerator::SetTimeStep(unsigned int timeStep)
144  {
145  if (m_TimeStep != timeStep)
146  {
147  m_TimeStep = timeStep;
148  }
149  }
150 
151  void HotspotMaskGenerator::SetLabel(unsigned short label)
152  {
153  if (label != m_Label)
154  {
155  m_Label = label;
156  this->Modified();
157  }
158  }
159 
161  {
162  this->GetMask(); // make sure we are up to date
163  return m_ConvolutionImageMinIndex;
164  }
165 
167  {
168  this->GetMask(); // make sure we are up to date
169  return m_ConvolutionImageMaxIndex;
170  }
171 
172  template <typename TPixel, unsigned int VImageDimension >
174  HotspotMaskGenerator::CalculateExtremaWorld( const itk::Image<TPixel, VImageDimension>* inputImage,
176  double neccessaryDistanceToImageBorderInMM,
177  unsigned int label )
178  {
179  typedef itk::Image< TPixel, VImageDimension > ImageType;
180  typedef itk::Image< unsigned short, VImageDimension > MaskImageType;
181 
182  typedef itk::ImageRegionConstIteratorWithIndex<MaskImageType> MaskImageIteratorType;
183  typedef itk::ImageRegionConstIteratorWithIndex<ImageType> InputImageIndexIteratorType;
184 
185  typename ImageType::SpacingType spacing = inputImage->GetSpacing();
186 
187  ImageExtrema minMax;
188  minMax.Defined = false;
189  minMax.MaxIndex.set_size(VImageDimension);
190  minMax.MaxIndex.set_size(VImageDimension);
191 
192  typename ImageType::RegionType allowedExtremaRegion = inputImage->GetLargestPossibleRegion();
193 
194  bool keepDistanceToImageBorders( neccessaryDistanceToImageBorderInMM > 0 );
195  if (keepDistanceToImageBorders)
196  {
197  long distanceInPixels[VImageDimension];
198  for(unsigned short dimension = 0; dimension < VImageDimension; ++dimension)
199  {
200  // To confirm that the whole hotspot is inside the image we have to keep a specific distance to the image-borders, which is as long as
201  // the radius. To get the amount of indices we divide the radius by spacing and add 0.5 because voxels are center based:
202  // For example with a radius of 2.2 and a spacing of 1 two indices are enough because 2.2 / 1 + 0.5 = 2.7 => 2.
203  // But with a radius of 2.7 we need 3 indices because 2.7 / 1 + 0.5 = 3.2 => 3
204  distanceInPixels[dimension] = int( neccessaryDistanceToImageBorderInMM / spacing[dimension] + 0.5);
205  }
206 
207  allowedExtremaRegion.ShrinkByRadius(distanceInPixels);
208  }
209 
210  InputImageIndexIteratorType imageIndexIt(inputImage, allowedExtremaRegion);
211 
212  float maxValue = itk::NumericTraits<float>::min();
213  float minValue = itk::NumericTraits<float>::max();
214 
215  typename ImageType::IndexType maxIndex;
216  typename ImageType::IndexType minIndex;
217 
218  for(unsigned short i = 0; i < VImageDimension; ++i)
219  {
220  maxIndex[i] = 0;
221  minIndex[i] = 0;
222  }
223 
224  if (maskImage != nullptr)
225  {
226  MaskImageIteratorType maskIt(maskImage, maskImage->GetLargestPossibleRegion());
227  typename ImageType::IndexType imageIndex;
228  typename ImageType::PointType worldPosition;
229  typename ImageType::IndexType maskIndex;
230 
231  for(maskIt.GoToBegin(); !maskIt.IsAtEnd(); ++maskIt)
232  {
233  imageIndex = maskIndex = maskIt.GetIndex();
234 
235  if(maskIt.Get() == label)
236  {
237  if( allowedExtremaRegion.IsInside(imageIndex) )
238  {
239  imageIndexIt.SetIndex( imageIndex );
240  double value = imageIndexIt.Get();
241  minMax.Defined = true;
242 
243  //Calculate minimum, maximum and corresponding index-values
244  if( value > maxValue )
245  {
246  maxIndex = imageIndexIt.GetIndex();
247  maxValue = value;
248  }
249 
250  if(value < minValue )
251  {
252  minIndex = imageIndexIt.GetIndex();
253  minValue = value;
254  }
255  }
256  }
257  }
258  }
259  else
260  {
261  for(imageIndexIt.GoToBegin(); !imageIndexIt.IsAtEnd(); ++imageIndexIt)
262  {
263  double value = imageIndexIt.Get();
264  minMax.Defined = true;
265 
266  //Calculate minimum, maximum and corresponding index-values
267  if( value > maxValue )
268  {
269  maxIndex = imageIndexIt.GetIndex();
270  maxValue = value;
271  }
272 
273  if(value < minValue )
274  {
275  minIndex = imageIndexIt.GetIndex();
276  minValue = value;
277  }
278  }
279  }
280 
281  minMax.MaxIndex.set_size(VImageDimension);
282  minMax.MinIndex.set_size(VImageDimension);
283 
284  for(unsigned int i = 0; i < minMax.MaxIndex.size(); ++i)
285  {
286  minMax.MaxIndex[i] = maxIndex[i];
287  }
288 
289  for(unsigned int i = 0; i < minMax.MinIndex.size(); ++i)
290  {
291  minMax.MinIndex[i] = minIndex[i];
292  }
293 
294  minMax.Max = maxValue;
295  minMax.Min = minValue;
296 
297  return minMax;
298  }
299 
300  template <unsigned int VImageDimension>
301  itk::Size<VImageDimension>
302  HotspotMaskGenerator::CalculateConvolutionKernelSize( double spacing[VImageDimension],
303  double radiusInMM )
304  {
305  typedef itk::Image< float, VImageDimension > KernelImageType;
306  typedef typename KernelImageType::SizeType SizeType;
307  SizeType maskSize;
308 
309  for(unsigned int i = 0; i < VImageDimension; ++i)
310  {
311  maskSize[i] = static_cast<int>( 2 * radiusInMM / spacing[i]);
312 
313  // We always want an uneven size to have a clear center point in the convolution mask
314  if(maskSize[i] % 2 == 0 )
315  {
316  ++maskSize[i];
317  }
318  }
319  return maskSize;
320  }
321 
322  template <unsigned int VImageDimension>
324  HotspotMaskGenerator::GenerateHotspotSearchConvolutionKernel(double mmPerPixel[VImageDimension],
325  double radiusInMM )
326  {
327  std::stringstream ss;
328  for (unsigned int i = 0; i < VImageDimension; ++i)
329  {
330  ss << mmPerPixel[i];
331  if (i < VImageDimension -1)
332  ss << ",";
333  }
334  MITK_DEBUG << "Update convolution kernel for spacing (" << ss.str() << ") and radius " << radiusInMM << "mm";
335 
336 
337  double radiusInMMSquared = radiusInMM * radiusInMM;
338  typedef itk::Image< float, VImageDimension > KernelImageType;
339  typename KernelImageType::Pointer convolutionKernel = KernelImageType::New();
340 
341  // Calculate size and allocate mask image
342  typedef typename KernelImageType::SizeType SizeType;
343  SizeType maskSize = this->CalculateConvolutionKernelSize<VImageDimension>(mmPerPixel, radiusInMM);
344 
345  mitk::Point3D convolutionMaskCenterIndex;
346  convolutionMaskCenterIndex.Fill(0.0);
347  for(unsigned int i = 0; i < VImageDimension; ++i)
348  {
349  convolutionMaskCenterIndex[i] = 0.5 * (double)(maskSize[i]-1);
350  }
351 
352  typedef typename KernelImageType::IndexType IndexType;
353  IndexType maskIndex;
354  maskIndex.Fill(0);
355 
356  typedef typename KernelImageType::RegionType RegionType;
357  RegionType maskRegion;
358  maskRegion.SetSize(maskSize);
359  maskRegion.SetIndex(maskIndex);
360 
361  convolutionKernel->SetRegions(maskRegion);
362  convolutionKernel->SetSpacing(mmPerPixel);
363  convolutionKernel->Allocate();
364 
365  // Fill mask image values by subsampling the image grid
366  typedef itk::ImageRegionIteratorWithIndex<KernelImageType> MaskIteratorType;
367  MaskIteratorType maskIt(convolutionKernel,maskRegion);
368 
369  int numberOfSubVoxelsPerDimension = 2; // per dimension!
370  int numberOfSubVoxels = ::pow( static_cast<float>(numberOfSubVoxelsPerDimension), static_cast<float>(VImageDimension) );
371  double subVoxelSizeInPixels = 1.0 / (double)numberOfSubVoxelsPerDimension;
372  double valueOfOneSubVoxel = 1.0 / (double)numberOfSubVoxels;
373  double maskValue = 0.0;
374  mitk::Point3D subVoxelIndexPosition;
375  double distanceSquared = 0.0;
376 
377  typedef itk::ContinuousIndex<double, VImageDimension> ContinuousIndexType;
378  for(maskIt.GoToBegin(); !maskIt.IsAtEnd(); ++maskIt)
379  {
380  ContinuousIndexType indexPoint(maskIt.GetIndex());
381  mitk::Point3D voxelPosition;
382  for (unsigned int dimension = 0; dimension < VImageDimension; ++dimension)
383  {
384  voxelPosition[dimension] = indexPoint[dimension];
385  }
386 
387  maskValue = 0.0;
388  mitk::Vector3D subVoxelOffset; subVoxelOffset.Fill(0.0);
389  // iterate sub-voxels by iterating all possible offsets
390  for (subVoxelOffset[0] = -0.5 + subVoxelSizeInPixels / 2.0;
391  subVoxelOffset[0] < +0.5;
392  subVoxelOffset[0] += subVoxelSizeInPixels)
393  {
394  for (subVoxelOffset[1] = -0.5 + subVoxelSizeInPixels / 2.0;
395  subVoxelOffset[1] < +0.5;
396  subVoxelOffset[1] += subVoxelSizeInPixels)
397  {
398  for (subVoxelOffset[2] = -0.5 + subVoxelSizeInPixels / 2.0;
399  subVoxelOffset[2] < +0.5;
400  subVoxelOffset[2] += subVoxelSizeInPixels)
401  {
402  subVoxelIndexPosition = voxelPosition + subVoxelOffset; // this COULD be integrated into the for-loops if neccessary (add voxelPosition to initializer and end condition)
403  distanceSquared =
404  (subVoxelIndexPosition[0]-convolutionMaskCenterIndex[0]) * mmPerPixel[0] * (subVoxelIndexPosition[0]-convolutionMaskCenterIndex[0]) * mmPerPixel[0]
405  + (subVoxelIndexPosition[1]-convolutionMaskCenterIndex[1]) * mmPerPixel[1] * (subVoxelIndexPosition[1]-convolutionMaskCenterIndex[1]) * mmPerPixel[1]
406  + (subVoxelIndexPosition[2]-convolutionMaskCenterIndex[2]) * mmPerPixel[2] * (subVoxelIndexPosition[2]-convolutionMaskCenterIndex[2]) * mmPerPixel[2];
407 
408  if (distanceSquared <= radiusInMMSquared)
409  {
410  maskValue += valueOfOneSubVoxel;
411  }
412  }
413  }
414  }
415  maskIt.Set( maskValue );
416  }
417 
418  return convolutionKernel;
419  }
420 
421  template <typename TPixel, unsigned int VImageDimension>
423  HotspotMaskGenerator::GenerateConvolutionImage( const itk::Image<TPixel, VImageDimension>* inputImage )
424  {
425  double mmPerPixel[VImageDimension];
426  for (unsigned int dimension = 0; dimension < VImageDimension; ++dimension)
427  {
428  mmPerPixel[dimension] = inputImage->GetSpacing()[dimension];
429  }
430 
431  // update convolution kernel
432  typedef itk::Image< float, VImageDimension > KernelImageType;
433  typename KernelImageType::Pointer convolutionKernel = this->GenerateHotspotSearchConvolutionKernel<VImageDimension>(mmPerPixel, m_HotspotRadiusinMM);
434 
435  // update convolution image
436  typedef itk::Image< TPixel, VImageDimension > InputImageType;
437  typedef itk::Image< TPixel, VImageDimension > ConvolutionImageType;
438  typedef itk::FFTConvolutionImageFilter<InputImageType,
439  KernelImageType,
440  ConvolutionImageType> ConvolutionFilterType;
441 
442  typename ConvolutionFilterType::Pointer convolutionFilter = ConvolutionFilterType::New();
443  typedef itk::ConstantBoundaryCondition<InputImageType, InputImageType> BoundaryConditionType;
444  BoundaryConditionType boundaryCondition;
445  boundaryCondition.SetConstant(0.0);
446 
447  if (m_HotspotMustBeCompletelyInsideImage)
448  {
449  // overwrite default boundary condition
450  convolutionFilter->SetBoundaryCondition(&boundaryCondition);
451  }
452 
453  convolutionFilter->SetInput(inputImage);
454  convolutionFilter->SetKernelImage(convolutionKernel);
455  convolutionFilter->SetNormalize(true);
456  MITK_DEBUG << "Update Convolution image for hotspot search";
457  convolutionFilter->UpdateLargestPossibleRegion();
458 
459  typename ConvolutionImageType::Pointer convolutionImage = convolutionFilter->GetOutput();
460  convolutionImage->SetSpacing( inputImage->GetSpacing() ); // only workaround because convolution filter seems to ignore spacing of input image
461 
462  return convolutionImage;
463  }
464 
465  template < typename TPixel, unsigned int VImageDimension>
466  void
467  HotspotMaskGenerator::FillHotspotMaskPixels( itk::Image<TPixel, VImageDimension>* maskImage,
468  itk::Point<double, VImageDimension> sphereCenter,
469  double sphereRadiusInMM )
470  {
471  typedef itk::Image< TPixel, VImageDimension > MaskImageType;
472  typedef itk::ImageRegionIteratorWithIndex<MaskImageType> MaskImageIteratorType;
473 
474  MaskImageIteratorType maskIt(maskImage, maskImage->GetLargestPossibleRegion());
475 
476  typename MaskImageType::IndexType maskIndex;
477  typename MaskImageType::PointType worldPosition;
478 
479  // this is not very smart. I would rather use a 0 initialized mask (not the case here -> blame CalculateHotspotMask) and find the region where I need to iterate over, then iterate only over the small region
480  for(maskIt.GoToBegin(); !maskIt.IsAtEnd(); ++maskIt)
481  {
482  maskIndex = maskIt.GetIndex();
483  maskImage->TransformIndexToPhysicalPoint(maskIndex, worldPosition);
484  maskIt.Set( worldPosition.EuclideanDistanceTo(sphereCenter) <= sphereRadiusInMM ? 1 : 0 );
485  }
486  }
487 
488  template <typename TPixel, unsigned int VImageDimension>
489  void
490  HotspotMaskGenerator::CalculateHotspotMask(itk::Image<TPixel, VImageDimension>* inputImage,
492  unsigned int label)
493  {
494  typedef itk::Image< TPixel, VImageDimension > InputImageType;
495  typedef itk::Image< TPixel, VImageDimension > ConvolutionImageType;
496  typedef itk::Image< float, VImageDimension > KernelImageType;
497  typedef itk::Image< unsigned short, VImageDimension > MaskImageType;
498 
499  typename ConvolutionImageType::Pointer convolutionImage = this->GenerateConvolutionImage(inputImage);
500 
501  if (convolutionImage.IsNull())
502  {
503  MITK_ERROR << "Empty convolution image in CalculateHotspotStatistics(). We should never reach this state (logic error).";
504  throw std::logic_error("Empty convolution image in CalculateHotspotStatistics()");
505  }
506 
507  // if mask image is not defined, create an image of the same size as inputImage and fill it with 1's
508  // there is maybe a better way to do this!?
509  if (maskImage == nullptr)
510  {
511  maskImage = MaskImageType::New();
512  typename MaskImageType::RegionType maskRegion = inputImage->GetLargestPossibleRegion();
513  typename MaskImageType::SpacingType maskSpacing = inputImage->GetSpacing();
514  typename MaskImageType::PointType maskOrigin = inputImage->GetOrigin();
515  typename MaskImageType::DirectionType maskDirection = inputImage->GetDirection();
516  maskImage->SetRegions(maskRegion);
517  maskImage->Allocate();
518  maskImage->SetOrigin(maskOrigin);
519  maskImage->SetSpacing(maskSpacing);
520  maskImage->SetDirection(maskDirection);
521 
522  maskImage->FillBuffer(1);
523 
524  label = 1;
525  }
526 
527  // find maximum in convolution image, given the current mask
528  double requiredDistanceToBorder = m_HotspotMustBeCompletelyInsideImage ? m_HotspotRadiusinMM : -1.0;
529  ImageExtrema convolutionImageInformation = CalculateExtremaWorld(convolutionImage.GetPointer(), maskImage, requiredDistanceToBorder, label);
530 
531  bool isHotspotDefined = convolutionImageInformation.Defined;
532 
533  if (!isHotspotDefined)
534  {
535  MITK_ERROR << "No origin of hotspot-sphere was calculated!";
536  m_InternalMask = nullptr;
537  }
538  else
539  {
540  // create a binary mask around the "hotspot" region, fill the shape of a sphere around our hotspot center
541 // typename DuplicatorType::Pointer copyMachine = DuplicatorType::New();
542 // copyMachine->SetInputImage(inputImage);
543 // copyMachine->Update();
544 
545 // typename CastFilterType::Pointer caster = CastFilterType::New();
546 // caster->SetInput( copyMachine->GetOutput() );
547 // caster->Update();
548  typename MaskImageType::Pointer hotspotMaskITK = MaskImageType::New();
549  hotspotMaskITK->SetOrigin(inputImage->GetOrigin());
550  hotspotMaskITK->SetSpacing(inputImage->GetSpacing());
551  hotspotMaskITK->SetLargestPossibleRegion(inputImage->GetLargestPossibleRegion());
552  hotspotMaskITK->SetBufferedRegion(inputImage->GetBufferedRegion());
553  hotspotMaskITK->SetDirection(inputImage->GetDirection());
554  hotspotMaskITK->SetNumberOfComponentsPerPixel(inputImage->GetNumberOfComponentsPerPixel());
555  hotspotMaskITK->Allocate();
556  hotspotMaskITK->FillBuffer(1);
557 
558  typedef typename InputImageType::IndexType IndexType;
559  IndexType maskCenterIndex;
560  for (unsigned int d =0; d< VImageDimension;++d)
561  {
562  maskCenterIndex[d]=convolutionImageInformation.MaxIndex[d];
563  }
564 
565  typename ConvolutionImageType::PointType maskCenter;
566  inputImage->TransformIndexToPhysicalPoint(maskCenterIndex,maskCenter);
567 
568  FillHotspotMaskPixels(hotspotMaskITK.GetPointer(), maskCenter, m_HotspotRadiusinMM);
569 
570  //obtain mitk::Image::Pointer from itk::Image
571  mitk::Image::Pointer hotspotMaskAsMITKImage = mitk::GrabItkImageMemory(hotspotMaskITK);
572 
573  m_InternalMask = hotspotMaskAsMITKImage;
574  m_ConvolutionImageMaxIndex = convolutionImageInformation.MaxIndex;
575  m_ConvolutionImageMinIndex = convolutionImageInformation.MinIndex;
576  }
577  }
578 
579  bool HotspotMaskGenerator::IsUpdateRequired() const
580  {
581  unsigned long thisClassTimeStamp = this->GetMTime();
582  unsigned long internalMaskTimeStamp = m_InternalMask->GetMTime();
583  unsigned long maskGeneratorTimeStamp = m_Mask->GetMTime();
584  unsigned long inputImageTimeStamp = m_inputImage->GetMTime();
585 
586  if (thisClassTimeStamp > m_InternalMaskUpdateTime) // inputs have changed
587  {
588  return true;
589  }
590 
591  if (m_InternalMaskUpdateTime < maskGeneratorTimeStamp || m_InternalMaskUpdateTime < inputImageTimeStamp) // mask image has changed outside of this class
592  {
593  return true;
594  }
595 
596  if (internalMaskTimeStamp > m_InternalMaskUpdateTime) // internal mask has been changed outside of this class
597  {
598  return true;
599  }
600 
601  return false;
602  }
603 }
mitk::Image::Pointer m_inputImage
vnl_vector< int > GetHotspotIndex()
Returns the image index where the hotspot is located.
mitk::Point3D PointType
void SetHotspotRadiusInMM(double radiusInMillimeter)
Set the radius of the hotspot (in MM)
itk::SmartPointer< Self > Pointer
#define MITK_ERROR
Definition: mitkLogMacros.h:24
const double & GetHotspotRadiusinMM() const
#define MITK_DEBUG
Definition: mitkLogMacros.h:26
DataCollection - Class to facilitate loading/accessing structured data.
void SetLabel(unsigned short label)
If a maskGenerator is set, this detemines which mask value is used.
void SetInputImage(mitk::Image::Pointer inputImage)
Set the input image. Required for this class.
Image::Pointer GrabItkImageMemory(itk::SmartPointer< ItkOutputImageType > &itkimage, mitk::Image *mitkImage=nullptr, const BaseGeometry *geometry=nullptr, bool update=true)
Grabs the memory of an itk::Image (with a specific type) and puts it into an mitk::Image.The memory is managed by the mitk::Image after calling this function. The itk::Image remains valid until the mitk::Image decides to free the memory.
mitk::Image::Pointer GetMask()
Computes and returns the hotspot mask. The hotspot mask has the same size as the input image...
void SetMask(MaskGenerator::Pointer mask)
Set a mask (can be nullptr if no mask is desired)
map::core::discrete::Elements< 3 >::InternalImageType ImageType
itk::Image< double, 3 > InputImageType
#define AccessFixedDimensionByItk_2(mitkImage, itkImageTypeFunction, dimension, arg1, arg2)
itk::Image< unsigned char, 3 > MaskImageType
Definition: CLBrainMask.cpp:36
void SetTimeStep(unsigned int timeStep)
SetTimeStep is used to set the time step for which the mask is to be generated.
static T max(T x, T y)
Definition: svm.cpp:70
mitk::Image::Pointer m_InternalMask
vnl_vector< int > GetConvolutionImageMinIndex()
Returns the index where the convolution image is minimal (darkest spot in image)
void SetHotspotMustBeCompletelyInsideImage(bool hotspotCompletelyInsideImage)
Define whether the hotspot must be completely inside the image. Default is true.
static Pointer New()
static T min(T x, T y)
Definition: svm.cpp:67
void MITKCORE_EXPORT CastToItkImage(const mitk::Image *mitkImage, itk::SmartPointer< ItkOutputImageType > &itkOutputImage)
Cast an mitk::Image to an itk::Image with a specific type.
static Pointer New()
static itkEventMacro(BoundingShapeInteractionEvent, itk::AnyEvent) class MITKBOUNDINGSHAPE_EXPORT BoundingShapeInteractor Pointer New()
Basic interaction methods for mitk::GeometryData.