From 5b0a8467f664b624f7fc0a5020cd7610e8da2c13 Mon Sep 17 00:00:00 2001 From: Romulo Pinho Date: Wed, 25 Jan 2012 15:46:23 +0100 Subject: [PATCH] new tool: clitkCoeffsToDVF - converts a BLUT-coefficient image to a DVF --- common/clitkCoeffsToDVF.h | 150 ++++++++++++++++++++++++------------- tools/CMakeLists.txt | 8 +- tools/clitkCoeffsToDVF.cxx | 56 ++++++++++++++ tools/clitkCoeffsToDVF.ggo | 12 +++ 4 files changed, 174 insertions(+), 52 deletions(-) create mode 100644 tools/clitkCoeffsToDVF.cxx create mode 100644 tools/clitkCoeffsToDVF.ggo diff --git a/common/clitkCoeffsToDVF.h b/common/clitkCoeffsToDVF.h index 0fe30bb..603ca70 100644 --- a/common/clitkCoeffsToDVF.h +++ b/common/clitkCoeffsToDVF.h @@ -18,69 +18,119 @@ #ifndef clitkCoeffsToDVF_h #define clitkCoeffsToDVF_h +#include "itkImageFileReader.h" +#include "itkImageIOBase.h" + #include "clitkBSplineDeformableTransform.h" +#include "clitkResampleBSplineDeformableTransformImageFilter.h" #if ITK_VERSION_MAJOR >= 4 #include "itkTransformToDisplacementFieldSource.h" #else #include "itkTransformToDeformationFieldSource.h" #endif +#include "itkBSplineDeformableTransform.h" -//------------------------------------------------------------------- -// Convert Coefficient image to DVF -//------------------------------------------------------------------- -template -typename DisplacementFieldType::Pointer -CoeffsToDVF(std::string fileName, std::string likeFileName, bool verbose = false) +namespace clitk { - typedef clitk::BSplineDeformableTransform TransformType; - typedef typename TransformType::CoefficientImageType CoefficientImageType; + //------------------------------------------------------------------- + // Initialize transform from coefficient images + //------------------------------------------------------------------- + template + void + SetInitialTransformParameters(typename TransformType::Pointer transform, const typename TransformType::CoefficientImageType::Pointer coefficientImage, typename TransformType::CoefficientImageType::SpacingType outputSpacing) + { + unsigned int dim = TransformType::CoefficientImageType::ImageDimension; + transform->SetSplineOrder(3); + transform->SetGridRegion( coefficientImage->GetLargestPossibleRegion() ); + transform->SetGridOrigin( coefficientImage->GetOrigin() ); + transform->SetGridSpacing( coefficientImage->GetSpacing() ); + transform->SetGridDirection( coefficientImage->GetDirection() ); + typename TransformType::RegionType::SizeType samplingFactors; + for (unsigned int i=0; i< dim; i++) { + samplingFactors[i]= (int) ( coefficientImage->GetSpacing()[i]/ outputSpacing[i]); + } + transform->SetLUTSamplingFactors(samplingFactors); + + typedef typename TransformType::ParametersType ParametersType; + const unsigned int numberOfParameters = transform->GetNumberOfParameters(); + ParametersType params(numberOfParameters); + params.Fill( 0.0 ); - typedef itk::ImageFileReader CoeffReaderType; - typename CoeffReaderType::Pointer reader = CoeffReaderType::New(); - reader->SetFileName(fileName); - reader->Update(); + typedef itk::ImageRegionConstIterator Iterator; + Iterator it (coefficientImage, coefficientImage->GetLargestPossibleRegion() ); + it.GoToBegin(); + unsigned int i = 0; + while (! it.IsAtEnd()) { + for (unsigned int j = 0; j < dim; j++) + params[i+j]=it.Get()[j]; - typename TransformType::Pointer transform = TransformType::New(); - transform->SetCoefficientImage(reader->GetOutput()); - -#if ITK_VERSION_MAJOR >= 4 - typedef itk::TransformToDisplacementFieldSource ConvertorType; -#else - typedef itk::TransformToDeformationFieldSource ConvertorType; -#endif + ++it; + i += dim; + } - typedef itk::ImageIOBase ImageIOType; - typename ImageIOType::Pointer imageIO = itk::ImageIOFactory::CreateImageIO(likeFileName.c_str(), itk::ImageIOFactory::ReadMode); - imageIO->SetFileName(likeFileName); - imageIO->ReadImageInformation(); - - typename ConvertorType::Pointer convertor= ConvertorType::New(); - typename ConvertorType::SizeType output_size; - typename ConvertorType::SpacingType output_spacing; - typename ConvertorType::OriginType output_origin; - typename ConvertorType::DirectionType output_direction; - for (unsigned int i = 0; i < DisplacementFieldType::ImageDimension; i++) { - output_size[i] = imageIO->GetDimensions(i); - output_spacing[i] = imageIO->GetSpacing(i); - output_origin[i] = imageIO->GetOrigin(i); - for (unsigned int j = 0; j < DisplacementFieldType::ImageDimension; j++) - output_direction[i][j] = imageIO->GetDirection(i)[j]; + transform->SetParameters(params); + transform->SetBulkTransform(NULL); } - - if (verbose) { - std::cout << "Interpolating coefficients with grid:" << std::endl; - std::cout << output_size << output_spacing << std::endl; + + //------------------------------------------------------------------- + // Convert Coefficient image to DVF + //------------------------------------------------------------------- + template + typename DisplacementFieldType::Pointer + BLUTCoeffsToDVF(std::string fileName, std::string likeFileName, bool verbose = false) + { + const unsigned int dim = DisplacementFieldType::ImageDimension; + typedef clitk::BSplineDeformableTransform TransformType; + typedef typename TransformType::CoefficientImageType CoefficientImageType; + + typedef itk::ImageFileReader CoeffReaderType; + typename CoeffReaderType::Pointer reader = CoeffReaderType::New(); + reader->SetFileName(fileName); + reader->Update(); + + #if ITK_VERSION_MAJOR >= 4 + typedef itk::TransformToDisplacementFieldSource ConvertorType; + #else + typedef itk::TransformToDeformationFieldSource ConvertorType; + #endif + + typedef itk::ImageIOBase ImageIOType; + typename ImageIOType::Pointer imageIO = itk::ImageIOFactory::CreateImageIO(likeFileName.c_str(), itk::ImageIOFactory::ReadMode); + imageIO->SetFileName(likeFileName); + imageIO->ReadImageInformation(); + + typename ConvertorType::Pointer convertor= ConvertorType::New(); + typename ConvertorType::SizeType output_size; + typename ConvertorType::SpacingType output_spacing; + typename ConvertorType::OriginType output_origin; + typename ConvertorType::DirectionType output_direction; + for (unsigned int i = 0; i < dim; i++) { + output_size[i] = imageIO->GetDimensions(i); + output_spacing[i] = imageIO->GetSpacing(i); + output_origin[i] = imageIO->GetOrigin(i); + for (unsigned int j = 0; j < DisplacementFieldType::ImageDimension; j++) + output_direction[i][j] = imageIO->GetDirection(i)[j]; + } + + typename CoefficientImageType::Pointer coeffs = reader->GetOutput(); + typename TransformType::Pointer transform = TransformType::New(); + SetInitialTransformParameters(transform, coeffs, output_spacing); + + if (verbose) { + std::cout << "Interpolating coefficients with grid:" << std::endl; + std::cout << output_size << output_spacing << std::endl; + } + + convertor->SetNumberOfThreads(1); + convertor->SetTransform(transform); + convertor->SetOutputOrigin(output_origin); + convertor->SetOutputSpacing(output_spacing); + convertor->SetOutputSize(output_size); + convertor->SetOutputDirection(output_direction); + convertor->Update(); + + return convertor->GetOutput(); } - - convertor->SetNumberOfThreads(1); - convertor->SetTransform(transform); - convertor->SetOutputOrigin(output_origin); - convertor->SetOutputSpacing(output_spacing); - convertor->SetOutputSize(output_size); - convertor->SetOutputDirection(output_direction); - convertor->Update(); - - return convertor->GetOutput(); } #endif diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt index 7b1a9fa..a201e18 100644 --- a/tools/CMakeLists.txt +++ b/tools/CMakeLists.txt @@ -360,8 +360,12 @@ IF (CLITK_BUILD_TOOLS) TARGET_LINK_LIBRARIES(clitkCatImage clitkCommon ${ITK_LIBRARIES}) SET(TOOLS_INSTALL ${TOOLS_INSTALL} clitkCatImage) - IF(CLITK_EXPERIMENTAL) + WRAP_GGO(clitkCoeffsToDVF_GGO_C clitkCoeffsToDVF.ggo) + ADD_EXECUTABLE(clitkCoeffsToDVF clitkCoeffsToDVF.cxx ${clitkCoeffsToDVF_GGO_C}) + TARGET_LINK_LIBRARIES(clitkCoeffsToDVF clitkCommon ${ITK_LIBRARIES}) + SET(TOOLS_INSTALL ${TOOLS_INSTALL} clitkCoeffsToDVF) + IF(CLITK_EXPERIMENTAL) WRAP_GGO(clitkBinaryImageToMesh_GGO_C clitkBinaryImageToMesh.ggo) ADD_EXECUTABLE(clitkBinaryImageToMesh clitkBinaryImageToMesh.cxx ${clitkBinaryImageToMesh_GGO_C}) TARGET_LINK_LIBRARIES(clitkBinaryImageToMesh ${ITK_LIBRARIES} ${VTK_LIBRARIES}) @@ -379,7 +383,7 @@ IF (CLITK_BUILD_TOOLS) ENDIF(CLITK_EXPERIMENTAL) SET_TARGET_PROPERTIES(${TOOLS_INSTALL} PROPERTIES INSTALL_RPATH "${VTK_DIR}:${ITK_DIR}" ) - INSTALL (TARGETS ${TOOLS_INSTALL} DESTINATION bin PERMISSIONS OWNER_READ OWNER_WRITE OWNER_EXECUTE GROUP_EXECUTE WORLD_EXECUTE) + INSTALL (TARGETS ${TOOLS_INSTALL} DESTINATION bin PERMISSIONS OWNER_READ OWNER_WRITE OWNER_EXECUTE GROUP_READ GROUP_EXECUTE WORLD_READ WORLD_EXECUTE) ENDIF(CLITK_BUILD_TOOLS) diff --git a/tools/clitkCoeffsToDVF.cxx b/tools/clitkCoeffsToDVF.cxx new file mode 100644 index 0000000..266f8ae --- /dev/null +++ b/tools/clitkCoeffsToDVF.cxx @@ -0,0 +1,56 @@ +#include "clitkCoeffsToDVF_ggo.h" +#include "clitkCoeffsToDVF.h" +#include "itkImage.h" +#include "itkImageFileWriter.h" +#include "itkImageIOFactory.h" +#include + +template +void +Write(typename DisplacementFieldType::Pointer dvf, std::string fileName) +{ + typedef itk::ImageFileWriter ImageWriterType; + typename ImageWriterType::Pointer writer = ImageWriterType::New(); + writer->SetFileName(fileName); + writer->SetInput(dvf); + writer->Update(); +} + +int main(int argc, char** argv) +{ + GGO(clitkCoeffsToDVF, args_info); + CLITK_INIT; + + typename itk::ImageIOBase::Pointer image_io = itk::ImageIOFactory::CreateImageIO(args_info.input_arg, itk::ImageIOFactory::ReadMode); + image_io->SetFileName(args_info.input_arg); + image_io->ReadImageInformation(); + + unsigned int ndim = image_io->GetNumberOfDimensions(); + switch (ndim) { + case 2: + { + unsigned const dim = 2; + typedef itk::Vector PixelType; + typedef itk::Image DVFType; + typename DVFType::Pointer dvf = clitk::BLUTCoeffsToDVF(args_info.input_arg, args_info.like_arg); + Write(dvf, args_info.output_arg); + } + break; + + case 3: + { + unsigned const dim = 3; + typedef itk::Vector PixelType; + typedef itk::Image DVFType; + typename DVFType::Pointer dvf = clitk::BLUTCoeffsToDVF(args_info.input_arg, args_info.like_arg); + Write(dvf, args_info.output_arg); + } + break; + + default: + std::cerr << "Unsupported image dimension (either 2 or 3)" << std::endl; + return -1; + } + + return 0; +} \ No newline at end of file diff --git a/tools/clitkCoeffsToDVF.ggo b/tools/clitkCoeffsToDVF.ggo new file mode 100644 index 0000000..a3d9d5e --- /dev/null +++ b/tools/clitkCoeffsToDVF.ggo @@ -0,0 +1,12 @@ +#File clitkComposeVF.ggo +#Author: Rômulo Pinho +#Date : Wed 24 January 2012 + +package "clitk" +version "Convert a BLUT-coefficient image to a vector field." + +option "config" - "Config file" string no +option "input" i "Input1 VF filename" string yes +option "output" o "Output VF filename" string yes +option "like" l "Image to read output parameters from" string yes + -- 2.45.1