ANIMA  4.0
animaLinearTransformToSVF.cxx
Go to the documentation of this file.
1 #include <tclap/CmdLine.h>
2 
3 #include <itkTransformFileReader.h>
4 #include <itkTransformFileWriter.h>
5 #include <itkAffineTransform.h>
6 #include <animaMatrixLogExp.h>
7 #include <itkTransformToDisplacementFieldFilter.h>
9 
10 int main(int argc, char **argv)
11 {
12  std::string descriptionMessage = "Linear transform to SVF\n INRIA / IRISA - VisAGeS/Empenn Team";
13  TCLAP::CmdLine cmd(descriptionMessage, ' ', ANIMA_VERSION);
14 
15  TCLAP::ValueArg<std::string> inArg("i", "input", "Input linear transform", true, "", "input transform", cmd);
16  TCLAP::ValueArg<std::string> outArg("o", "output", "Output SVF", true, "", "output transform", cmd);
17  TCLAP::ValueArg<std::string> geomArg("g", "geometry", "Geometry image", true, "", "geometry image", cmd);
18 
19  try
20  {
21  cmd.parse(argc, argv);
22  }
23  catch (TCLAP::ArgException& e)
24  {
25  std::cerr << "Error: " << e.error() << "for argument " << e.argId() << std::endl;
26  return EXIT_FAILURE;
27  }
28 
29  const unsigned int Dimension = 3;
30  typedef double PixelType;
31  typedef itk::Image< PixelType, Dimension > GeomImageType;
32  GeomImageType::Pointer geomImage = anima::readImage <GeomImageType> (geomArg.getValue());
33 
34  typedef double PrecisionType;
35  typedef itk::AffineTransform <PrecisionType, Dimension> MatrixTransformType;
36  typedef MatrixTransformType::Pointer MatrixTransformPointer;
37  typedef vnl_matrix <double> MatrixType;
38  typedef itk::TransformFileReader TransformReaderType;
39 
40  TransformReaderType::Pointer trReader = TransformReaderType::New();
41  trReader->SetFileName(inArg.getValue());
42  try
43  {
44  trReader->Update();
45  }
46  catch (itk::ExceptionObject &e)
47  {
48  std::cerr << "Problem reading transform file " << inArg.getValue() << ", exiting\nerror exception object :\n" << e << std::endl;
49  return EXIT_FAILURE;
50  }
51 
52  itk::TransformFileReader::TransformListType trsfList = *(trReader->GetTransformList());
53  itk::TransformFileReader::TransformListType::iterator tr_it = trsfList.begin();
54 
55  MatrixTransformType *trsf = dynamic_cast <MatrixTransformType *> ((*tr_it).GetPointer());
56 
57  if (trsf == nullptr)
58  {
59  std::cerr << "Problem converting transform file to linear file " << inArg.getValue() << ", exiting" << std::endl;
60  return EXIT_FAILURE;
61  }
62 
63  MatrixType workMatrix(Dimension + 1, Dimension + 1), logWorkMatrix(Dimension + 1, Dimension + 1);
64  logWorkMatrix.fill(0);
65 
66  workMatrix.set_identity();
67  for (unsigned int i = 0; i < Dimension; ++i)
68  {
69  workMatrix(i, Dimension) = trsf->GetOffset()[i];
70  for (unsigned int j = 0; j < Dimension; ++j)
71  workMatrix(i, j) = trsf->GetMatrix()(i, j);
72  }
73 
74  logWorkMatrix = anima::GetLogarithm(workMatrix);
75 
76  MatrixTransformPointer logTrsf = MatrixTransformType::New();
77  logTrsf->SetIdentity();
78 
79  MatrixTransformType::OffsetType logOffset;
80  MatrixTransformType::MatrixType logMatrix;
81 
82  for (unsigned int i = 0; i < Dimension;++i)
83  {
84  logOffset[i] = logWorkMatrix(i, Dimension);
85  for (unsigned int j = 0; j < Dimension;++j)
86  logMatrix(i, j) = logWorkMatrix(i, j);
87  logMatrix(i, i) += 1; // add identity because TransformToDisplacementFieldFilter
88  }
89 
90  logTrsf->SetMatrix(logMatrix);
91  logTrsf->SetOffset(logOffset);
92 
93  typedef double CoordinateRepType;
94  typedef itk::Vector< double, Dimension > VectorPixelType;
95  typedef itk::Image< VectorPixelType, Dimension > DisplacementFieldImageType;
96  typedef itk::TransformToDisplacementFieldFilter< DisplacementFieldImageType, CoordinateRepType > DisplacementFieldGeneratorType;
97 
98  DisplacementFieldGeneratorType::Pointer dispfieldGenerator = DisplacementFieldGeneratorType::New();
99  dispfieldGenerator->UseReferenceImageOn();
100  dispfieldGenerator->SetReferenceImage(geomImage);
101  dispfieldGenerator->SetTransform(logTrsf);
102 
103  anima::writeImage <DisplacementFieldImageType> (outArg.getValue(),dispfieldGenerator->GetOutput());
104 
105  return EXIT_SUCCESS;
106 }
int main(int argc, char **argv)
vnl_matrix< T > GetLogarithm(const vnl_matrix< T > &m, const double precision=0.00000000001, const int numApprox=1)
Computation of the matrix logarithm. Algo: inverse scaling and squaring, variant proposed by Cheng et...