00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #include "mitkBinaryThresholdULTool.h"
00019
00020 #include "mitkBinaryThresholdULTool.xpm"
00021
00022 #include "mitkToolManager.h"
00023 #include "mitkBoundingObjectToSegmentationFilter.h"
00024
00025 #include <mitkCoreObjectFactory.h>
00026 #include "mitkLevelWindowProperty.h"
00027 #include "mitkColorProperty.h"
00028 #include "mitkProperties.h"
00029 #include "mitkOrganTypeProperty.h"
00030 #include "mitkVtkResliceInterpolationProperty.h"
00031 #include "mitkDataStorage.h"
00032 #include "mitkRenderingManager.h"
00033
00034 #include "mitkImageCast.h"
00035 #include "mitkImageTimeSelector.h"
00036 #include <itkImageRegionIterator.h>
00037 #include <itkMaskImageFilter.h>
00038 #include <itkBinaryThresholdImageFilter.h>
00039
00040 namespace mitk {
00041 MITK_TOOL_MACRO(MitkExt_EXPORT, BinaryThresholdULTool, "ThresholdingUL tool");
00042 }
00043
00044 mitk::BinaryThresholdULTool::BinaryThresholdULTool()
00045 :m_SensibleMinimumThresholdValue(-100),
00046 m_SensibleMaximumThresholdValue(+100),
00047 m_CurrentLowerThresholdValue(1),
00048 m_CurrentUpperThresholdValue(1)
00049 {
00050 this->SupportRoiOn();
00051
00052 m_ThresholdFeedbackNode = DataNode::New();
00053 mitk::CoreObjectFactory::GetInstance()->SetDefaultProperties( m_ThresholdFeedbackNode );
00054
00055 m_ThresholdFeedbackNode->SetProperty( "color", ColorProperty::New(1.0, 0.0, 0.0) );
00056 m_ThresholdFeedbackNode->SetProperty( "texture interpolation", BoolProperty::New(false) );
00057 m_ThresholdFeedbackNode->SetProperty( "layer", IntProperty::New( 100 ) );
00058
00059 m_ThresholdFeedbackNode->SetProperty( "name", StringProperty::New("Thresholding feedback") );
00060 m_ThresholdFeedbackNode->SetProperty( "opacity", FloatProperty::New(0.3) );
00061 m_ThresholdFeedbackNode->SetProperty("binary", BoolProperty::New(true));
00062 m_ThresholdFeedbackNode->SetProperty( "helper object", BoolProperty::New(true) );
00063 }
00064
00065 mitk::BinaryThresholdULTool::~BinaryThresholdULTool()
00066 {
00067 }
00068
00069 const char** mitk::BinaryThresholdULTool::GetXPM() const
00070 {
00071 return mitkBinaryThresholdULTool_xpm;
00072 }
00073
00074 const char* mitk::BinaryThresholdULTool::GetName() const
00075 {
00076 return "ThresholdingUL";
00077 }
00078
00079 void mitk::BinaryThresholdULTool::Activated()
00080 {
00081 m_ToolManager->RoiDataChanged += mitk::MessageDelegate<mitk::BinaryThresholdULTool>(this, &mitk::BinaryThresholdULTool::OnRoiDataChanged);
00082 m_OriginalImageNode = m_ToolManager->GetReferenceData(0);
00083 m_NodeForThresholding = m_OriginalImageNode;
00084
00085 if ( m_NodeForThresholding.IsNotNull() )
00086 {
00087 SetupPreviewNodeFor( m_NodeForThresholding );
00088 }
00089 else
00090 {
00091 m_ToolManager->ActivateTool(-1);
00092 }
00093 }
00094
00095 void mitk::BinaryThresholdULTool::Deactivated()
00096 {
00097 m_ToolManager->RoiDataChanged -= mitk::MessageDelegate<mitk::BinaryThresholdULTool>(this, &mitk::BinaryThresholdULTool::OnRoiDataChanged);
00098 m_NodeForThresholding = NULL;
00099 m_OriginalImageNode = NULL;
00100 try
00101 {
00102 if (DataStorage* storage = m_ToolManager->GetDataStorage())
00103 {
00104 storage->Remove( m_ThresholdFeedbackNode );
00105 RenderingManager::GetInstance()->RequestUpdateAll();
00106 }
00107 }
00108 catch(...)
00109 {
00110
00111 }
00112 m_ThresholdFeedbackNode->SetData(NULL);
00113 }
00114
00115 void mitk::BinaryThresholdULTool::SetThresholdValues(int lower, int upper)
00116 {
00117 if (m_ThresholdFeedbackNode.IsNotNull())
00118 {
00119 m_CurrentLowerThresholdValue = lower;
00120 m_CurrentUpperThresholdValue = upper;
00121 UpdatePreview();
00122
00123 RenderingManager::GetInstance()->RequestUpdateAll();
00124 }
00125 }
00126
00127 void mitk::BinaryThresholdULTool::AcceptCurrentThresholdValue(const std::string& organName, const Color& color)
00128 {
00129
00130 CreateNewSegmentationFromThreshold(m_NodeForThresholding, organName, color );
00131
00132 RenderingManager::GetInstance()->RequestUpdateAll();
00133 m_ToolManager->ActivateTool(-1);
00134 }
00135
00136 void mitk::BinaryThresholdULTool::CancelThresholding()
00137 {
00138 m_ToolManager->ActivateTool(-1);
00139 }
00140
00141 void mitk::BinaryThresholdULTool::SetupPreviewNodeFor( DataNode* nodeForThresholding )
00142 {
00143 if (nodeForThresholding)
00144 {
00145 Image::Pointer image = dynamic_cast<Image*>( nodeForThresholding->GetData() );
00146 Image::Pointer originalImage = dynamic_cast<Image*> (m_OriginalImageNode->GetData());
00147 if (image.IsNotNull())
00148 {
00149
00150
00151 m_ThresholdFeedbackNode->SetData( image );
00152 int layer(50);
00153 nodeForThresholding->GetIntProperty("layer", layer);
00154 m_ThresholdFeedbackNode->SetIntProperty("layer", layer+1);
00155
00156 if (DataStorage* storage = m_ToolManager->GetDataStorage())
00157 {
00158 if (storage->Exists(m_ThresholdFeedbackNode))
00159 storage->Remove(m_ThresholdFeedbackNode);
00160 storage->Add( m_ThresholdFeedbackNode, nodeForThresholding );
00161 }
00162
00163 m_SensibleMinimumThresholdValue = static_cast<int>( originalImage->GetScalarValueMin() );
00164 m_SensibleMaximumThresholdValue = static_cast<int>( originalImage->GetScalarValueMax() );
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174 m_CurrentLowerThresholdValue = (m_SensibleMaximumThresholdValue + m_SensibleMinimumThresholdValue) / 3;
00175 m_CurrentUpperThresholdValue = 2*m_CurrentLowerThresholdValue;
00176
00177
00178 IntervalBordersChanged.Send(m_SensibleMinimumThresholdValue, m_SensibleMaximumThresholdValue);
00179 ThresholdingValuesChanged.Send(m_CurrentLowerThresholdValue, m_CurrentUpperThresholdValue);
00180 }
00181 }
00182 }
00183
00184 void mitk::BinaryThresholdULTool::CreateNewSegmentationFromThreshold(DataNode* node, const std::string& organName, const Color& color)
00185 {
00186 if (node)
00187 {
00188 Image::Pointer image = dynamic_cast<Image*>( m_NodeForThresholding->GetData() );
00189 if (image.IsNotNull())
00190 {
00191
00192 DataNode::Pointer emptySegmentation = Tool::CreateEmptySegmentationNode( image, organName, color );
00193
00194 if (emptySegmentation)
00195 {
00196
00197 for (unsigned int timeStep = 0; timeStep < image->GetTimeSteps(); ++timeStep)
00198 {
00199 try
00200 {
00201 ImageTimeSelector::Pointer timeSelector = ImageTimeSelector::New();
00202 timeSelector->SetInput( image );
00203 timeSelector->SetTimeNr( timeStep );
00204 timeSelector->UpdateLargestPossibleRegion();
00205 Image::Pointer image3D = timeSelector->GetOutput();
00206
00207 AccessFixedDimensionByItk_2( image3D, ITKThresholding, 3, dynamic_cast<Image*>(emptySegmentation->GetData()), timeStep );
00208 }
00209 catch(...)
00210 {
00211 Tool::ErrorMessage("Error accessing single time steps of the original image. Cannot create segmentation.");
00212 }
00213 }
00214
00215 if (DataStorage* storage = m_ToolManager->GetDataStorage())
00216 {
00217 storage->Add( emptySegmentation, m_OriginalImageNode );
00218 }
00219
00220 m_ToolManager->SetWorkingData( emptySegmentation );
00221 }
00222 }
00223 }
00224 }
00225
00226 template <typename TPixel, unsigned int VImageDimension>
00227 void mitk::BinaryThresholdULTool::ITKThresholding( itk::Image<TPixel, VImageDimension>* originalImage, Image* segmentation, unsigned int timeStep )
00228 {
00229 ImageTimeSelector::Pointer timeSelector = ImageTimeSelector::New();
00230 timeSelector->SetInput( segmentation );
00231 timeSelector->SetTimeNr( timeStep );
00232 timeSelector->UpdateLargestPossibleRegion();
00233 Image::Pointer segmentation3D = timeSelector->GetOutput();
00234
00235 typedef itk::Image< Tool::DefaultSegmentationDataType, 3> SegmentationType;
00236 SegmentationType::Pointer itkSegmentation;
00237 CastToItkImage( segmentation3D, itkSegmentation );
00238
00239
00240 typedef itk::ImageRegionConstIterator< itk::Image<TPixel, VImageDimension> > InputIteratorType;
00241 typedef itk::ImageRegionIterator< SegmentationType > SegmentationIteratorType;
00242
00243 InputIteratorType inputIterator( originalImage, originalImage->GetLargestPossibleRegion() );
00244 SegmentationIteratorType outputIterator( itkSegmentation, itkSegmentation->GetLargestPossibleRegion() );
00245
00246 inputIterator.GoToBegin();
00247 outputIterator.GoToBegin();
00248
00249 while (!outputIterator.IsAtEnd())
00250 {
00251 if ( (signed)inputIterator.Get() >= m_CurrentLowerThresholdValue && (signed)inputIterator.Get() <= m_CurrentUpperThresholdValue )
00252 {
00253 outputIterator.Set( 1 );
00254 }
00255 else
00256 {
00257 outputIterator.Set( 0 );
00258 }
00259
00260 ++inputIterator;
00261 ++outputIterator;
00262 }
00263 }
00264
00265 void mitk::BinaryThresholdULTool::OnRoiDataChanged()
00266 {
00267 typedef itk::Image<int, 3> ItkImageType;
00268 typedef itk::Image<unsigned char, 3> ItkMaskType;
00269 typedef itk::MaskImageFilter<ItkImageType, ItkMaskType, ItkImageType> MaskFilterType;
00270 mitk::DataNode* node = m_ToolManager->GetRoiData(0);
00271 if (node == NULL)
00272 {
00273 this->SetupPreviewNodeFor(m_OriginalImageNode);
00274 m_NodeForThresholding = m_OriginalImageNode;
00275 return;
00276 }
00277
00278 mitk::DataNode::Pointer new_node = mitk::DataNode::New();
00279 mitk::Image* image = dynamic_cast<mitk::Image*> (m_OriginalImageNode->GetData());
00280 mitk::Image::Pointer new_image = mitk::Image::New();
00281
00282 mitk::Image::Pointer roi;
00283 mitk::BoundingObject* boundingObject = dynamic_cast<mitk::BoundingObject*> (node->GetData());
00284
00285 if (boundingObject)
00286 {
00287 mitk::BoundingObjectToSegmentationFilter::Pointer filter = mitk::BoundingObjectToSegmentationFilter::New();
00288 filter->SetBoundingObject( boundingObject);
00289 filter->SetInput(image);
00290 filter->Update();
00291 roi = filter->GetOutput();
00292 }
00293 else
00294 roi = dynamic_cast<mitk::Image*> (node->GetData());
00295
00296 if (roi)
00297 {
00298 MaskFilterType::Pointer filter = MaskFilterType::New();
00299 ItkMaskType::Pointer itkRoi = ItkMaskType::New();
00300 ItkImageType::Pointer itkImage = ItkImageType::New();
00301 mitk::CastToItkImage(image, itkImage);
00302 mitk::CastToItkImage(roi, itkRoi);
00303 filter->SetInput1(itkImage);
00304 filter->SetInput2(itkRoi);
00305 filter->SetOutsideValue(-32765);
00306 filter->Update();
00307 mitk::CastToMitkImage(filter->GetOutput(),new_image);
00308 }
00309 new_node->SetData(new_image);
00310
00311 this->SetupPreviewNodeFor(new_node);
00312 m_NodeForThresholding = new_node;
00313 UpdatePreview();
00314 }
00315
00316 void mitk::BinaryThresholdULTool::UpdatePreview()
00317 {
00318 typedef itk::Image<int, 3> ImageType;
00319 typedef itk::Image<unsigned char, 3> SegmentationType;
00320 typedef itk::BinaryThresholdImageFilter<ImageType, SegmentationType> ThresholdFilterType;
00321 mitk::Image::Pointer thresholdimage = dynamic_cast<mitk::Image*> (m_NodeForThresholding->GetData());
00322 if(thresholdimage)
00323 {
00324 ImageType::Pointer itkImage = ImageType::New();
00325 CastToItkImage(thresholdimage, itkImage);
00326 ThresholdFilterType::Pointer filter = ThresholdFilterType::New();
00327 filter->SetInput(itkImage);
00328 filter->SetLowerThreshold(m_CurrentLowerThresholdValue);
00329 filter->SetUpperThreshold(m_CurrentUpperThresholdValue);
00330 filter->SetInsideValue(1);
00331 filter->SetOutsideValue(0);
00332 filter->Update();
00333
00334 mitk::Image::Pointer new_image = mitk::Image::New();
00335 CastToMitkImage(filter->GetOutput(), new_image);
00336 m_ThresholdFeedbackNode->SetData(new_image);
00337 }
00338 }