diff --git a/code/interpolation/ITKTransformation/rttbITKTransformation.cpp b/code/interpolation/ITKTransformation/rttbITKTransformation.cpp index a5e442e..8d55f58 100644 --- a/code/interpolation/ITKTransformation/rttbITKTransformation.cpp +++ b/code/interpolation/ITKTransformation/rttbITKTransformation.cpp @@ -1,91 +1,85 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "rttbITKTransformation.h" #include "rttbNullPointerException.h" namespace rttb { namespace interpolation { ITKTransformation::ITKTransformation(const Transform3D3DType* aTransformation): _pTransformation(aTransformation) { //handle null pointer if (aTransformation == nullptr) { throw core::NullPointerException("Pointer to registration is nullptr."); } } void ITKTransformation::convert(const WorldCoordinate3D& aWorldCoordinate, InputPointType& aInputPoint) const { assert(aWorldCoordinate.size() == 3); assert(aInputPoint.Length == 3); for (unsigned int i = 0; i < aInputPoint.Length; ++i) { aInputPoint[i] = aWorldCoordinate[i]; } } void ITKTransformation::convert(const OutputPointType& aOutputPoint, WorldCoordinate3D& aWorldCoordinate) const { assert(aWorldCoordinate.size() == 3); assert(aOutputPoint.Length == 3); for (unsigned int i = 0; i < aOutputPoint.Length; ++i) { aWorldCoordinate[i] = aOutputPoint[i]; } } bool ITKTransformation::transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const { InputPointType aTargetPoint; OutputPointType aMovingPoint; convert(worldCoordinateTarget, aTargetPoint); aMovingPoint = _pTransformation->TransformPoint(aTargetPoint); convert(aMovingPoint, worldCoordinateMoving); //TransformPoint has no return value... return true; } bool ITKTransformation::transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const { OutputPointType aTargetPoint; InputPointType aMovingPoint; convert(worldCoordinateMoving, aMovingPoint); aTargetPoint = _pTransformation->TransformPoint(aMovingPoint); convert(aTargetPoint, worldCoordinateTarget); //TransformPoint has no return value... return true; } } } diff --git a/code/interpolation/ITKTransformation/rttbITKTransformation.h b/code/interpolation/ITKTransformation/rttbITKTransformation.h index 830fda5..3f907d3 100644 --- a/code/interpolation/ITKTransformation/rttbITKTransformation.h +++ b/code/interpolation/ITKTransformation/rttbITKTransformation.h @@ -1,81 +1,76 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __ITK_MAPPABLE_DOSE_ACCESSOR_H #define __ITK_MAPPABLE_DOSE_ACCESSOR_H #include <boost/shared_ptr.hpp> #include "itkTransform.h" #include "rttbTransformationInterface.h" #include "RTTBInterpolationITKTransformationExports.h" namespace rttb { namespace interpolation { /*! @class ITKTransformation @brief This class can deal with dose information that has to be transformed into another geometry than the original dose image (transformation specified by ITK transformation object). */ class RTTBInterpolationITKTransformation_EXPORT ITKTransformation : public TransformationInterface { public: static const unsigned int InputDimension3D = 3; static const unsigned int OutputDimension3D = 3; using TransformScalarType = double; typedef itk::Transform<TransformScalarType, InputDimension3D, OutputDimension3D> Transform3D3DType; using InputPointType = Transform3D3DType::InputPointType; using OutputPointType = Transform3D3DType::OutputPointType; private: //! Has to be a Pointer type because of inheritance issues with itkSmartPointer (that doesn't recognize the inheritance) const Transform3D3DType* _pTransformation; protected: void convert(const WorldCoordinate3D& aWorldCoordinate, InputPointType& aInputPoint) const; void convert(const OutputPointType& aOutputPoint, WorldCoordinate3D& aWorldCoordinate) const; public: /*! @brief Constructor. @param aTransformation transformation in ITK format. @sa MappableDoseAccessorBase @pre all input parameters have to be valid @exception core::NullPointerException if one input parameter is nullptr @exception core::PaddingException if the transformation is undefined and if _acceptPadding==false */ ITKTransformation(const Transform3D3DType* aTransformation); ~ITKTransformation() override = default; /*! @brief performs a transformation targetImage --> movingImage */ bool transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const override; /*! @brief performs a transformation movingImage --> targetImage */ bool transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const override; }; } } #endif diff --git a/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.cpp b/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.cpp index 09f5f65..6f72a3f 100644 --- a/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.cpp +++ b/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.cpp @@ -1,88 +1,82 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "rttbMatchPointTransformation.h" #include "rttbNullPointerException.h" namespace rttb { namespace interpolation { MatchPointTransformation::MatchPointTransformation( const Registration3D3DType* aRegistration): _pRegistration(aRegistration) { //handle null pointers if (aRegistration == nullptr) { throw core::NullPointerException("Pointer to registration is nullptr."); } } void MatchPointTransformation::convert(const WorldCoordinate3D& aWorldCoordinate, TargetPointType& aTargetPoint) const { assert(aWorldCoordinate.size() == 3); assert(aTargetPoint.Length == 3); for (unsigned int i = 0; i < aTargetPoint.Length; ++i) { aTargetPoint[i] = aWorldCoordinate[i]; } } void MatchPointTransformation::convert(const MovingPointType& aMovingPoint, WorldCoordinate3D& aWorldCoordinate) const { assert(aWorldCoordinate.size() == 3); assert(aMovingPoint.Length == 3); for (unsigned int i = 0; i < aMovingPoint.Length; ++i) { aWorldCoordinate[i] = aMovingPoint[i]; } } bool MatchPointTransformation::transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const { TargetPointType aTargetPoint; MovingPointType aMovingPoint; convert(worldCoordinateTarget, aTargetPoint); bool ok = _pRegistration->mapPointInverse(aTargetPoint, aMovingPoint); convert(aMovingPoint, worldCoordinateMoving); return ok; } bool MatchPointTransformation::transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const { TargetPointType aTargetPoint; MovingPointType aMovingPoint; convert(worldCoordinateMoving, aMovingPoint); bool ok = _pRegistration->mapPoint(aMovingPoint, aTargetPoint); convert(aTargetPoint, worldCoordinateTarget); return ok; } } } diff --git a/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.h b/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.h index 07a480f..b255571 100644 --- a/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.h +++ b/code/interpolation/MatchPointTransformation/rttbMatchPointTransformation.h @@ -1,80 +1,75 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __MATCHPOINT_TRANSFORMATION_H #define __MATCHPOINT_TRANSFORMATION_H #include "mapRegistration.h" #include "rttbTransformationInterface.h" #include "RTTBInterpolationMatchPointTransformationExports.h" namespace rttb { namespace interpolation { /*! @class MatchPointTransformation @brief This class can deal with dose information that has to be transformed into another geometry than the original dose image (transformation specified by MatchPoint registration object). @ingroup interpolation */ class RTTBInterpolationMatchPointTransformation_EXPORT MatchPointTransformation : public TransformationInterface { public: static const unsigned int TargetDimension3D = 3; static const unsigned int MovingDimension3D = 3; typedef map::core::Registration<MovingDimension3D, TargetDimension3D> Registration3D3DType; typedef map::core::Registration<MovingDimension3D, TargetDimension3D>::MovingPointType MovingPointType; typedef map::core::Registration<MovingDimension3D, TargetDimension3D>::TargetPointType TargetPointType; /*! @brief Constructor. @param aRegistration registration given in MatchPoint format (note the use of pointer since itkSmartPointer does not support inheritance) @pre all input parameters have to be valid @exception core::NullPointerException if one input parameter is nullptr @exception core::PaddingException if the transformation is undefined and if _acceptPadding==false */ MatchPointTransformation(const Registration3D3DType* aRegistration); ~MatchPointTransformation() override = default; /*! @brief performs a transformation targetImage --> movingImage */ bool transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const override; /*! @brief performs a transformation movingImage --> targetImage */ bool transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const override; protected: void convert(const WorldCoordinate3D& aWorldCoordinate, TargetPointType& aTargetPoint) const; void convert(const MovingPointType& aMovingPoint, WorldCoordinate3D& aWorldCoordinate) const; private: //! Has to be a Pointer type because of inheritance issues with itkSmartPointer (that doesn't recognize the inheritance) const Registration3D3DType* _pRegistration; }; } } #endif diff --git a/code/interpolation/rttbInterpolationBase.cpp b/code/interpolation/rttbInterpolationBase.cpp index 0fd1863..282bb3f 100644 --- a/code/interpolation/rttbInterpolationBase.cpp +++ b/code/interpolation/rttbInterpolationBase.cpp @@ -1,197 +1,191 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include <list> #include <cassert> #include "rttbInterpolationBase.h" #include "rttbInvalidParameterException.h" #include "rttbNullPointerException.h" #include "rttbMappingOutsideOfImageException.h" namespace rttb { namespace interpolation { void InterpolationBase::setAccessorPointer(core::AccessorInterface::ConstPointer originalData) { if (originalData != nullptr) { _spOriginalData = originalData; } else { throw core::NullPointerException("originalDose is nullptr!"); } }; void InterpolationBase::getNeighborhoodVoxelValues( const WorldCoordinate3D& aWorldCoordinate, unsigned int neighborhood, std::array<double, 3>& target, boost::shared_ptr<DoseTypeGy[]> values) const { if (_spOriginalData == nullptr) { throw core::NullPointerException("originalDose is nullptr!"); } //Determine target (abs(desired worldCoordinate- corner pixel world coordinate/pixel spacing) and values of corner pixels (from originalDose) VoxelGridIndex3D aIndex; if (_spOriginalData->getGeometricInfo().worldCoordinateToIndex(aWorldCoordinate, aIndex)) { //determine just the nearest voxel to the world coordinate if (neighborhood == 0) { values[0] = _spOriginalData->getValueAt(aIndex); } //determine the 8 voxels around the world coordinate else if (neighborhood == 8) { std::list<VoxelGridIndex3D> cornerPoints; WorldCoordinate3D theNextVoxel; _spOriginalData->getGeometricInfo().indexToWorldCoordinate(aIndex, theNextVoxel); SpacingVectorType3D pixelSpacing = (_spOriginalData->getGeometricInfo()).getSpacing(); VoxelGridIndex3D leftTopFrontCoordinate; //find the voxel with the smallest coordinate values in each dimension. This defines the standard cube for (unsigned int i = 0; i < 3; i++) { if (aWorldCoordinate[i] < theNextVoxel[i]) { if (aIndex[i] > 0) { leftTopFrontCoordinate[i] = aIndex[i] - 1; target[i] = (aWorldCoordinate[i] - (theNextVoxel[i] - pixelSpacing[i])) / pixelSpacing[i]; } //@todo: see T22315 else { leftTopFrontCoordinate[i] = aIndex[i]; target[i] = (aWorldCoordinate[i] - (theNextVoxel[i] - pixelSpacing[i])) / pixelSpacing[i]; } } else { leftTopFrontCoordinate[i] = aIndex[i]; target[i] = (aWorldCoordinate[i] - theNextVoxel[i]) / pixelSpacing[i]; } } for (unsigned int zIncr = 0; zIncr < 2; zIncr++) { for (unsigned int yIncr = 0; yIncr < 2; yIncr++) { for (unsigned int xIncr = 0; xIncr < 2; xIncr++) { cornerPoints.emplace_back(leftTopFrontCoordinate[0] + xIncr, leftTopFrontCoordinate[1] + yIncr, leftTopFrontCoordinate[2] + zIncr); } } } //target range has to be always [0,1] for (unsigned int i = 0; i < 3; i++) { assert(target[i] >= 0.0 && target[i] <= 1.0); } unsigned int count = 0; //now just get the values of all (dose) voxels and store them in values for (auto cornerPointsIterator = cornerPoints.begin(); cornerPointsIterator != cornerPoints.end(); ++cornerPointsIterator, ++count) { if (_spOriginalData->getGeometricInfo().isInside(*cornerPointsIterator)) { values[count] = _spOriginalData->getValueAt(*cornerPointsIterator); } else { //outside value! boundary treatment values[count] = getNearestInsideVoxelValue(*cornerPointsIterator); } assert(values[count] != -1); } } else { throw core::InvalidParameterException("neighborhoods other than 0 and 8 not yet supported in Interpolation"); } } else { throw core::MappingOutsideOfImageException("Error in conversion from world coordinates to index"); } } DoseTypeGy InterpolationBase::getNearestInsideVoxelValue(const VoxelGridIndex3D& currentVoxelIndex) const { VoxelGridIndex3D voxelChangedXYZ[] = {currentVoxelIndex, currentVoxelIndex, currentVoxelIndex, currentVoxelIndex, currentVoxelIndex, currentVoxelIndex, currentVoxelIndex}; unsigned int runningIndex; //x,y,z for (runningIndex = 0; runningIndex < 3; ++runningIndex) { voxelChangedXYZ[runningIndex][runningIndex] -= 1; } //xy voxelChangedXYZ[runningIndex][0] -= 1; voxelChangedXYZ[runningIndex][1] -= 1; ++runningIndex; //xz voxelChangedXYZ[runningIndex][0] -= 1; voxelChangedXYZ[runningIndex][2] -= 1; ++runningIndex; //yz voxelChangedXYZ[runningIndex][1] -= 1; voxelChangedXYZ[runningIndex][2] -= 1; ++runningIndex; //xyz voxelChangedXYZ[runningIndex][0] -= 1; voxelChangedXYZ[runningIndex][1] -= 1; voxelChangedXYZ[runningIndex][2] -= 1; ++runningIndex; unsigned int replacementVoxelIndex = 0; while (replacementVoxelIndex < runningIndex) { if (_spOriginalData->getGeometricInfo().validIndex(voxelChangedXYZ[replacementVoxelIndex])) { return _spOriginalData->getValueAt(voxelChangedXYZ[replacementVoxelIndex]); } ++replacementVoxelIndex; } return -1; } }//end namespace core }//end namespace rttb diff --git a/code/interpolation/rttbInterpolationBase.h b/code/interpolation/rttbInterpolationBase.h index b007b8f..990f775 100644 --- a/code/interpolation/rttbInterpolationBase.h +++ b/code/interpolation/rttbInterpolationBase.h @@ -1,100 +1,94 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #ifndef __INTERPOLATION_BASE_H #define __INTERPOLATION_BASE_H #include <boost/shared_ptr.hpp> #include <array> #include <rttbCommon.h> #include "rttbAccessorInterface.h" #include "RTTBInterpolationExports.h" #ifdef _MSC_VER #pragma warning(push) #pragma warning(disable: 4251) #endif namespace rttb { namespace interpolation { /*! @class InterpolationBase @brief Base class for interpolation. @ingroup interpolation */ class RTTBInterpolation_EXPORT InterpolationBase { public: rttbClassMacroNoParent(InterpolationBase) /*! @brief Constructor */ InterpolationBase() = default; /*! @brief Virtual destructor of base class */ virtual ~InterpolationBase() = default; /*! @brief Sets the AccessorPointer @pre originalData initialized @exception core::NullPointerException if originalData==nullptr */ void setAccessorPointer(core::AccessorInterface::ConstPointer originalData); /*! @brief Returns the interpolated value for the given world coordinate */ virtual DoseTypeGy getValue(const WorldCoordinate3D& aWorldCoordinate) const = 0; protected: rttb::core::AccessorInterface::ConstPointer _spOriginalData; /*! @brief determines voxels in a certain neighborhood of a physical based coordinate and converts in a standard cube with corner points [0 0 0], [1 0 0], [0 1 0], [1 1 0], [0 0 1], [1 0 1], [0 1 1], [1 1 1]. @param aWorldCoordinate the coordinate where to start @param neighborhood voxel around coordinate (currently only 0 and 8 implemented) @param target coordinates inside the standard cube with values [0 1] in each dimension. @param values dose values at all corner points of the standard cube. Is of type boost:shared_ptr[neighborhood] @pre target and values have to be correctly initialized (e.g. std::array<double, 3> target = {0.0, 0.0, 0.0}; boost::shared_ptr<DoseTypeGy> values(new DoseTypeGy[8]()); where 8 is neighborhood) @exception core::InvalidParameterException if neighborhood =! 0 && !=8 @exception core::MappingOutsideOfImageException if initial mapping of aWorldCoordinate is outside image @exception core::NullPointerException if dose is nullptr */ void getNeighborhoodVoxelValues(const WorldCoordinate3D& aWorldCoordinate, unsigned int neighborhood, std::array<double, 3>& target, boost::shared_ptr<DoseTypeGy[]> values) const; /*! @brief returns the nearest inside voxel value @pre the voxelGridIndex is outside the image and voxelGridIndex>image.size() for all dimensions. Also voxelGridIndex[]>=0 for all dimensions @note used for virtually expanding the image by one voxel as edge handling */ DoseTypeGy getNearestInsideVoxelValue(const VoxelGridIndex3D& currentVoxelIndex) const; }; } } #ifdef _MSC_VER #pragma warning(pop) #endif #endif diff --git a/code/interpolation/rttbLinearInterpolation.cpp b/code/interpolation/rttbLinearInterpolation.cpp index c2bb553..f399052 100644 --- a/code/interpolation/rttbLinearInterpolation.cpp +++ b/code/interpolation/rttbLinearInterpolation.cpp @@ -1,59 +1,53 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "rttbLinearInterpolation.h" #include <boost/make_shared.hpp> namespace rttb { namespace interpolation { DoseTypeGy LinearInterpolation::trilinear(std::array<double, 3> target, boost::shared_ptr<DoseTypeGy[]> values) const { //4 linear interpolation in x direction DoseTypeGy c_00 = values[0] * (1.0 - target[0]) + values[1] * target[0]; DoseTypeGy c_10 = values[2] * (1.0 - target[0]) + values[3] * target[0]; DoseTypeGy c_01 = values[4] * (1.0 - target[0]) + values[5] * target[0]; DoseTypeGy c_11 = values[6] * (1.0 - target[0]) + values[7] * target[0]; //combine result in y direction DoseTypeGy c_0 = c_00 * (1.0 - target[1]) + c_10 * target[1]; DoseTypeGy c_1 = c_01 * (1.0 - target[1]) + c_11 * target[1]; //finally incorporate z direction return (c_0 * (1.0 - target[2]) + c_1 * target[2]); } DoseTypeGy LinearInterpolation::getValue(const WorldCoordinate3D& aWorldCoordinate) const { //proper initialization of target and values std::array<double, 3> target = {0.0, 0.0, 0.0}; auto values = boost::make_shared<DoseTypeGy[]>(8); getNeighborhoodVoxelValues(aWorldCoordinate, 8, target, values); return trilinear(target, values); } } } diff --git a/code/interpolation/rttbLinearInterpolation.h b/code/interpolation/rttbLinearInterpolation.h index 5fdd399..f9c7865 100644 --- a/code/interpolation/rttbLinearInterpolation.h +++ b/code/interpolation/rttbLinearInterpolation.h @@ -1,62 +1,56 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #ifndef __LINEAR_INTERPOLATION_H #define __LINEAR_INTERPOLATION_H #include <array> #include "rttbInterpolationBase.h" #include "RTTBInterpolationExports.h" namespace rttb { namespace interpolation { /*! @class LinearInterpolation @brief Linear interpolation. @ingroup interpolation */ class RTTBInterpolation_EXPORT LinearInterpolation : public InterpolationBase { public: /*! @brief Constructor */ LinearInterpolation() = default; /*! @brief Returns the interpolated value */ DoseTypeGy getValue(const WorldCoordinate3D& aWorldCoordinate) const override; private: /*! @brief Trilinar interpolation @sa InterpolationBase for details about target and values @note Source: http://en.wikipedia.org/wiki/Trilinear_interpolation */ DoseTypeGy trilinear(std::array<double, 3> target, boost::shared_ptr<DoseTypeGy[]> values) const; }; } } #endif diff --git a/code/interpolation/rttbMappableDoseAccessorInterface.h b/code/interpolation/rttbMappableDoseAccessorInterface.h index b691c8e..f62ba1b 100644 --- a/code/interpolation/rttbMappableDoseAccessorInterface.h +++ b/code/interpolation/rttbMappableDoseAccessorInterface.h @@ -1,100 +1,95 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __MAPPABLE_DOSE_ACCESSOR_BASE_H #define __MAPPABLE_DOSE_ACCESSOR_BASE_H #include <rttbCommon.h> #include "rttbDoseAccessorInterface.h" #include "rttbGeometricInfo.h" #include "rttbBaseType.h" #include "rttbTransformationInterface.h" #include "rttbNullPointerException.h" namespace rttb { namespace interpolation { /*! @class MappableDoseAccessorInterface @brief Interface for dealing with dose information that has to be transformed into another geometry than the original dose image @details implementation of strategy is done by derived class (e.g. SimpleMappableDoseAccessor or RosuMappableDoseAccessor. Transformation is defined in TransformationInterface @ingroup interpolation */ class MappableDoseAccessorInterface: public core::DoseAccessorInterface { public: rttbClassMacro(MappableDoseAccessorInterface,core::DoseAccessorInterface) protected: core::DoseAccessorInterface::ConstPointer _spOriginalDoseDataMovingImage; TransformationInterface::Pointer _spTransformation; core::GeometricInfo _geoInfoTargetImage; bool _acceptPadding; DoseTypeGy _defaultOutsideValue; public: /*! @brief Constructor. @param geoInfoTargetImage target image geometry @param doseMovingImage dose of moving image @param aTransformation the transformation @param acceptPadding is mapping outside the image allowed @param defaultOutsideValue the default outside voxel value if accepptPadding=true @pre all input parameters have to be valid @exception core::NullPointerException if one input parameter is nullptr */ MappableDoseAccessorInterface(const core::GeometricInfo& geoInfoTargetImage, core::DoseAccessorInterface::ConstPointer doseMovingImage, const TransformationInterface::Pointer aTransformation, bool acceptPadding = true, DoseTypeGy defaultOutsideValue = 0.0): _spOriginalDoseDataMovingImage(doseMovingImage), _spTransformation(aTransformation), _geoInfoTargetImage(geoInfoTargetImage), _acceptPadding(acceptPadding), _defaultOutsideValue(defaultOutsideValue) { //handle null pointers if (doseMovingImage == nullptr || aTransformation == nullptr) { throw core::NullPointerException("Pointers to input accessors/transformation cannot be nullptr."); } } /*! @brief Virtual destructor of base class */ ~MappableDoseAccessorInterface() override = default; inline const core::GeometricInfo& getGeometricInfo() const override { return _geoInfoTargetImage; }; inline GridSizeType getGridSize() const override { return _geoInfoTargetImage.getNumberOfVoxels(); }; const IDType getUID() const override { return _spOriginalDoseDataMovingImage->getUID(); }; }; } } #endif diff --git a/code/interpolation/rttbNearestNeighborInterpolation.cpp b/code/interpolation/rttbNearestNeighborInterpolation.cpp index bc34750..6493de5 100644 --- a/code/interpolation/rttbNearestNeighborInterpolation.cpp +++ b/code/interpolation/rttbNearestNeighborInterpolation.cpp @@ -1,41 +1,35 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "rttbNearestNeighborInterpolation.h" #include <array> #include <boost/make_shared.hpp> namespace rttb { namespace interpolation { DoseTypeGy NearestNeighborInterpolation::getValue(const WorldCoordinate3D& aWorldCoordinate) const { //proper initialization of target and values (although target is irrelevant in nearest neighbor case) std::array<double, 3> target = {{0.0, 0.0, 0.0}}; auto values = boost::make_shared<DoseTypeGy[]>(8); getNeighborhoodVoxelValues(aWorldCoordinate, 0, target, values); return values[0]; } } } diff --git a/code/interpolation/rttbNearestNeighborInterpolation.h b/code/interpolation/rttbNearestNeighborInterpolation.h index eb4ee74..168b8f7 100644 --- a/code/interpolation/rttbNearestNeighborInterpolation.h +++ b/code/interpolation/rttbNearestNeighborInterpolation.h @@ -1,53 +1,47 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #ifndef __NEAREST_NEIGHBOR_INTERPOLATION_H #define __NEAREST_NEIGHBOR_INTERPOLATION_H #include "rttbInterpolationBase.h" #include "RTTBInterpolationExports.h" namespace rttb { namespace interpolation { /*! @class NearestNeighborInterpolation @brief Nearest Neighbor interpolation @ingroup interpolation */ class RTTBInterpolation_EXPORT NearestNeighborInterpolation : public InterpolationBase { public: /*! @brief Constructor */ NearestNeighborInterpolation() = default; /*! @brief Returns the interpolated value (the nearest voxel value given by _spOriginalData->getGeometricInfo().worldCoordinateToIndex()) */ DoseTypeGy getValue(const WorldCoordinate3D& aWorldCoordinate) const override; }; } } #endif diff --git a/code/interpolation/rttbRosuMappableDoseAccessor.h b/code/interpolation/rttbRosuMappableDoseAccessor.h index aaecd0d..a7ea314 100644 --- a/code/interpolation/rttbRosuMappableDoseAccessor.h +++ b/code/interpolation/rttbRosuMappableDoseAccessor.h @@ -1,80 +1,75 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __ROSU_MAPPABLE_DOSE_ACCESSOR_H #define __ROSU_MAPPABLE_DOSE_ACCESSOR_H #include <boost/shared_ptr.hpp> #include "rttbBaseType.h" #include "rttbInterpolationBase.h" #include "rttbMappableDoseAccessorInterface.h" namespace rttb { namespace interpolation { class TransformationInterface; /*! @class RosuMappableDoseAccessor @brief Class for dose mapping based on interpolation described in the Rosu2005 paper @details implementation of the following paper: Rosu, M., Chetty, I. J., Balter, J. M., Kessler, M. L., McShan, D. L., & Ten Haken, R. K. (2005). Dose reconstruction in deforming lung anatomy: Dose grid size effects and clinical implications. Medical Physics, 32(8), 2487. @ingroup interpolation */ class RosuMappableDoseAccessor: public MappableDoseAccessorInterface { private: InterpolationBase::Pointer _spInterpolation; public: /*! @brief Constructor. Just hands values over to base class constructor. @note no interpolation as parameter since linear interpolation is fixed. @sa MappableDoseAccessorBase */ RosuMappableDoseAccessor(const core::GeometricInfo& geoInfoTargetImage, core::DoseAccessorInterface::ConstPointer doseMovingImage, const TransformationInterface::Pointer aTransformation, bool acceptPadding = true, DoseTypeGy defaultOutsideValue = 0.0); /*! @brief Virtual destructor. */ ~RosuMappableDoseAccessor() override = default; GenericValueType getValueAt(const VoxelGridID aID) const override; /*! @brief Returns the dose for a given voxel grid index. The computation of the octant around the voxel is done and the interpolation is performed. @details Boundary treatment: if more than 6 subvoxels are outside: return _defaultOutsideValue. Otherwise: ignore the outside values. @return the dose or if (isOutside==true && _acceptPadding==true) then _defaultValue @exception core::MappingOutsideOfImageException if the point is mapped outside and if _acceptPadding==false, possibly returning _defaultValue) */ GenericValueType getValueAt(const VoxelGridIndex3D& aIndex) const override; private: /*! @brief returns the octant coordinates around a coordinate. @details i.e. coordinate is the center of a virtual voxel. Then, each side is divided into equal parts. The centers of the new subvoxels are then returned. @return a vector of the octant coordinates. */ std::vector<WorldCoordinate3D> getOctants(const WorldCoordinate3D& aCoordinate) const; }; } } #endif diff --git a/code/interpolation/rttbSimpleMappableDoseAccessor.h b/code/interpolation/rttbSimpleMappableDoseAccessor.h index 35f3b89..d152af2 100644 --- a/code/interpolation/rttbSimpleMappableDoseAccessor.h +++ b/code/interpolation/rttbSimpleMappableDoseAccessor.h @@ -1,76 +1,71 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __SIMPLE_MAPPABLE_DOSE_ACCESSOR_H #define __SIMPLE_MAPPABLE_DOSE_ACCESSOR_H #include <boost/shared_ptr.hpp> #include <boost/make_shared.hpp> #include "rttbInterpolationBase.h" #include "rttbLinearInterpolation.h" #include "rttbTransformationInterface.h" #include "rttbMappableDoseAccessorInterface.h" #include "RTTBInterpolationExports.h" namespace rttb { namespace interpolation { /*! @class SimpleMappableDoseAccessor @brief Class for dose mapping based on simple trilinear interpolation @ingroup interpolation */ class RTTBInterpolation_EXPORT SimpleMappableDoseAccessor : public MappableDoseAccessorInterface { private: InterpolationBase::Pointer _spInterpolation; public: /*! @brief Constructor. Just hands values over to base class constructor. @param aInterpolation the used interpolation. @sa MappableDoseAccessorBase */ SimpleMappableDoseAccessor(const core::GeometricInfo& geoInfoTargetImage, core::DoseAccessorInterface::ConstPointer doseMovingImage, const TransformationInterface::Pointer aTransformation, const InterpolationBase::Pointer aInterpolation = ::boost::make_shared<LinearInterpolation>(), bool acceptPadding = true, DoseTypeGy defaultOutsideValue = 0.0); /*! @brief Virtual destructor of class */ ~SimpleMappableDoseAccessor() override = default; /*! @brief Returns the dose for a given voxel grid id. Plain trilinear interpolation is performed. @sa getDoseAt(const VoxelGridIndex3D& aIndex) */ GenericValueType getValueAt(const VoxelGridID aID) const override; /*! @brief Returns the dose for a given voxel grid index. Plain trilinear interpolation is performed. @return the dose or if (isOutside==true && _acceptPadding==true) then _defaultValue @exception core::MappingOutsideOfImageException if the point is mapped outside and if _acceptPadding==false, possibly returning _defaultValue) */ GenericValueType getValueAt(const VoxelGridIndex3D& aIndex) const override; }; } } #endif diff --git a/code/interpolation/rttbTransformationInterface.h b/code/interpolation/rttbTransformationInterface.h index 407e52e..90e4d17 100644 --- a/code/interpolation/rttbTransformationInterface.h +++ b/code/interpolation/rttbTransformationInterface.h @@ -1,81 +1,75 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #ifndef __TRANSFORMATION_INTERFACE_H #define __TRANSFORMATION_INTERFACE_H #include <rttbCommon.h> #include "rttbBaseType.h" #include "RTTBInterpolationExports.h" #ifdef _MSC_VER #pragma warning(push) #pragma warning(disable: 4251) #endif namespace rttb { namespace interpolation { /*! @class TransformationInterface @brief Base class for transformation (in World coordinates). @ingroup interpolation */ class RTTBInterpolation_EXPORT TransformationInterface { public: rttbClassMacroNoParent(TransformationInterface) protected: /*! @brief Constructor */ TransformationInterface() = default; /*! @brief Virtual destructor of interface class */ virtual ~TransformationInterface() = default; public: /*! @brief performs a transformation targetImage --> movingImage */ virtual bool transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const = 0; /*! @brief performs a transformation movingImage --> targetImage */ virtual bool transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const = 0; private: TransformationInterface(const TransformationInterface&) = delete;//not implemented on purpose -> non-copyable TransformationInterface& operator=(const TransformationInterface&) = delete;//not implemented on purpose -> non-copyable }; } } #ifdef _MSC_VER #pragma warning(pop) #endif #endif diff --git a/testing/interpolation/DummyTransformation.cpp b/testing/interpolation/DummyTransformation.cpp index 1951b0e..4c6b4b7 100644 --- a/testing/interpolation/DummyTransformation.cpp +++ b/testing/interpolation/DummyTransformation.cpp @@ -1,42 +1,36 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "DummyTransformation.h" namespace rttb { namespace testing { bool DummyTransformation::transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const { worldCoordinateMoving = worldCoordinateTarget; return true; } bool DummyTransformation::transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const { worldCoordinateTarget = worldCoordinateMoving; return true; } } } diff --git a/testing/interpolation/DummyTransformation.h b/testing/interpolation/DummyTransformation.h index 546a140..34f89ab 100644 --- a/testing/interpolation/DummyTransformation.h +++ b/testing/interpolation/DummyTransformation.h @@ -1,54 +1,49 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __DUMMY_TRANSFORMATION_H #define __DUMMY_TRANSFORMATION_H #include "rttbTransformationInterface.h" namespace rttb { namespace testing { /*! @class DummyTransformation @brief implements a dummy transformation (return the points as they were given) */ class DummyTransformation : public interpolation::TransformationInterface { public: /*! @brief Constructor */ DummyTransformation() {}; /*! @brief target equals to moving */ bool transformInverse(const WorldCoordinate3D& worldCoordinateTarget, WorldCoordinate3D& worldCoordinateMoving) const; /*! @brief moving equals to target */ bool transform(const WorldCoordinate3D& worldCoordinateMoving, WorldCoordinate3D& worldCoordinateTarget) const; }; } } #endif \ No newline at end of file diff --git a/testing/interpolation/InterpolationITKTransformation/SimpleMappableDoseAccessorWithITKTest.cpp b/testing/interpolation/InterpolationITKTransformation/SimpleMappableDoseAccessorWithITKTest.cpp index 7cf2995..b4c184f 100644 --- a/testing/interpolation/InterpolationITKTransformation/SimpleMappableDoseAccessorWithITKTest.cpp +++ b/testing/interpolation/InterpolationITKTransformation/SimpleMappableDoseAccessorWithITKTest.cpp @@ -1,178 +1,172 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "litCheckMacros.h" #include "rttbBaseType.h" #include "rttbGenericDoseIterator.h" #include "rttbDicomFileDoseAccessorGenerator.h" #include "rttbSimpleMappableDoseAccessor.h" #include "rttbNearestNeighborInterpolation.h" #include "rttbLinearInterpolation.h" #include "rttbTransformationInterface.h" #include "rttbITKTransformation.h" #include "rttbNullPointerException.h" #include "itkTranslationTransform.h" namespace rttb { namespace testing { typedef core::GenericDoseIterator::DoseAccessorPointer DoseAccessorPointer; typedef rttb::interpolation::SimpleMappableDoseAccessor SimpleMappableDoseAccessor; typedef rttb::interpolation::NearestNeighborInterpolation NearestNeighborInterpolation; typedef rttb::interpolation::LinearInterpolation LinearInterpolation; typedef rttb::interpolation::TransformationInterface TransformationInterface; typedef rttb::interpolation::ITKTransformation ITKTransformation; typedef itk::TranslationTransform<DoseTypeGy, 3> TranslationTransformType; /*! @brief SimpleMappableDoseAccessorWithITKTest - test the API of SimpleMappableDoseAccessor with ITK transformation 1) Test constructor 2) test getDoseAt() a) with Identity transform b) with translation transform */ int SimpleMappableDoseAccessorWithITKTest(int argc, char* argv[]) { PREPARE_DEFAULT_TEST_REPORTING; std::string RTDOSE_FILENAME_CONSTANT_TWO; std::string RTDOSE_FILENAME_INCREASE_X; if (argc > 2) { RTDOSE_FILENAME_CONSTANT_TWO = argv[1]; RTDOSE_FILENAME_INCREASE_X = argv[2]; } else { std::cout << "at least two parameters for SimpleMappableDoseAccessorWithITKTest are expected" << std::endl; return -1; } const double doseGridScaling = 2.822386e-005; rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator1( RTDOSE_FILENAME_CONSTANT_TWO.c_str()); DoseAccessorPointer doseAccessor1(doseAccessorGenerator1.generateDoseAccessor()); rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator2( RTDOSE_FILENAME_INCREASE_X.c_str()); DoseAccessorPointer doseAccessor2(doseAccessorGenerator2.generateDoseAccessor()); core::GeometricInfo doseAccessor1GeometricInfo = doseAccessor1->getGeometricInfo(); auto interpolationNN = boost::make_shared<rttb::interpolation::NearestNeighborInterpolation>(); auto interpolationLinear = boost::make_shared<rttb::interpolation::LinearInterpolation>(); TranslationTransformType::Pointer transformITKIdentityTemporary = TranslationTransformType::New(); TranslationTransformType::OutputVectorType translationIdentity; translationIdentity[0] = 0.0; translationIdentity[1] = 0.0; translationIdentity[2] = 0.0; transformITKIdentityTemporary->Translate(translationIdentity); auto transformITKIdentity = boost::make_shared<ITKTransformation>(transformITKIdentityTemporary); TranslationTransformType::Pointer transformITKTranslationTemporary = TranslationTransformType::New(); TranslationTransformType::OutputVectorType translation; translation[0] = 5.0; translation[1] = 5.0; translation[2] = 5.0; transformITKTranslationTemporary->Translate(translation); auto transformITKTranslation = boost::make_shared<ITKTransformation>(transformITKTranslationTemporary); auto aSimpleMappableDoseAccessorITKIdentity = boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformITKIdentity, interpolationLinear); auto aSimpleMappableDoseAccessorITKTranslation = boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformITKTranslation, interpolationLinear); //1) Test constructor CHECK_NO_THROW(SimpleMappableDoseAccessor( doseAccessor1GeometricInfo, doseAccessor2, transformITKIdentity, interpolationLinear)); CHECK_NO_THROW(SimpleMappableDoseAccessor( doseAccessor1GeometricInfo, doseAccessor2, transformITKTranslation, interpolationLinear)); CHECK_NO_THROW(ITKTransformation(transformITKTranslationTemporary.GetPointer())); CHECK_THROW_EXPLICIT(ITKTransformation(nullptr), core::NullPointerException); //2) test getDoseAt() // a) with Identity transform //test valid voxels std::vector<VoxelGridIndex3D> voxelsAsIndexToTest; std::vector<DoseTypeGy> expectedValues; voxelsAsIndexToTest.push_back(VoxelGridIndex3D(5, 9, 8)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(22, 15, 10)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(30, 20, 7)); expectedValues.push_back(5.0 * doseGridScaling); expectedValues.push_back(22.0 * doseGridScaling); expectedValues.push_back(30.0 * doseGridScaling); //convert VoxelGridIndex3D to VoxelGridID for (size_t i = 0; i < voxelsAsIndexToTest.size(); i++) { VoxelGridID currentId; doseAccessor1GeometricInfo.convert(voxelsAsIndexToTest.at(i), currentId); //test if the expected interpolation values are computed CHECK_EQUAL(aSimpleMappableDoseAccessorITKIdentity->getValueAt(voxelsAsIndexToTest.at(i)), expectedValues.at(i)); //test if getDoseAt(VoxelGridIndex3D) and getDoseAt(VoxelGridD) lead to the same results CHECK_EQUAL(aSimpleMappableDoseAccessorITKIdentity->getValueAt(voxelsAsIndexToTest.at(i)), aSimpleMappableDoseAccessorITKIdentity->getValueAt(currentId)); } //no tests with invalid IDs, this has been done already tested in SimpleMappableDoseAccessorTest //b) with translation transform //translation of one voxel in each direction expectedValues.clear(); expectedValues.push_back(6.0 * doseGridScaling); expectedValues.push_back(23.0 * doseGridScaling); expectedValues.push_back(31.0 * doseGridScaling); for (size_t i = 0; i < voxelsAsIndexToTest.size(); i++) { VoxelGridID currentId; doseAccessor1GeometricInfo.convert(voxelsAsIndexToTest.at(i), currentId); //test if the expected interpolation values are computed CHECK_EQUAL(aSimpleMappableDoseAccessorITKTranslation->getValueAt(voxelsAsIndexToTest.at(i)), expectedValues.at(i)); //test if getDoseAt(VoxelGridIndex3D) and getDoseAt(VoxelGridD) lead to the same results CHECK_EQUAL(aSimpleMappableDoseAccessorITKTranslation->getValueAt(voxelsAsIndexToTest.at(i)), aSimpleMappableDoseAccessorITKTranslation->getValueAt(currentId)); } RETURN_AND_REPORT_TEST_SUCCESS; } }//end namespace testing }//end namespace rttb diff --git a/testing/interpolation/InterpolationMatchPointTransformation/SimpleMappableDoseAccessorWithMatchPointTest.cpp b/testing/interpolation/InterpolationMatchPointTransformation/SimpleMappableDoseAccessorWithMatchPointTest.cpp index fbd711b..677ce61 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/SimpleMappableDoseAccessorWithMatchPointTest.cpp +++ b/testing/interpolation/InterpolationMatchPointTransformation/SimpleMappableDoseAccessorWithMatchPointTest.cpp @@ -1,239 +1,233 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "litCheckMacros.h" #include "rttbBaseType.h" #include "rttbGenericDoseIterator.h" #include "rttbDicomFileDoseAccessorGenerator.h" #include "rttbSimpleMappableDoseAccessor.h" #include "rttbNearestNeighborInterpolation.h" #include "rttbLinearInterpolation.h" #include "rttbGeometricInfo.h" #include "rttbTransformationInterface.h" #include "rttbMatchPointTransformation.h" #include "rttbNullPointerException.h" #include "registrationTest.h" #include "simpleRegistrationWorkflow.h" namespace rttb { namespace testing { static const unsigned int TargetDimension3D = 3; static const unsigned int MovingDimension3D = 3; typedef core::GenericDoseIterator::DoseAccessorPointer DoseAccessorPointer; typedef rttb::interpolation::SimpleMappableDoseAccessor SimpleMappableDoseAccessor; typedef map::core::RegistrationTest<MovingDimension3D, TargetDimension3D> Registration3D3DTypeTest; typedef Registration3D3DTypeTest::Pointer Registration3D3DTypeTestPointer; typedef map::core::Registration<MovingDimension3D, TargetDimension3D> Registration3D3DType; typedef Registration3D3DType::Pointer Registration3D3DPointer; typedef rttb::interpolation::NearestNeighborInterpolation NearestNeighborInterpolation; typedef rttb::interpolation::LinearInterpolation LinearInterpolation; typedef rttb::interpolation::TransformationInterface TransformationInterface; typedef rttb::interpolation::MatchPointTransformation MatchPointTransformation; /*! @brief SimpleMappableDoseAccessorWithMatchPointTest - test the API of SimpleMappableDoseAccessor with MatchPoint transform 1) Test constructor 2) test getDoseAt() a) with Identity transform b) with translation transform [3) test with rigid registration optional (if filenames are given as argument)] */ int SimpleMappableDoseAccessorWithMatchPointTest(int argc, char* argv[]) { PREPARE_DEFAULT_TEST_REPORTING; std::string RTDOSE_FILENAME_CONSTANT_TWO; std::string RTDOSE_FILENAME_INCREASE_X; std::string RTDOSE_FILENAME_REALISTIC = ""; std::string CT_PLANNING = ""; std::string CT_FRACTION = ""; if (argc > 2) { RTDOSE_FILENAME_CONSTANT_TWO = argv[1]; RTDOSE_FILENAME_INCREASE_X = argv[2]; } else { std::cout << "at least two parameters for SimpleMappableDoseAccessorWithMatchPointTest are expected" << std::endl; return -1; } if (argc > 5) { RTDOSE_FILENAME_REALISTIC = argv[3]; CT_PLANNING = argv[4]; CT_FRACTION = argv[5]; } rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator1( RTDOSE_FILENAME_CONSTANT_TWO.c_str()); DoseAccessorPointer doseAccessor1(doseAccessorGenerator1.generateDoseAccessor()); DoseAccessorPointer doseAccessorNull; rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator2( RTDOSE_FILENAME_INCREASE_X.c_str()); DoseAccessorPointer doseAccessor2(doseAccessorGenerator2.generateDoseAccessor()); core::GeometricInfo doseAccessor1GeometricInfo = doseAccessor1->getGeometricInfo(); Registration3D3DTypeTestPointer registration = Registration3D3DTypeTest::New(); double translation[] = {0.0, 0.0, 0.0}; registration->_translation = translation; registration->_limitedTarget = false; auto interpolationNN = ::boost::make_shared<NearestNeighborInterpolation>(); auto interpolationLinear = ::boost::make_shared<LinearInterpolation>(); NearestNeighborInterpolation::Pointer interpolationNull; auto transformMP = ::boost::make_shared<MatchPointTransformation>(registration.GetPointer()); auto aSimpleMappableDoseAccessorMPIdentityLinear = ::boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationLinear); auto aSimpleMappableDoseAccessorMPIdentityNN = ::boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationNN); //1) Test constructor CHECK_NO_THROW(SimpleMappableDoseAccessor( doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationLinear)); CHECK_NO_THROW(SimpleMappableDoseAccessor( doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationNN)); CHECK_NO_THROW(MatchPointTransformation(registration.GetPointer())); CHECK_THROW_EXPLICIT(MatchPointTransformation(nullptr), core::NullPointerException); //2) test getDoseAt() // a) with Identity transform double vectorDoseAccessorStartEnd = 0.0; while (vectorDoseAccessorStartEnd <= 1.0) { VoxelGridID runningID = (VoxelGridID)(vectorDoseAccessorStartEnd * (double)aSimpleMappableDoseAccessorMPIdentityLinear->getGridSize()); CHECK_EQUAL(aSimpleMappableDoseAccessorMPIdentityLinear->getValueAt(runningID), doseAccessor2->getValueAt(runningID)); CHECK_EQUAL(aSimpleMappableDoseAccessorMPIdentityNN->getValueAt(runningID), doseAccessor2->getValueAt(runningID)); vectorDoseAccessorStartEnd += 0.1; } // b) with translation transform //Second: Translation (5mm/5mm/5mm) --> in voxel: (1/1/1) as pixelspacing = 5 mm translation[0] = translation[1] = translation[2] = 5.0; registration->_translation = translation; auto aSimpleMappableDoseAccessorMPTranslationLinear = boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationLinear); auto aSimpleMappableDoseAccessorMPTranslationNN = boost::make_shared<SimpleMappableDoseAccessor>(doseAccessor1GeometricInfo, doseAccessor2, transformMP, interpolationNN); rttb::VoxelGridIndex3D aIndexBeforeTransformation(0, 0, 0); rttb::VoxelGridIndex3D aIndexAfterTransformation(1, 1, 1); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationLinear->getValueAt(aIndexBeforeTransformation), doseAccessor2->getValueAt(aIndexAfterTransformation)); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationNN->getValueAt(aIndexBeforeTransformation), doseAccessor2->getValueAt(aIndexAfterTransformation)); rttb::VoxelGridIndex3D aIndexBeforeTransformation2(20, 10, 10); rttb::VoxelGridIndex3D aIndexAfterTransformation2(21, 11, 11); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationLinear->getValueAt(aIndexBeforeTransformation2), doseAccessor2->getValueAt(aIndexAfterTransformation2)); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationNN->getValueAt(aIndexBeforeTransformation2), doseAccessor2->getValueAt(aIndexAfterTransformation2)); rttb::VoxelGridIndex3D aIndexBeforeTransformation3( aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumColumns() - 2, aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumRows() - 2, aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumSlices() - 2); rttb::VoxelGridIndex3D aIndexAfterTransformation3( aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumColumns() - 1, aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumRows() - 1, aSimpleMappableDoseAccessorMPTranslationLinear->getGeometricInfo().getNumSlices() - 1); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationLinear->getValueAt(aIndexBeforeTransformation3), doseAccessor2->getValueAt(aIndexAfterTransformation3)); CHECK_EQUAL(aSimpleMappableDoseAccessorMPTranslationNN->getValueAt(aIndexBeforeTransformation3), doseAccessor2->getValueAt(aIndexAfterTransformation3)); if (RTDOSE_FILENAME_REALISTIC != "" && CT_FRACTION != "" && CT_PLANNING != "") { //3) test with rigid registration //realistic background: registration from BP-CT to fraction CT, apply on planning dose that is based on BP-CT (proof of concept) //Target image: fraction CT, Moving image: planning CT simpleRegistrationWorkflow prepareRegistrationRealisticScenario(CT_FRACTION, CT_PLANNING, true); Registration3D3DPointer registrationRealisticScenario = prepareRegistrationRealisticScenario.getRegistration(); auto transformRealistic = boost::make_shared<MatchPointTransformation>(registrationRealisticScenario); io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator3(RTDOSE_FILENAME_REALISTIC.c_str()); DoseAccessorPointer doseAccessor3(doseAccessorGenerator3.generateDoseAccessor()); core::GeometricInfo geoInfoRealistic; geoInfoRealistic.setNumColumns( prepareRegistrationRealisticScenario.getTargetImage()->GetLargestPossibleRegion().GetSize()[0]); geoInfoRealistic.setNumRows( prepareRegistrationRealisticScenario.getTargetImage()->GetLargestPossibleRegion().GetSize()[1]); geoInfoRealistic.setNumSlices( prepareRegistrationRealisticScenario.getTargetImage()->GetLargestPossibleRegion().GetSize()[2]); //Dose is related to BP-CT, map dose to fraction CT geometry auto aSimpleMappableDoseAccessorRealisticScenarioLinear = boost::make_shared<SimpleMappableDoseAccessor>(geoInfoRealistic, doseAccessor3, transformRealistic, interpolationLinear); //combination of 0, size/2 and size to check as coordinates std::vector<unsigned int> coordinatesToCheckX, coordinatesToCheckY, coordinatesToCheckZ; coordinatesToCheckX.push_back(0); coordinatesToCheckX.push_back(geoInfoRealistic.getNumColumns() / 2); coordinatesToCheckX.push_back(geoInfoRealistic.getNumColumns() - 1); coordinatesToCheckY.push_back(0); coordinatesToCheckY.push_back(geoInfoRealistic.getNumRows() / 2); coordinatesToCheckY.push_back(geoInfoRealistic.getNumRows() - 1); coordinatesToCheckZ.push_back(0); coordinatesToCheckZ.push_back(geoInfoRealistic.getNumSlices() / 2); coordinatesToCheckZ.push_back(geoInfoRealistic.getNumSlices() - 1); //Pixels are inside the fraction CT image and mapping should work (even if they map outside of doseAccessor3) for (size_t i = 0; i < coordinatesToCheckX.size(); ++i) { for (size_t j = 0; j < coordinatesToCheckY.size(); ++j) { for (size_t k = 0; k < coordinatesToCheckZ.size(); ++k) { CHECK_NO_THROW(aSimpleMappableDoseAccessorRealisticScenarioLinear->getValueAt(VoxelGridIndex3D( coordinatesToCheckX.at(i), coordinatesToCheckY.at(j), coordinatesToCheckZ.at(k)))); } } } } RETURN_AND_REPORT_TEST_SUCCESS; } }//end namespace testing }//end namespace rttb diff --git a/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.cpp b/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.cpp index ba9af1b..1dfd4a5 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.cpp +++ b/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.cpp @@ -1,86 +1,80 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #if defined(_MSC_VER) #pragma warning ( disable : 4786 ) #endif #include "registrationHelper.h" #include "litTestImageIO.h" #include "litImageTester.h" #include <fstream> int setImageFileNames(std::string targetImage, std::string movingImage, bool isDirectory, AppGlobals& globals) { globals.targetImageFileName = targetImage; globals.movingImageFileName = movingImage; globals.isDirectory = isDirectory; return EXIT_SUCCESS; } int loadData(AppGlobals& globals) { if (!globals.isDirectory) { globals.spTargetImage = lit::TestImageIO<short, map::core::discrete::Elements<3>::InternalImageType>::readImage( globals.targetImageFileName); } else { globals.spTargetImage = map::io::readImage<ImageType::PixelType, ImageType::PixelType, 3> (globals.targetImageFileName, map::io::ImageSeriesReadStyle::Dicom); } if (globals.spTargetImage.IsNull()) { std::cerr << "Error. Cannot load target image: " << globals.targetImageFileName << std::endl; return EXIT_FAILURE; } if (!globals.isDirectory) { globals.spMovingImage = lit::TestImageIO<short, map::core::discrete::Elements<3>::InternalImageType>::readImage( globals.movingImageFileName); } else { globals.spMovingImage = map::io::readImage<ImageType::PixelType, ImageType::PixelType, 3> (globals.movingImageFileName, map::io::ImageSeriesReadStyle::Dicom); } if (globals.spMovingImage.IsNull()) { std::cerr << "Error. Cannot load moving image: " << globals.movingImageFileName << std::endl; return EXIT_FAILURE; } return EXIT_SUCCESS; } AppGlobals::AppGlobals() { }; \ No newline at end of file diff --git a/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.h b/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.h index ee79206..4124dde 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.h +++ b/testing/interpolation/InterpolationMatchPointTransformation/registrationHelper.h @@ -1,56 +1,50 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #if defined(_MSC_VER) #pragma warning ( disable : 4786 ) #endif #ifndef __REGISTRATION_HELPER_H #define __REGISTRATION_HELPER_H #include "mapContinuousElements.h" #include "mapDiscreteElements.h" #include "mapImageReader.h" typedef map::core::discrete::Elements<3>::InternalImageType ImageType; typedef map::core::continuous::Elements<3>::InternalPointSetType LandmarksType; struct AppGlobals { std::string targetImageFileName; std::string movingImageFileName; bool isDirectory; ImageType::Pointer spTargetImage; ImageType::Pointer spMovingImage; ImageType::Pointer spResultImage; AppGlobals(); }; int setImageFileNames(std::string targetImage, std::string movingImage, bool isDirectory, AppGlobals& globals); int loadData(AppGlobals& globals); #endif \ No newline at end of file diff --git a/testing/interpolation/InterpolationMatchPointTransformation/registrationTest.h b/testing/interpolation/InterpolationMatchPointTransformation/registrationTest.h index ee23b74..7046991 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/registrationTest.h +++ b/testing/interpolation/InterpolationMatchPointTransformation/registrationTest.h @@ -1,84 +1,79 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __REGISTRATION_TEST_H #define __REGISTRATION_TEST_H #include "mapRegistration.h" namespace map { namespace core { /*! @class TestRegistration @brief Simple implementation of MatchPoint Registration class with direct access to mapping. */ template<unsigned int VMovingDimensions, unsigned int VTargetDimensions> class RegistrationTest: public Registration<VMovingDimensions, VTargetDimensions> { public: typedef RegistrationTest<VMovingDimensions, VTargetDimensions> Self; typedef RegistrationBase Superclass; typedef itk::SmartPointer<Self> Pointer; typedef itk::SmartPointer<const Self> ConstPointer; typedef typename Registration<VMovingDimensions, VTargetDimensions>::TargetPointType TargetPointType; typedef typename Registration<VMovingDimensions, VTargetDimensions>::MovingPointType MovingPointType; itkTypeMacro(RegistrationTest, Registration); itkNewMacro(Self); bool _limitedTarget; double* _translation; RegistrationTest() {}; ~RegistrationTest() { }; virtual bool mapPointInverse(const TargetPointType& inPoint, MovingPointType& outPoint) const { for (unsigned int i = 0; i < VTargetDimensions; i++) { outPoint[i] = inPoint[i] + _translation[i]; } return true; }; virtual bool hasLimitedTargetRepresentation() const { return _limitedTarget; } private: RegistrationTest(const Self& source); //purposely not implemented void operator=(const Self&); //purposely not implemented }; } } #endif diff --git a/testing/interpolation/InterpolationMatchPointTransformation/rttbInterpolationMatchPointTests.cpp b/testing/interpolation/InterpolationMatchPointTransformation/rttbInterpolationMatchPointTests.cpp index 473ee84..9a298bf 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/rttbInterpolationMatchPointTests.cpp +++ b/testing/interpolation/InterpolationMatchPointTransformation/rttbInterpolationMatchPointTests.cpp @@ -1,63 +1,56 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ // this file defines the rttbAlgorithmsTests for the test driver // and all it expects is that you have a function called RegisterTests #if defined(_MSC_VER) #pragma warning ( disable : 4786 ) #endif - #include "litMultiTestsMain.h" namespace rttb { namespace testing { void registerTests() { LIT_REGISTER_TEST(SimpleMappableDoseAccessorWithMatchPointTest); } } } int main(int argc, char* argv[]) { int result = 0; rttb::testing::registerTests(); try { result = lit::multiTestsMain(argc, argv); } catch (const std::exception& /*e*/) { result = -1; } catch (...) { result = -1; } return result; } diff --git a/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.cpp b/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.cpp index 8fca7ce..fb4b417 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.cpp +++ b/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.cpp @@ -1,110 +1,104 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #undef MAP_SEAL_ALGORITHMS #include "simpleRegistrationWorkflow.h" #include "registrationHelper.h" simpleRegistrationWorkflow::simpleRegistrationWorkflow(std::string targetFilename, std::string movingFilename, bool isDirectory) : _targetFilename(targetFilename), _movingFilename(movingFilename) { setImageFileNames(_targetFilename, _movingFilename, isDirectory, globals); loadData(globals); _spAlgorithmEuler = nullptr; } vnl_vector<double> simpleRegistrationWorkflow::getRegistrationParameters( Registration3D3DPointer reg) { typedef map::core::PreCachedRegistrationKernel<3, 3> PreCachedRegistrationKernel3D3D; const PreCachedRegistrationKernel3D3D* pModelBasedDirectKernel3D3D = dynamic_cast<const PreCachedRegistrationKernel3D3D*>(&(reg->getDirectMapping())); if (pModelBasedDirectKernel3D3D) { PreCachedRegistrationKernel3D3D::TransformType::ParametersType params = pModelBasedDirectKernel3D3D->getTransformModel()->GetParameters(); return params; } else { return vnl_vector<double>(); } } void simpleRegistrationWorkflow::initializeAndPerformRegistration() { _spAlgorithmEuler = AlgorithmTypeEuler::New(); _spAlgorithmEuler->setProperty("PreinitTransform", map::core::MetaProperty<bool>::New(true)); _spAlgorithmEuler->setMovingImage(globals.spMovingImage); _spAlgorithmEuler->setTargetImage(globals.spTargetImage); AlgorithmTypeEuler::RegistrationType::Pointer spRegistration; try { spRegistration = _spAlgorithmEuler->getRegistration(); } catch (const map::core::ExceptionObject& e) { std::cerr << "caught an MatchPoint exception:\n"; e.Print(std::cerr); std::cerr << "\n"; } catch (const itk::ExceptionObject& e) { std::cerr << "caught an ITK exception:\n"; std::cerr << e.GetFile() << ":" << e.GetLine() << ":\n" << e.GetDescription() << "\n"; } catch (const std::exception& e) { std::cerr << "caught an exception:\n"; std::cerr << e.what() << "\n"; } catch (...) { std::cerr << "caught an unknown exception!!!\n"; } } map::core::Registration<3, 3>::Pointer simpleRegistrationWorkflow::getRegistration() { if (_spAlgorithmEuler.IsNull()) { initializeAndPerformRegistration(); } return _spAlgorithmEuler->getRegistration(); }; const itk::Image<ImageType::PixelType, 3>* simpleRegistrationWorkflow::getTargetImage() { if (_spAlgorithmEuler.IsNull()) { initializeAndPerformRegistration(); } return _spAlgorithmEuler->getTargetImage(); }; diff --git a/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.h b/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.h index 75baffa..9a12227 100644 --- a/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.h +++ b/testing/interpolation/InterpolationMatchPointTransformation/simpleRegistrationWorkflow.h @@ -1,63 +1,58 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html [^] // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ + #ifndef __SIMPLE_REGISTRATION_WORKFLOW_H #define __SIMPLE_REGISTRATION_WORKFLOW_H #include <boost/shared_ptr.hpp> #include "registrationHelper.h" #include "mapImageMappingTask.h" #include "mapITKEuler3DMattesMIRegistrationAlgorithmTemplate.h" #include "mapExceptionObject.h" /*! @class simpleRegistrationWorkflow @brief implements a concrete registration algorithm of MatchPoint */ class simpleRegistrationWorkflow { public: typedef map::core::Registration<3, 3> Registration3D3DType; typedef Registration3D3DType::Pointer Registration3D3DPointer; typedef map::algorithm::boxed::ITKEuler3DMattesMIRegistrationAlgorithm<ImageType> AlgorithmTypeEuler; private: std::string _targetFilename; std::string _movingFilename; std::string _targetDirectory; std::string _movingDirectory; AppGlobals globals; AlgorithmTypeEuler::Pointer _spAlgorithmEuler; public: /*! @brief Constructor */ simpleRegistrationWorkflow(std::string targetFilename, std::string movingFilename, bool isDirectory = false); map::core::Registration<3, 3>::Pointer getRegistration(); const itk::Image<ImageType::PixelType, 3>* getTargetImage(); vnl_vector<double> getRegistrationParameters(Registration3D3DPointer reg); protected: void initializeAndPerformRegistration(); }; #endif \ No newline at end of file diff --git a/testing/interpolation/RosuMappableDoseAccessorTest.cpp b/testing/interpolation/RosuMappableDoseAccessorTest.cpp index eaaa6b2..6dac371 100644 --- a/testing/interpolation/RosuMappableDoseAccessorTest.cpp +++ b/testing/interpolation/RosuMappableDoseAccessorTest.cpp @@ -1,150 +1,144 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "litCheckMacros.h" #include <boost/make_shared.hpp> #include "rttbBaseType.h" #include "rttbGenericDoseIterator.h" #include "rttbDicomFileDoseAccessorGenerator.h" #include "rttbRosuMappableDoseAccessor.h" #include "DummyTransformation.h" #include "rttbNullPointerException.h" #include "rttbMappingOutsideOfImageException.h" namespace rttb { namespace testing { typedef core::GenericDoseIterator::DoseAccessorPointer DoseAccessorPointer; typedef rttb::interpolation::RosuMappableDoseAccessor RosuMappableDoseAccessor; typedef rttb::interpolation::TransformationInterface TransformationInterface; /*! @brief RosuMappableDoseAccessorTest - test the API of RosuMappableDoseAccessor 1) Constructor 2) test getDoseAt() */ int RosuMappableDoseAccessorTest(int argc, char* argv[]) { PREPARE_DEFAULT_TEST_REPORTING; std::string RTDOSE_FILENAME_CONSTANT_TWO; std::string RTDOSE_FILENAME_INCREASE_X; if (argc > 2) { RTDOSE_FILENAME_CONSTANT_TWO = argv[1]; RTDOSE_FILENAME_INCREASE_X = argv[2]; } else { std::cout << "at least two parameters for RosuMappableDoseAccessorTest are expected" << std::endl; return -1; } const double doseGridScaling = 2.822386e-005; rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator1( RTDOSE_FILENAME_CONSTANT_TWO.c_str()); DoseAccessorPointer doseAccessor1(doseAccessorGenerator1.generateDoseAccessor()); rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator2( RTDOSE_FILENAME_INCREASE_X.c_str()); DoseAccessorPointer doseAccessor2(doseAccessorGenerator2.generateDoseAccessor()); DoseAccessorPointer doseAccessorNull; auto transformDummy = boost::make_shared<DummyTransformation>(); TransformationInterface::Pointer transformNull; auto aRosuMappableDoseAccessorDefault = boost::make_shared<RosuMappableDoseAccessor>(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy); auto aRosuMappableDoseAccessorNoPadding = boost::make_shared<RosuMappableDoseAccessor>(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, false); //1) Constructor CHECK_NO_THROW(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy)); CHECK_NO_THROW(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, false)); CHECK_NO_THROW(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, true, 5.0)); CHECK_THROW_EXPLICIT(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessorNull, transformDummy), core::NullPointerException); CHECK_THROW_EXPLICIT(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformNull), core::NullPointerException); CHECK_THROW_EXPLICIT(RosuMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessorNull, transformNull), core::NullPointerException); //2) test getDoseAt() std::vector<VoxelGridIndex3D> voxelsAsIndexToTest; std::vector<VoxelGridID> voxelsAsIdToTest; std::vector<DoseTypeGy> expectedValues; voxelsAsIndexToTest.push_back(VoxelGridIndex3D(5, 9, 8)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(22, 15, 10)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(30, 20, 7)); expectedValues.push_back(5.0 * doseGridScaling); expectedValues.push_back(22.0 * doseGridScaling); expectedValues.push_back(30.0 * doseGridScaling); //convert VoxelGridIndex3D to VoxelGridID for (unsigned int i = 0; i < voxelsAsIndexToTest.size(); i++) { VoxelGridID currentId; doseAccessor1->getGeometricInfo().convert(voxelsAsIndexToTest.at(i), currentId); voxelsAsIdToTest.push_back(currentId); } for (unsigned int i = 0; i < voxelsAsIndexToTest.size(); i++) { //test if the expected interpolation values are computed CHECK_CLOSE(aRosuMappableDoseAccessorDefault->getValueAt(voxelsAsIndexToTest.at(i)), expectedValues.at(i), errorConstant); //test if getDoseAt(VoxelGridIndex3D) and getDoseAt(VoxelGridD) lead to the same results CHECK_EQUAL(aRosuMappableDoseAccessorDefault->getValueAt(voxelsAsIndexToTest.at(i)), aRosuMappableDoseAccessorDefault->getValueAt(voxelsAsIdToTest.at(i))); } //test invalid voxels VoxelGridID invalidID(doseAccessor1->getGeometricInfo().getNumberOfVoxels() + 1); VoxelGridIndex3D invalidIndex(doseAccessor1->getGeometricInfo().getNumColumns() + 1, doseAccessor1->getGeometricInfo().getNumRows() + 1, doseAccessor1->getGeometricInfo().getNumSlices() + 1); CHECK_EQUAL(aRosuMappableDoseAccessorDefault->getValueAt(invalidID), 0.0); CHECK_EQUAL(aRosuMappableDoseAccessorDefault->getValueAt(invalidIndex), 0.0); CHECK_THROW_EXPLICIT(aRosuMappableDoseAccessorNoPadding->getValueAt(invalidID), core::MappingOutsideOfImageException); CHECK_THROW_EXPLICIT(aRosuMappableDoseAccessorNoPadding->getValueAt(invalidIndex), core::MappingOutsideOfImageException); RETURN_AND_REPORT_TEST_SUCCESS; } }//end namespace testing }//end namespace rttb diff --git a/testing/interpolation/SimpleMappableDoseAccessorTest.cpp b/testing/interpolation/SimpleMappableDoseAccessorTest.cpp index 99a1b17..0506aba 100644 --- a/testing/interpolation/SimpleMappableDoseAccessorTest.cpp +++ b/testing/interpolation/SimpleMappableDoseAccessorTest.cpp @@ -1,168 +1,162 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ -/*! -// @file -// @version $Revision$ (last changed revision) -// @date $Date$ (last change date) -// @author $Author$ (last changed by) -*/ #include "boost/make_shared.hpp" #include "litCheckMacros.h" #include "rttbBaseType.h" #include "rttbGenericDoseIterator.h" #include "rttbDicomFileDoseAccessorGenerator.h" #include "rttbSimpleMappableDoseAccessor.h" #include "rttbNearestNeighborInterpolation.h" #include "rttbLinearInterpolation.h" #include "rttbTransformationInterface.h" #include "DummyTransformation.h" #include "rttbNullPointerException.h" #include "rttbMappingOutsideOfImageException.h" namespace rttb { namespace testing { typedef core::GenericDoseIterator::DoseAccessorPointer DoseAccessorPointer; typedef rttb::interpolation::SimpleMappableDoseAccessor SimpleMappableDoseAccessor; typedef rttb::interpolation::TransformationInterface TransformationInterface; typedef rttb::interpolation::LinearInterpolation LinearInterpolation; typedef rttb::interpolation::NearestNeighborInterpolation NearestNeighborInterpolation; /*! @brief SimpleMappableDoseAccessorTest - test the API of SimpleMappableDoseAccessor 1) Test constructor 2) test getDoseAt() */ int SimpleMappableDoseAccessorTest(int argc, char* argv[]) { PREPARE_DEFAULT_TEST_REPORTING; std::string RTDOSE_FILENAME_CONSTANT_TWO; std::string RTDOSE_FILENAME_INCREASE_X; if (argc > 2) { RTDOSE_FILENAME_CONSTANT_TWO = argv[1]; RTDOSE_FILENAME_INCREASE_X = argv[2]; } else { std::cout << "at least two parameters for SimpleMappableDoseAccessorTest are expected" << std::endl; return -1; } const double doseGridScaling = 2.822386e-005; rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator1( RTDOSE_FILENAME_CONSTANT_TWO.c_str()); DoseAccessorPointer doseAccessor1(doseAccessorGenerator1.generateDoseAccessor()); core::GeometricInfo doseAccessor1GeometricInfo = doseAccessor1->getGeometricInfo(); rttb::io::dicom::DicomFileDoseAccessorGenerator doseAccessorGenerator2( RTDOSE_FILENAME_INCREASE_X.c_str()); DoseAccessorPointer doseAccessor2(doseAccessorGenerator2.generateDoseAccessor()); DoseAccessorPointer doseAccessorNull; TransformationInterface::Pointer transformDummy = boost::make_shared<DummyTransformation>(); TransformationInterface::Pointer transformNull; auto interpolationNN = boost::make_shared<NearestNeighborInterpolation>(); auto interpolationLinear = boost::make_shared<LinearInterpolation>(); boost::shared_ptr<NearestNeighborInterpolation> interpolationNull; auto aSimpleMappableDoseAccessorDefault = boost::make_shared<SimpleMappableDoseAccessor>( doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy); auto aSimpleMappableDoseAccessorNoPadding = boost::make_shared<SimpleMappableDoseAccessor>( doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, interpolationLinear, false); //1) Test constructor CHECK_NO_THROW(SimpleMappableDoseAccessor( doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy)); CHECK_NO_THROW(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, interpolationLinear)); CHECK_NO_THROW(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, interpolationLinear, false)); CHECK_NO_THROW(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformDummy, interpolationLinear, true, 5.0)); CHECK_NO_THROW(SimpleMappableDoseAccessor(doseAccessor1GeometricInfo, doseAccessor2, transformDummy, interpolationNN)); CHECK_THROW_EXPLICIT(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessorNull, transformDummy, interpolationLinear), core::NullPointerException); CHECK_THROW_EXPLICIT(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessor2, transformNull, interpolationLinear), core::NullPointerException); CHECK_THROW_EXPLICIT(SimpleMappableDoseAccessor test(doseAccessor1->getGeometricInfo(), doseAccessorNull, transformNull, interpolationLinear), core::NullPointerException); CHECK_THROW_EXPLICIT(SimpleMappableDoseAccessor(doseAccessor1GeometricInfo, doseAccessor2, transformDummy, interpolationNull), core::NullPointerException); //2) test getGeometricInfo(), getGridSize(), getDoseUID() function CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getGeometricInfo(), doseAccessor1->getGeometricInfo()); CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getGridSize(), doseAccessor1->getGeometricInfo().getNumberOfVoxels()); CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getUID(), doseAccessor2->getUID()); //3) test getDoseAt() //test valid voxels std::vector<VoxelGridIndex3D> voxelsAsIndexToTest; std::vector<DoseTypeGy> expectedValues; voxelsAsIndexToTest.push_back(VoxelGridIndex3D(5, 9, 8)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(22, 15, 10)); voxelsAsIndexToTest.push_back(VoxelGridIndex3D(30, 20, 7)); expectedValues.push_back(5.0 * doseGridScaling); expectedValues.push_back(22.0 * doseGridScaling); expectedValues.push_back(30.0 * doseGridScaling); for (unsigned int i = 0; i < voxelsAsIndexToTest.size(); i++) { VoxelGridID currentId; doseAccessor1GeometricInfo.convert(voxelsAsIndexToTest.at(i), currentId); //test if the expected interpolation values are computed CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getValueAt(currentId), expectedValues.at(i)); //test if getDoseAt(VoxelGridIndex3D) and getDoseAt(VoxelGridD) lead to the same results CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getValueAt(currentId), aSimpleMappableDoseAccessorDefault->getValueAt(voxelsAsIndexToTest.at(i))); } //test invalid voxels VoxelGridID invalidID(doseAccessor1GeometricInfo.getNumberOfVoxels() + 1); VoxelGridIndex3D invalidIndex(doseAccessor1GeometricInfo.getNumColumns() + 1, doseAccessor1GeometricInfo.getNumRows() + 1, doseAccessor1GeometricInfo.getNumSlices() + 1); CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getValueAt(invalidID), 0.0); CHECK_EQUAL(aSimpleMappableDoseAccessorDefault->getValueAt(invalidIndex), 0.0); CHECK_THROW_EXPLICIT(aSimpleMappableDoseAccessorNoPadding->getValueAt(invalidID), core::MappingOutsideOfImageException); CHECK_THROW_EXPLICIT(aSimpleMappableDoseAccessorNoPadding->getValueAt(invalidIndex), core::MappingOutsideOfImageException); RETURN_AND_REPORT_TEST_SUCCESS; } }//end namespace testing }//end namespace rttb diff --git a/testing/interpolation/rttbInterpolationTests.cpp b/testing/interpolation/rttbInterpolationTests.cpp index a4180bc..bd21cec 100644 --- a/testing/interpolation/rttbInterpolationTests.cpp +++ b/testing/interpolation/rttbInterpolationTests.cpp @@ -1,55 +1,54 @@ // ----------------------------------------------------------------------- // RTToolbox - DKFZ radiotherapy quantitative evaluation library // // Copyright (c) German Cancer Research Center (DKFZ), // Software development for Integrated Diagnostics and Therapy (SIDT). // ALL RIGHTS RESERVED. // See rttbCopyright.txt or // http://www.dkfz.de/en/sidt/projects/rttb/copyright.html // // This software is distributed WITHOUT ANY WARRANTY; without even // the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // PURPOSE. See the above copyright notices for more information. // //------------------------------------------------------------------------ // this file defines the rttbAlgorithmsTests for the test driver // and all it expects is that you have a function called RegisterTests #if defined(_MSC_VER) #pragma warning ( disable : 4786 ) #endif - #include "litMultiTestsMain.h" namespace rttb { namespace testing { void registerTests() { LIT_REGISTER_TEST(SimpleMappableDoseAccessorTest); LIT_REGISTER_TEST(RosuMappableDoseAccessorTest); LIT_REGISTER_TEST(InterpolationTest); } } } int main(int argc, char* argv[]) { int result = 0; rttb::testing::registerTests(); try { result = lit::multiTestsMain(argc, argv); } catch (...) { result = -1; } return result; }