diff --git a/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.cpp b/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.cpp index bb3b59670a..5c8ec14b9d 100644 --- a/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.cpp +++ b/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.cpp @@ -1,90 +1,108 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "mitkSurfaceToSurfaceFilter.h" #include "mitkSurface.h" mitk::SurfaceToSurfaceFilter::SurfaceToSurfaceFilter() : SurfaceSource() { } mitk::SurfaceToSurfaceFilter::~SurfaceToSurfaceFilter() { } void mitk::SurfaceToSurfaceFilter::SetInput( const mitk::Surface* surface ) { this->SetInput( 0, const_cast( surface ) ); } void mitk::SurfaceToSurfaceFilter::SetInput( unsigned int idx, const mitk::Surface* surface ) { if ( this->GetInput(idx) != surface ) { this->SetNthInput( idx, const_cast( surface ) ); - this->CreateOutputsForAllInputs(idx); + this->CreateOutputForInput(idx); this->Modified(); } } const mitk::Surface* mitk::SurfaceToSurfaceFilter::GetInput() { if (this->GetNumberOfInputs() < 1) return NULL; return static_cast(this->ProcessObject::GetInput(0)); } const mitk::Surface* mitk::SurfaceToSurfaceFilter::GetInput( unsigned int idx) { if (this->GetNumberOfInputs() < 1) return NULL; return static_cast(this->ProcessObject::GetInput(idx)); } +void mitk::SurfaceToSurfaceFilter::CreateOutputForInput(unsigned int idx) +{ + if (this->GetNumberOfIndexedInputs() < idx || this->GetInput(idx) == NULL) + { + mitkThrow() << "Error creating output for input [" <GetNumberOfIndexedOutputs() <= idx) + this->SetNumberOfIndexedOutputs( idx+1 ); + + if (this->GetOutput(idx) == NULL) + { + DataObjectPointer newOutput = this->MakeOutput(idx); + this->SetNthOutput(idx, newOutput); + } + this->GetOutput( idx )->Graft( this->GetInput( idx) ); + this->Modified(); +} -void mitk::SurfaceToSurfaceFilter::CreateOutputsForAllInputs(unsigned int /*idx*/) +void mitk::SurfaceToSurfaceFilter::CreateOutputsForAllInputs() { this->SetNumberOfIndexedOutputs( this->GetNumberOfIndexedInputs() ); for (unsigned int idx = 0; idx < this->GetNumberOfIndexedInputs(); ++idx) { if (this->GetOutput(idx) == NULL) { DataObjectPointer newOutput = this->MakeOutput(idx); this->SetNthOutput(idx, newOutput); } this->GetOutput( idx )->Graft( this->GetInput( idx) ); } this->Modified(); } void mitk::SurfaceToSurfaceFilter::RemoveInputs( mitk::Surface* surface ) { for (unsigned int idx = 0; idx < this->GetNumberOfIndexedInputs(); ++idx) { if ( this->GetInput(idx) == surface ) { this->RemoveOutput(idx); } } } diff --git a/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.h b/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.h index 1452868b49..b6e74c5e3c 100644 --- a/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.h +++ b/Core/Code/Algorithms/mitkSurfaceToSurfaceFilter.h @@ -1,68 +1,85 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #ifndef MITKSURFACETOSURFACEFILTER_H_HEADER_INCLUDED_C10B4740 #define MITKSURFACETOSURFACEFILTER_H_HEADER_INCLUDED_C10B4740 #include "mitkSurfaceSource.h" namespace mitk { class Surface; //##Documentation //## @brief Superclass of all classes getting surfaces (instances of class //## Surface) as input and generating surfaces as output. //## //## In itk and vtk the generated result of a ProcessObject is only guaranteed //## to be up-to-date, when Update() of the ProcessObject or the generated //## DataObject is called immediately before access of the data stored in the //## DataObject. This is also true for subclasses of mitk::BaseProcess and thus //## for mitk::mitkSurfaceToSurfaceFilter. //## @ingroup Process class MITK_CORE_EXPORT SurfaceToSurfaceFilter : public mitk::SurfaceSource { public: mitkClassMacro(SurfaceToSurfaceFilter, mitk::SurfaceSource); itkFactorylessNewMacro(Self) itkCloneMacro(Self) typedef itk::DataObject::Pointer DataObjectPointer; using itk::ProcessObject::SetInput; virtual void SetInput( const mitk::Surface* surface ); + /** + * @brief Add a new input at the given index (idx) + * Calls mitk::Surface::CreateOutputForInput(idx) + * @note The inputs must be added sequentially + * @param idx the index of the input, which must be incremental + * @param surface the input which should be added + */ virtual void SetInput( unsigned int idx, const mitk::Surface* surface ); virtual const mitk::Surface* GetInput(); virtual const mitk::Surface* GetInput( unsigned int idx ); - virtual void CreateOutputsForAllInputs(unsigned int idx); + /** + * @brief Create a new output for the input at idx + * @param idx the index of the input for which the output should be created + */ + virtual void CreateOutputForInput(unsigned int idx); + + /** + * @brief Creates outputs for all existing inputs + * @note For each existing input a new output will be allocated + */ + virtual void CreateOutputsForAllInputs(); virtual void RemoveInputs( mitk::Surface* surface ); protected: SurfaceToSurfaceFilter(); virtual ~SurfaceToSurfaceFilter(); }; } // namespace mitk #endif /* MITKSURFACETOSURFACEFILTER_H_HEADER_INCLUDED_C10B4740 */ diff --git a/Core/Code/DataManagement/mitkSurface.cpp b/Core/Code/DataManagement/mitkSurface.cpp index 843c587744..e56dc8d3e6 100644 --- a/Core/Code/DataManagement/mitkSurface.cpp +++ b/Core/Code/DataManagement/mitkSurface.cpp @@ -1,529 +1,520 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "mitkSurface.h" #include "mitkInteractionConst.h" #include "mitkSurfaceOperation.h" #include #include static vtkPolyData* DeepCopy(vtkPolyData* other) { if (other == NULL) return NULL; vtkPolyData* copy = vtkPolyData::New(); copy->DeepCopy(other); return copy; } -static void Delete(vtkPolyData* polyData) -{ - if (polyData != NULL) - polyData->Delete(); -} - static void Update(vtkPolyData* /*polyData*/) { // if (polyData != NULL) // polyData->Update(); //VTK6_TODO vtk pipeline } mitk::Surface::Surface() : m_CalculateBoundingBox(false) { this->InitializeEmpty(); } mitk::Surface::Surface(const mitk::Surface& other) : BaseData(other), m_LargestPossibleRegion(other.m_LargestPossibleRegion), m_RequestedRegion(other.m_RequestedRegion), m_CalculateBoundingBox(other.m_CalculateBoundingBox) { if(!other.m_PolyDatas.empty()) { m_PolyDatas.resize(other.m_PolyDatas.size()); std::transform(other.m_PolyDatas.begin(), other.m_PolyDatas.end(), m_PolyDatas.begin(), DeepCopy); } else { this->InitializeEmpty(); } } void mitk::Surface::Swap(mitk::Surface& other) { std::swap(m_PolyDatas, other.m_PolyDatas); std::swap(m_LargestPossibleRegion, other.m_LargestPossibleRegion); std::swap(m_RequestedRegion, other.m_RequestedRegion); std::swap(m_CalculateBoundingBox, other.m_CalculateBoundingBox); } mitk::Surface& mitk::Surface::operator=(Surface other) { this->Swap(other); return *this; } mitk::Surface::~Surface() { this->ClearData(); } void mitk::Surface::ClearData() { - using ::Delete; - - std::for_each(m_PolyDatas.begin(), m_PolyDatas.end(), Delete); m_PolyDatas.clear(); Superclass::ClearData(); } const mitk::Surface::RegionType& mitk::Surface::GetLargestPossibleRegion() const { m_LargestPossibleRegion.SetIndex(3, 0); m_LargestPossibleRegion.SetSize(3, GetTimeGeometry()->CountTimeSteps()); return m_LargestPossibleRegion; } const mitk::Surface::RegionType& mitk::Surface::GetRequestedRegion() const { return m_RequestedRegion; } void mitk::Surface::InitializeEmpty() { if (!m_PolyDatas.empty()) this->ClearData(); Superclass::InitializeTimeGeometry(); m_PolyDatas.push_back(NULL); m_Initialized = true; } void mitk::Surface::SetVtkPolyData(vtkPolyData* polyData, unsigned int t) { this->Expand(t + 1); if (m_PolyDatas[t] != NULL) { if (m_PolyDatas[t] == polyData) return; m_PolyDatas[t]->Delete(); } m_PolyDatas[t] = polyData; if(polyData != NULL) polyData->Register(NULL); m_CalculateBoundingBox = true; this->Modified(); this->UpdateOutputInformation(); } bool mitk::Surface::IsEmptyTimeStep(unsigned int t) const { if(!IsInitialized()) return false; vtkPolyData* polyData = const_cast(this)->GetVtkPolyData(t); return polyData == NULL || ( polyData->GetNumberOfLines() == 0 && polyData->GetNumberOfPolys() == 0 && polyData->GetNumberOfStrips() == 0 && polyData->GetNumberOfVerts() == 0 ); } vtkPolyData* mitk::Surface::GetVtkPolyData(unsigned int t) const { if (t < m_PolyDatas.size()) { if(m_PolyDatas[t] == NULL && this->GetSource().IsNotNull()) { RegionType requestedRegion; requestedRegion.SetIndex(3, t); requestedRegion.SetSize(3, 1); this->m_RequestedRegion = requestedRegion; this->GetSource()->Update(); } - return m_PolyDatas[t]; + return m_PolyDatas[t].GetPointer(); } return NULL; } void mitk::Surface::UpdateOutputInformation() { if (this->GetSource().IsNotNull()) this->GetSource()->UpdateOutputInformation(); if (m_CalculateBoundingBox == true && !m_PolyDatas.empty()) this->CalculateBoundingBox(); else this->GetTimeGeometry()->Update(); } void mitk::Surface::CalculateBoundingBox() { TimeGeometry* timeGeometry = this->GetTimeGeometry(); if (timeGeometry->CountTimeSteps() != m_PolyDatas.size()) mitkThrow() << "Number of geometry time steps is inconsistent with number of poly data pointers."; for (unsigned int i = 0; i < m_PolyDatas.size(); ++i) { vtkPolyData* polyData = m_PolyDatas[i]; double bounds[6] = {0}; if (polyData != NULL && polyData->GetNumberOfPoints() > 0) { // polyData->Update(); //VTK6_TODO vtk pipeline polyData->ComputeBounds(); polyData->GetBounds(bounds); } BaseGeometry::Pointer geometry = timeGeometry->GetGeometryForTimeStep(i); if (geometry.IsNull()) mitkThrow() << "Time-sliced geometry is invalid (equals NULL)."; geometry->SetFloatBounds(bounds); } timeGeometry->Update(); m_CalculateBoundingBox = false; } void mitk::Surface::SetRequestedRegionToLargestPossibleRegion() { m_RequestedRegion = GetLargestPossibleRegion(); } bool mitk::Surface::RequestedRegionIsOutsideOfTheBufferedRegion() { RegionType::IndexValueType end = m_RequestedRegion.GetIndex(3) + m_RequestedRegion.GetSize(3); if(static_cast(m_PolyDatas.size()) < end) return true; for(RegionType::IndexValueType t = m_RequestedRegion.GetIndex(3); t < end; ++t) { if(m_PolyDatas[t] == NULL) return true; } return false; } bool mitk::Surface::VerifyRequestedRegion() { if(m_RequestedRegion.GetIndex(3) >= 0 && m_RequestedRegion.GetIndex(3) + m_RequestedRegion.GetSize(3) <= m_PolyDatas.size()) return true; return false; } void mitk::Surface::SetRequestedRegion(const itk::DataObject* data ) { const mitk::Surface *surface = dynamic_cast(data); if (surface != NULL) m_RequestedRegion = surface->GetRequestedRegion(); else mitkThrow() << "Data object used to get requested region is not a mitk::Surface."; } void mitk::Surface::SetRequestedRegion(Surface::RegionType* region) { if (region == NULL) mitkThrow() << "Requested region is invalid (equals NULL)"; m_RequestedRegion = *region; } void mitk::Surface::CopyInformation(const itk::DataObject* data) { Superclass::CopyInformation(data); const mitk::Surface* surface = dynamic_cast(data); if (surface == NULL) mitkThrow() << "Data object used to get largest possible region is not a mitk::Surface."; m_LargestPossibleRegion = surface->GetLargestPossibleRegion(); } void mitk::Surface::Update() { using ::Update; if (this->GetSource().IsNull()) std::for_each(m_PolyDatas.begin(), m_PolyDatas.end(), Update); Superclass::Update(); } void mitk::Surface::Expand(unsigned int timeSteps) { if (timeSteps > m_PolyDatas.size()) { Superclass::Expand(timeSteps); m_PolyDatas.resize(timeSteps); m_CalculateBoundingBox = true; } } void mitk::Surface::ExecuteOperation(Operation* operation) { switch (operation->GetOperationType()) { case OpSURFACECHANGED: { mitk::SurfaceOperation* surfaceOperation = dynamic_cast(operation); if(surfaceOperation == NULL) break; unsigned int timeStep = surfaceOperation->GetTimeStep(); if(m_PolyDatas[timeStep] != NULL) { vtkPolyData* updatedPolyData = surfaceOperation->GetVtkPolyData(); if(updatedPolyData != NULL) { this->SetVtkPolyData(updatedPolyData, timeStep); this->CalculateBoundingBox(); this->Modified(); } } break; } default: return; } } unsigned int mitk::Surface::GetSizeOfPolyDataSeries() const { return m_PolyDatas.size(); } void mitk::Surface::Graft(const DataObject* data) { const Surface* surface = dynamic_cast(data); if(surface == NULL) mitkThrow() << "Data object used to graft surface is not a mitk::Surface."; this->CopyInformation(data); m_PolyDatas.clear(); for (unsigned int i = 0; i < surface->GetSizeOfPolyDataSeries(); ++i) { - m_PolyDatas.push_back(vtkPolyData::New()); + m_PolyDatas.push_back(vtkSmartPointer::New()); m_PolyDatas.back()->DeepCopy(const_cast(surface)->GetVtkPolyData(i)); } } void mitk::Surface::PrintSelf(std::ostream& os, itk::Indent indent) const { Superclass::PrintSelf(os, indent); os << indent << "\nNumber PolyDatas: " << m_PolyDatas.size() << "\n"; unsigned int count = 0; - for (std::vector::const_iterator it = m_PolyDatas.begin(); it != m_PolyDatas.end(); ++it) + for (std::vector >::const_iterator it = m_PolyDatas.begin(); it != m_PolyDatas.end(); ++it) { os << "\n"; if(*it != NULL) { os << indent << "PolyData at time step " << count << ":\n"; os << indent << "Number of cells: " << (*it)->GetNumberOfCells() << "\n"; os << indent << "Number of points: " << (*it)->GetNumberOfPoints() << "\n\n"; os << indent << "VTKPolyData:\n"; (*it)->Print(os); } else { os << indent << "Empty PolyData at time step " << count << "\n"; } ++count; } } bool mitk::Equal( vtkPolyData* leftHandSide, vtkPolyData* rightHandSide, mitk::ScalarType eps, bool verbose ) { if(( leftHandSide == NULL ) || ( rightHandSide == NULL )) { MITK_ERROR << "mitk::Equal( vtkPolyData* leftHandSide, vtkPolyData* rightHandSide, mitk::ScalarType eps, bool verbose ) does not work for NULL pointer input."; return false; } return Equal( *leftHandSide, *rightHandSide, eps, verbose); } bool mitk::Equal( vtkPolyData& leftHandSide, vtkPolyData& rightHandSide, mitk::ScalarType eps, bool verbose ) { bool noDifferenceFound = true; if( ! mitk::Equal( leftHandSide.GetNumberOfCells(), rightHandSide.GetNumberOfCells(), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of cells not equal"; noDifferenceFound = false; } if( ! mitk::Equal( leftHandSide.GetNumberOfVerts(), rightHandSide.GetNumberOfVerts(), eps, verbose )) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of vertices not equal"; noDifferenceFound = false; } if( ! mitk::Equal( leftHandSide.GetNumberOfLines(), rightHandSide.GetNumberOfLines(), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of lines not equal"; noDifferenceFound = false; } if( ! mitk::Equal( leftHandSide.GetNumberOfPolys(), rightHandSide.GetNumberOfPolys(), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of polys not equal"; noDifferenceFound = false; } if( ! mitk::Equal( leftHandSide.GetNumberOfStrips(), rightHandSide.GetNumberOfStrips(), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of strips not equal"; noDifferenceFound = false; } { unsigned int numberOfPointsRight = rightHandSide.GetPoints()->GetNumberOfPoints(); unsigned int numberOfPointsLeft = leftHandSide.GetPoints()->GetNumberOfPoints(); if(! mitk::Equal( numberOfPointsLeft, numberOfPointsRight, eps, verbose )) { if(verbose) MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Number of points not equal"; noDifferenceFound = false; } else { for( unsigned int i( 0 ); i < numberOfPointsRight; i++ ) { bool pointFound = false; double pointOne[3]; rightHandSide.GetPoints()->GetPoint(i, pointOne); for( unsigned int j( 0 ); j < numberOfPointsLeft; j++ ) { double pointTwo[3]; leftHandSide.GetPoints()->GetPoint(j, pointTwo); double x = pointOne[0] - pointTwo[0]; double y = pointOne[1] - pointTwo[1]; double z = pointOne[2] - pointTwo[2]; double distance = x*x + y*y + z*z; if( distance < eps ) { pointFound = true; break; } } if( !pointFound ) { if(verbose) { MITK_INFO << "[Equal( vtkPolyData*, vtkPolyData* )] Right hand side point with id " << i << " and coordinates ( " << std::setprecision(12) << pointOne[0] << " ; " << pointOne[1] << " ; " << pointOne[2] << " ) could not be found in left hand side with epsilon " << eps << "."; } noDifferenceFound = false; break; } } } } return noDifferenceFound; } bool mitk::Equal( mitk::Surface* leftHandSide, mitk::Surface* rightHandSide, mitk::ScalarType eps, bool verbose ) { if(( leftHandSide == NULL ) || ( rightHandSide == NULL )) { MITK_ERROR << "mitk::Equal( mitk::Surface* leftHandSide, mitk::Surface* rightHandSide, mitk::ScalarType eps, bool verbose ) does not work with NULL pointer input."; return false; } return Equal( *leftHandSide, *rightHandSide, eps, verbose); } bool mitk::Equal( mitk::Surface& leftHandSide, mitk::Surface& rightHandSide, mitk::ScalarType eps, bool verbose ) { bool noDifferenceFound = true; if( ! mitk::Equal( leftHandSide.GetSizeOfPolyDataSeries(), rightHandSide.GetSizeOfPolyDataSeries(), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( mitk::surface&, mitk::surface& )] Size of PolyData series not equal."; return false; } // No mitk::Equal for TimeGeometry implemented. //if( ! mitk::Equal( leftHandSide->GetTimeGeometry(), rightHandSide->GetTimeGeometry(), eps, verbose ) ) //{ // if(verbose) // MITK_INFO << "[Equal( mitk::surface&, mitk::surface& )] Time sliced geometries not equal"; // noDifferenceFound = false; //} for( unsigned int i( 0 ); i < rightHandSide.GetSizeOfPolyDataSeries(); i++ ) { if( ! mitk::Equal( *leftHandSide.GetVtkPolyData( i ), *rightHandSide.GetVtkPolyData( i ), eps, verbose ) ) { if(verbose) MITK_INFO << "[Equal( mitk::surface&, mitk::surface& )] Poly datas not equal."; noDifferenceFound = false; } } return noDifferenceFound; } diff --git a/Core/Code/DataManagement/mitkSurface.h b/Core/Code/DataManagement/mitkSurface.h index 83b0244154..904b279585 100644 --- a/Core/Code/DataManagement/mitkSurface.h +++ b/Core/Code/DataManagement/mitkSurface.h @@ -1,136 +1,137 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #ifndef mitkSurface_h #define mitkSurface_h #include "mitkBaseData.h" #include "itkImageRegion.h" +#include class vtkPolyData; namespace mitk { /** * \brief Class for storing surfaces (vtkPolyData). * \ingroup Data */ class MITK_CORE_EXPORT Surface : public BaseData { public: typedef itk::ImageRegion<5> RegionType; mitkClassMacro(Surface, BaseData); itkFactorylessNewMacro(Self) itkCloneMacro(Self) void CalculateBoundingBox(); virtual void CopyInformation(const itk::DataObject *data); virtual void ExecuteOperation(Operation *operation); virtual void Expand( unsigned int timeSteps = 1 ); const RegionType& GetLargestPossibleRegion() const; virtual const RegionType& GetRequestedRegion() const; unsigned int GetSizeOfPolyDataSeries() const; virtual vtkPolyData* GetVtkPolyData(unsigned int t = 0) const; virtual void Graft( const DataObject* data ); virtual bool IsEmptyTimeStep(unsigned int t) const; virtual void PrintSelf( std::ostream& os, itk::Indent indent ) const; virtual bool RequestedRegionIsOutsideOfTheBufferedRegion(); virtual void SetRequestedRegion(const itk::DataObject *data); virtual void SetRequestedRegion(Surface::RegionType *region); virtual void SetRequestedRegionToLargestPossibleRegion(); virtual void SetVtkPolyData(vtkPolyData* polydata, unsigned int t = 0); virtual void Swap(Surface& other); virtual void Update(); virtual void UpdateOutputInformation(); virtual bool VerifyRequestedRegion(); protected: mitkCloneMacro(Self); Surface(); virtual ~Surface(); Surface(const Surface& other); Surface& operator=(Surface other); virtual void ClearData(); virtual void InitializeEmpty(); private: - std::vector m_PolyDatas; + std::vector< vtkSmartPointer > m_PolyDatas; mutable RegionType m_LargestPossibleRegion; mutable RegionType m_RequestedRegion; bool m_CalculateBoundingBox; }; /** * @brief Equal Compare two surfaces for equality, returns true if found equal. * @warning This method is deprecated and will not be available in the future. Use the \a bool mitk::Equal(const mitk::Surface& s1, const mitk::Surface& s2) instead * @ingroup MITKTestingAPI * @param rightHandSide Surface to compare. * @param leftHandSide Surface to compare. * @param eps Epsilon to use for floating point comparison. Most of the time mitk::eps will be sufficient. * @param verbose Flag indicating if the method should give a detailed console output. * @return True if every comparison is true, false in any other case. */ DEPRECATED( MITK_CORE_EXPORT bool Equal( mitk::Surface* leftHandSide, mitk::Surface* rightHandSide, mitk::ScalarType eps, bool verbose)); /** * @brief Equal Compare two surfaces for equality, returns true if found equal. * @ingroup MITKTestingAPI * @param rightHandSide Surface to compare. * @param leftHandSide Surface to compare. * @param eps Epsilon to use for floating point comparison. Most of the time mitk::eps will be sufficient. * @param verbose Flag indicating if the method should give a detailed console output. * @return True if every comparison is true, false in any other case. */ MITK_CORE_EXPORT bool Equal( mitk::Surface& leftHandSide, mitk::Surface& rightHandSide, mitk::ScalarType eps, bool verbose); /** * @brief Equal Compare two vtk PolyDatas for equality, returns true if found equal. * @warning This method is deprecated and will not be available in the future. Use the \a bool mitk::Equal(const vtkPolyData& p1, const vtkPolyData& p2) instead * @ingroup MITKTestingAPI * @param rightHandSide Surface to compare. * @param leftHandSide Surface to compare. * @param eps Epsilon to use for floating point comparison. Most of the time mitk::eps will be sufficient. * @param verbose Flag indicating if the method should give a detailed console output. * @return True if every comparison is true, false in any other case. * * This will only check if the number of cells, vertices, polygons, stripes and lines is the same and whether * all the two poly datas have the same number of points with the same coordinates. It is not checked whether * all points are correctly connected. */ DEPRECATED( MITK_CORE_EXPORT bool Equal( vtkPolyData* leftHandSide, vtkPolyData* rightHandSide, mitk::ScalarType eps, bool verbose)); /** * @brief Equal Compare two vtk PolyDatas for equality, returns true if found equal. * @ingroup MITKTestingAPI * @param rightHandSide Surface to compare. * @param leftHandSide Surface to compare. * @param eps Epsilon to use for floating point comparison. Most of the time mitk::eps will be sufficient. * @param verbose Flag indicating if the method should give a detailed console output. * @return True if every comparison is true, false in any other case. * * This will only check if the number of cells, vertices, polygons, stripes and lines is the same and whether * all the two poly datas have the same number of points with the same coordinates. It is not checked whether * all points are correctly connected. */ MITK_CORE_EXPORT bool Equal( vtkPolyData& leftHandSide, vtkPolyData& rightHandSide, mitk::ScalarType eps, bool verbose); } #endif diff --git a/Core/Code/Testing/mitkSurfaceToSurfaceFilterTest.cpp b/Core/Code/Testing/mitkSurfaceToSurfaceFilterTest.cpp index 7f26be3e42..0fe7ca5980 100644 --- a/Core/Code/Testing/mitkSurfaceToSurfaceFilterTest.cpp +++ b/Core/Code/Testing/mitkSurfaceToSurfaceFilterTest.cpp @@ -1,121 +1,117 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "mitkSurface.h" #include "mitkSurfaceToSurfaceFilter.h" #include "mitkCommon.h" #include "mitkNumericTypes.h" +#include "mitkTestingMacros.h" #include "vtkPolyData.h" #include "vtkSphereSource.h" -#include int mitkSurfaceToSurfaceFilterTest(int /*argc*/, char* /*argv*/[]) { mitk::Surface::Pointer surface; surface = mitk::Surface::New(); vtkSphereSource* sphereSource = vtkSphereSource::New(); sphereSource->SetCenter(0,0,0); sphereSource->SetRadius(5.0); sphereSource->SetThetaResolution(10); sphereSource->SetPhiResolution(10); sphereSource->Update(); vtkPolyData* polys = sphereSource->GetOutput(); surface->SetVtkPolyData( polys ); sphereSource->Delete(); mitk::SurfaceToSurfaceFilter::Pointer filter = mitk::SurfaceToSurfaceFilter::New(); - std::cout << "Testing mitk::SurfaceToSurfaceFilter::SetInput() and ::GetNumberOfInputs() : " ; + MITK_TEST_OUTPUT(<<"Testing mitk::SurfaceToSurfaceFilter::SetInput() and ::GetNumberOfInputs() : "); filter->SetInput( surface ); - if ( filter->GetNumberOfInputs() < 1 ) - { - std::cout<<"[FAILED] : zero inputs set "<GetNumberOfInputs() == 1, "Number of inputs must be 1" ); + MITK_TEST_OUTPUT(<<"Testing if GetInput returns the right Input : "); + mitk::Surface::Pointer input = const_cast(filter->GetInput()); + MITK_ASSERT_EQUAL(input, surface, "GetInput() should return correct input. "); - std::cout << "Testing if GetInput returns the right Input : " << std::endl; - if ( filter->GetInput() != surface ) - { - std::cout<<"[FAILED] : GetInput does not return correct input. "<GetInput(5) == NULL, "GetInput(5) should return NULL. "); + MITK_TEST_OUTPUT(<<"Testing whether Output is created correctly : "); + MITK_TEST_CONDITION(filter->GetNumberOfOutputs() == filter->GetNumberOfInputs(), "Test if number of outputs == number of inputs"); - if ( filter->GetInput(5) != NULL ) - { - std::cout<<"[FAILED] : GetInput returns inputs that were not set. "< is NULL" << std::endl; + mitk::Surface::Pointer outputSurface = filter->GetOutput(); + MITK_ASSERT_EQUAL(outputSurface, surface, "Test if output == input"); + + filter->Update(); + outputSurface = filter->GetOutput(); + MITK_TEST_CONDITION(outputSurface->GetSizeOfPolyDataSeries() == surface->GetSizeOfPolyDataSeries(), "Test if number of PolyDatas in PolyDataSeries of output == number of PolyDatas of input"); + mitk::SurfaceToSurfaceFilter::Pointer s2sFilter = mitk::SurfaceToSurfaceFilter::New(); + MITK_TEST_FOR_EXCEPTION(mitk::Exception, s2sFilter->CreateOutputForInput(500)); - std::cout << "Testing whether Output is created correctly : " << std::endl; - if ( filter->GetNumberOfOutputs() != filter->GetNumberOfInputs() ) + std::vector polydatas; + for (unsigned int i = 0; i < 5; ++i) { - std::cout <<"[FAILED] : number of outputs != number of inputs" << std::endl; - return EXIT_FAILURE; + sphereSource = vtkSphereSource::New(); + sphereSource->SetCenter(0,i,0); + sphereSource->SetRadius(5.0 + i); + sphereSource->SetThetaResolution(10); + sphereSource->SetPhiResolution(10); + sphereSource->Update(); + + vtkPolyData* poly = sphereSource->GetOutput(); + mitk::Surface::Pointer s = mitk::Surface::New(); + s->SetVtkPolyData( poly ); + s2sFilter->SetInput(i, s); + polydatas.push_back(s2sFilter->GetOutput(i)->GetVtkPolyData()); + sphereSource->Delete(); } - std::cout << "[SUCCESS] : number of inputs == number of outputs." << std::endl; - - mitk::Surface::Pointer outputSurface = filter->GetOutput(); - if ( outputSurface->GetVtkPolyData()->GetNumberOfPolys() != surface->GetVtkPolyData()->GetNumberOfPolys() ) + // Test if the outputs are not recreated each time another input is added + for (unsigned int i = 0; i < 5; ++i) { - std::cout << "[FAILED] : number of Polys in PolyData of output != number of Polys in PolyData of input" << std::endl; - return EXIT_FAILURE; + MITK_TEST_CONDITION(s2sFilter->GetOutput(i)->GetVtkPolyData() == polydatas.at(i), "Test if pointers are still equal"); } - std::cout << "[SUCCESS] : number of Polys in PolyData of input and output are identical." << std::endl; - - - filter->Update(); - outputSurface = filter->GetOutput(); - if ( outputSurface->GetSizeOfPolyDataSeries() != surface->GetSizeOfPolyDataSeries() ) + // Test if the outputs are recreated after calling CreateOutputsForAllInputs() + s2sFilter->CreateOutputsForAllInputs(); + for (unsigned int i = 0; i < 5; ++i) { - std::cout << "[FAILED] : number of PolyDatas in PolyDataSeries of output != number of PolyDatas of input" << std::endl; - return EXIT_FAILURE; + MITK_TEST_CONDITION(s2sFilter->GetOutput(i)->GetVtkPolyData() != polydatas.at(i), "Test if pointers are not equal"); } - std::cout << "[SUCCESS] : Size of PolyDataSeries of input and output are identical." << std::endl; - //std::cout << "Testing RemoveInputs() : " << std::endl; //unsigned int numOfInputs = filter->GetNumberOfInputs(); //filter->RemoveInputs( mitk::Surface::New() ); //if ( filter->GetNumberOfInputs() != numOfInputs ) //{ // std::cout << "[FAILED] : input was removed that was not set." << std::endl; // return EXIT_FAILURE; //} //std::cout << "[SUCCESS] : no input was removed that was not set." << std::endl; //filter->RemoveInputs( surface ); //if ( filter->GetNumberOfInputs() != 0 ) //{ // std::cout << "[FAILED] : existing input was not removed correctly." << std::endl; // return EXIT_FAILURE; //} //std::cout << "[SUCCESS] : existing input was removed correctly." << std::endl; - - - std::cout<<"[TEST DONE]"<