clitkExceptionObject.cxx
clitkFilterBase.cxx
clitkMemoryUsage.cxx
+ clitkMatrix.cxx
vvImage.cxx
vvImageReader.cxx
vvImageWriter.cxx
--- /dev/null
+/*=========================================================================
+ Program: vv http://www.creatis.insa-lyon.fr/rio/vv
+
+ Authors belong to:
+ - University of LYON http://www.universite-lyon.fr/
+ - Léon Bérard cancer center http://www.centreleonberard.fr
+ - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr
+
+ This software is distributed WITHOUT ANY WARRANTY; without even
+ the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ PURPOSE. See the copyright notices for more information.
+
+ It is distributed under dual licence
+
+ - BSD See included LICENSE.txt file
+ - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
+===========================================================================**/
+
+#ifndef clitkElastix_h
+#define clitkElastix_h
+
+#include <itkEuler3DTransform.h>
+
+//--------------------------------------------------------------------
+namespace clitk {
+
+//-------------------------------------------------------------------
+bool
+GetElastixValueFromTag(std::ifstream & is,
+ std::string tag,
+ std::string & value)
+{
+ std::string line;
+ is.seekg (0, is.beg);
+ while(std::getline(is, line)) {
+ unsigned pos = line.find(tag);
+ if (pos<line.size()) {
+ value=line.substr(pos+tag.size(),line.size()-2);// remove last ')'
+ value.erase (std::remove (value.begin(), value.end(), '"'), value.end());
+ value.erase (std::remove (value.begin(), value.end(), ')'), value.end());
+ return true;
+ }
+ }
+ return false;
+}
+//-------------------------------------------------------------------
+
+
+//-------------------------------------------------------------------
+void
+GetValuesFromValue(const std::string & s,
+ std::vector<std::string> & values)
+{
+ std::stringstream strstr(s);
+ std::istream_iterator<std::string> it(strstr);
+ std::istream_iterator<std::string> end;
+ std::vector<std::string> results(it, end);
+ values.clear();
+ values.resize(results.size());
+ for(uint i=0; i<results.size(); i++) values[i] = results[i];
+}
+//-------------------------------------------------------------------
+
+
+//-------------------------------------------------------------------
+template<unsigned int Dimension>
+typename itk::Matrix<double, Dimension+1, Dimension+1>
+createMatrixFromElastixFile(std::vector<std::string> & filename, bool verbose=true) {
+ if (Dimension != 3) {
+ FATAL("Only 3D yet" << std::endl);
+ }
+ typename itk::Matrix<double, Dimension+1, Dimension+1> matrix;
+
+ itk::Euler3DTransform<double>::Pointer mat = itk::Euler3DTransform<double>::New();
+ itk::Euler3DTransform<double>::Pointer previous;
+ for(uint j=0; j<filename.size(); j++) {
+
+ // Open file
+ if (verbose) std::cout << "Read elastix parameters in " << filename[j] << std::endl;
+ std::ifstream is;
+ clitk::openFileForReading(is, filename[j]);
+
+ // Check Transform
+ std::string s;
+ bool b = GetElastixValueFromTag(is, "Transform ", s);
+ if (!b) {
+ FATAL("Error must read 'Transform' in " << filename[j] << std::endl);
+ }
+ if (s != "EulerTransform") {
+ FATAL("Sorry only 'EulerTransform'" << std::endl);
+ }
+
+ // FIXME check
+ // (InitialTransformParametersFilename[j] "NoInitialTransform")
+
+ // Get CenterOfRotationPoint
+ GetElastixValueFromTag(is, "CenterOfRotationPoint ", s); // space is needed
+ if (!b) {
+ FATAL("Error must read 'CenterOfRotationPoint' in " << filename[j] << std::endl);
+ }
+ std::vector<std::string> cor;
+ GetValuesFromValue(s, cor);
+ itk::Euler3DTransform<double>::CenterType c;
+ for(uint i=0; i<3; i++)
+ c[i] = atof(cor[i].c_str());
+ mat->SetCenter(c);
+
+ // Get Transformparameters
+ GetElastixValueFromTag(is, "ComputeZYX ", s); // space is needed
+ mat->SetComputeZYX( s==std::string("true") );
+
+ // Get Transformparameters
+ GetElastixValueFromTag(is, "TransformParameters ", s); // space is needed
+ if (!b) {
+ FATAL("Error must read 'TransformParameters' in " << filename[j] << std::endl);
+ }
+ std::vector<std::string> results;
+ GetValuesFromValue(s, results);
+
+ // construct a stream from the string
+ itk::Euler3DTransform<double>::ParametersType p;
+ p.SetSize(6);
+ for(uint i=0; i<3; i++)
+ p[i] = atof(results[i].c_str()); // Rotation
+ for(uint i=0; i<3; i++)
+ p[i+3] = atof(results[i+3].c_str()); // Translation
+ mat->SetParameters(p);
+
+ if (verbose) {
+ std::cout << "Rotation (deg) : " << rad2deg(p[0]) << " " << rad2deg(p[1]) << " " << rad2deg(p[2]) << std::endl;
+ std::cout << "Center of rot (phy) : " << c[0] << " " << c[1] << " " << c[2] << std::endl;
+ std::cout << "Translation (phy) : " << p[3] << " " << p[4] << " " << p[5] << std::endl;
+ }
+
+ // Compose with previous if needed
+ if (j!=0) {
+ mat->Compose(previous);
+ if (verbose) {
+ std::cout << "Composed rotation (deg) : " << rad2deg(mat->GetAngleX()) << " " << rad2deg(mat->GetAngleY()) << " " << rad2deg(mat->GetAngleZ()) << std::endl;
+ std::cout << "Composed center of rot (phy) : " << mat->GetCenter() << std::endl;
+ std::cout << "Compsoed translation (phy) : " << mat->GetTranslation() << std::endl;
+ }
+ }
+ // previous = mat->Clone(); // ITK4
+ previous = itk::Euler3DTransform<double>::New();
+ previous->SetParameters(mat->GetParameters());
+ previous->SetCenter(c);
+ previous->SetComputeZYX(mat->GetComputeZYX());
+ }
+
+ mat = previous;
+ for(uint i=0; i<3; i++)
+ for(uint j=0; j<3; j++)
+ matrix[i][j] = mat->GetMatrix()[i][j];
+ // Offset is -Rc + t + c
+ matrix[0][3] = mat->GetOffset()[0];
+ matrix[1][3] = mat->GetOffset()[1];
+ matrix[2][3] = mat->GetOffset()[2];
+ matrix[3][3] = 1;
+
+ return matrix;
+}
+}
+//-------------------------------------------------------------------
+
+#endif
--- /dev/null
+/*=========================================================================
+ Program: vv http://www.creatis.insa-lyon.fr/rio/vv
+
+ Authors belong to:
+ - University of LYON http://www.universite-lyon.fr/
+ - Léon Bérard cancer center http://www.centreleonberard.fr
+ - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr
+
+ This software is distributed WITHOUT ANY WARRANTY; without even
+ the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ PURPOSE. See the copyright notices for more information.
+
+ It is distributed under dual licence
+
+ - BSD See included LICENSE.txt file
+ - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
+===========================================================================**/
+
+#include "clitkMatrix.h"
+
+//--------------------------------------------------------------------
+namespace clitk {
+
+//-------------------------------------------------------------------
+std::string
+Get4x4MatrixDoubleAsString(vtkMatrix4x4 *matrix,
+ const int precision)
+{
+ std::ostringstream strmatrix;
+
+ // Figure out the number of digits of the integer part of the largest absolute value
+ // for each column
+ unsigned width[4];
+ for (unsigned int j = 0; j < 4; j++){
+ double absmax = 0.;
+ for (unsigned int i = 0; i < 4; i++)
+ absmax = std::max(absmax, vnl_math_abs(matrix->GetElement(i, j)));
+ unsigned ndigits = (unsigned)std::max(0.,std::log10(absmax))+1;
+ width[j] = precision+ndigits+3;
+ }
+
+ // Output with correct width, aligned to the right
+ for (unsigned int i = 0; i < 4; i++) {
+ for (unsigned int j = 0; j < 4; j++) {
+ strmatrix.setf(ios::fixed,ios::floatfield);
+ strmatrix.precision(precision);
+ strmatrix.fill(' ');
+ strmatrix.width(width[j]);
+ strmatrix << std::right << matrix->GetElement(i, j);
+ }
+ strmatrix << std::endl;
+ }
+ std::string result = strmatrix.str().c_str();
+ return result;
+}
+//-------------------------------------------------------------------
+
+//-------------------------------------------------------------------
+std::string
+Get4x4MatrixDoubleAsString(itk::Matrix<double, 4, 4> m,
+ const int precision)
+{
+ vtkSmartPointer<vtkMatrix4x4> matrix = vtkSmartPointer<vtkMatrix4x4>::New();
+ for (unsigned int j = 0; j < 4; j++)
+ for (unsigned int i = 0; i < 4; i++)
+ matrix->SetElement(j,i,m[j][i]);
+ return Get4x4MatrixDoubleAsString(matrix, precision);
+}
+//-------------------------------------------------------------------
+}
+//-------------------------------------------------------------------
--- /dev/null
+/*=========================================================================
+ Program: vv http://www.creatis.insa-lyon.fr/rio/vv
+
+ Authors belong to:
+ - University of LYON http://www.universite-lyon.fr/
+ - Léon Bérard cancer center http://www.centreleonberard.fr
+ - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr
+
+ This software is distributed WITHOUT ANY WARRANTY; without even
+ the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ PURPOSE. See the copyright notices for more information.
+
+ It is distributed under dual licence
+
+ - BSD See included LICENSE.txt file
+ - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
+===========================================================================**/
+
+#ifndef clitkMatrix_h
+#define clitkMatrix_h
+
+#include <itkMatrix.h>
+#include <vtkMatrix4x4.h>
+#include <vtkSmartPointer.h>
+
+//--------------------------------------------------------------------
+namespace clitk {
+std::string
+Get4x4MatrixDoubleAsString(vtkMatrix4x4 *matrix,
+ const int precision=3);
+
+std::string
+Get4x4MatrixDoubleAsString(itk::Matrix<double, 4, 4> m,
+ const int precision=3);
+}
+//-------------------------------------------------------------------
+
+#endif
#include "vvImageReader.h"
#include "vvImageReader.txx"
#include "clitkTransformUtilities.h"
+#include "clitkElastix.h"
//------------------------------------------------------------------------------
vvImageReader::vvImageReader()
{
std::string filename(mInputFilenames[0]);
std::string ext(itksys::SystemTools::GetFilenameLastExtension(filename));
+
+ // Try a ".mat" extension
if (ext.length() > 0) {
size_t pos = filename.rfind(ext);
filename.replace(pos, ext.length(), ".mat");
}
else
filename += ".mat";
-
std::ifstream f(filename.c_str());
+ itk::Matrix<double, 4, 4> itkMat;
+ bool itkMatRead = false;
if(f.is_open()) {
- f.close();
+ itkMatRead = true;
- itk::Matrix<double, 4, 4> itkMat;
itkMat.SetIdentity();
try {
itkMat = clitk::ReadMatrix3D(filename);
catch (itk::ExceptionObject & err) {
itkWarningMacro(<< "Found " << filename
<< " but this is not a 4x4 matrix so it is ignored.");
+ itkMatRead = false;
}
+ }
+ f.close();
+
+ // Try a ".elx" extension
+ filename = mInputFilenames[0];
+ if (ext.length() > 0) {
+ size_t pos = filename.rfind(ext);
+ filename.replace(pos, ext.length(), ".elx");
+ }
+ else
+ filename += ".elx";
+ f.open(filename.c_str());
+ if(!itkMatRead && f.is_open()) {
+ itkMatRead = true;
+ std::vector<std::string> l;
+ l.push_back(filename);
+ itkMat = clitk::createMatrixFromElastixFile<3>(l, true);
+ }
+ f.close();
+ if(itkMatRead) {
vtkSmartPointer<vtkMatrix4x4> matrix = vtkSmartPointer<vtkMatrix4x4>::New();
matrix->Identity();
for(int j=0; j<4; j++)
//for image sequences, apply the transform to each images of the sequence
if (mImage->IsTimeSequence())
{
- for (unsigned i = 1 ; i<mImage->GetTransform().size() ; i++)
- {
- mImage->GetTransform()[i]->PreMultiply();
- mImage->GetTransform()[i]->Concatenate(matrix);
- mImage->GetTransform()[i]->Update();
- }
+ for (unsigned i = 1 ; i<mImage->GetTransform().size() ; i++)
+ {
+ mImage->GetTransform()[i]->PreMultiply();
+ mImage->GetTransform()[i]->Concatenate(matrix);
+ mImage->GetTransform()[i]->Update();
+ }
}
}
std::cout << "LastDimIsTime = " << m_LastDimensionIsTime << std::endl;
}
+ // Compute origin based on image corner
+ typename FilterType::OriginPointType origin = input->GetOrigin();
+ for(unsigned int i=0; i<OutputImageType::ImageDimension; i++) {
+ origin[i] -= 0.5 * input->GetSpacing()[i];
+ origin[i] += 0.5 * m_OutputSpacing[i];
+ }
+
// Instance of the transform object to be passed to the resample
// filter. By default, identity transform is applied
filter->SetTransform(m_Transform);
filter->SetSize(m_OutputSize);
filter->SetOutputSpacing(m_OutputSpacing);
- filter->SetOutputOrigin(input->GetOrigin());
+ filter->SetOutputOrigin(origin);
filter->SetDefaultPixelValue(m_DefaultPixelValue);
filter->SetNumberOfThreads(this->GetNumberOfThreads());
filter->SetOutputDirection(input->GetDirection()); // <-- NEEDED if we want to keep orientation (in case of PermutAxes for example)
TARGET_LINK_LIBRARIES(clitkElastixTransformToMatrix clitkCommon )
SET(TOOLS_INSTALL ${TOOLS_INSTALL} clitkElastixTransformToMatrix)
+ WRAP_GGO(clitkMatrixToElastixTransform_GGO_C clitkMatrixToElastixTransform.ggo)
+ ADD_EXECUTABLE(clitkMatrixToElastixTransform clitkMatrixToElastixTransform.cxx ${clitkMatrixToElastixTransform_GGO_C})
+ TARGET_LINK_LIBRARIES(clitkMatrixToElastixTransform clitkCommon )
+ SET(TOOLS_INSTALL ${TOOLS_INSTALL} clitkMatrixToElastixTransform)
+
+ WRAP_GGO(clitkMatrixInverse_GGO_C clitkMatrixInverse.ggo)
+ ADD_EXECUTABLE(clitkMatrixInverse clitkMatrixInverse.cxx ${clitkMatrixInverse_GGO_C})
+ TARGET_LINK_LIBRARIES(clitkMatrixInverse clitkCommon )
+ SET(TOOLS_INSTALL ${TOOLS_INSTALL} clitkMatrixInverse)
WRAP_GGO(clitkSetBackground_GGO_C clitkSetBackground.ggo)
ADD_EXECUTABLE(clitkSetBackground clitkSetBackground.cxx clitkSetBackgroundGenericFilter.cxx ${clitkSetBackground_GGO_C})
//----------------------------------------
void Update();
- template<unsigned int Dimension, class PixelType>
- static
- typename itk::Matrix<double, Dimension+1, Dimension+1>
- createMatrixFromElastixFile(std::vector<std::string> & filename, bool verbose=true);
-
protected:
//----------------------------------------
template <unsigned int Dimension, class PixelType> void UpdateWithDimAndPixelType();
template <unsigned int Dimension, class PixelType> void UpdateWithDimAndVectorType();
- static bool GetElastixValueFromTag(std::ifstream & is, std::string tag, std::string & value);
- static void GetValuesFromValue(const std::string & s,
- std::vector<std::string> & values);
-
//----------------------------------------
// Data members
//----------------------------------------
#include <istream>
#include <iterator>
#include <itkCenteredEuler3DTransform.h>
+#include "clitkElastix.h"
namespace clitk
{
if (m_ArgsInfo.elastix_given) {
std::vector<std::string> s;
for(uint i=0; i<m_ArgsInfo.elastix_given; i++) s.push_back(m_ArgsInfo.elastix_arg[i]);
- matrix = createMatrixFromElastixFile<Dimension,PixelType>(s, m_Verbose);
+ matrix = createMatrixFromElastixFile<Dimension>(s, m_Verbose);
}
else
matrix.SetIdentity();
}
//-------------------------------------------------------------------
-
-
- //-------------------------------------------------------------------
- template<class args_info_type>
- template<unsigned int Dimension, class PixelType>
- typename itk::Matrix<double, Dimension+1, Dimension+1>
- AffineTransformGenericFilter<args_info_type>::createMatrixFromElastixFile(std::vector<std::string> & filename, bool verbose)
- {
- if (Dimension != 3) {
- FATAL("Only 3D yet" << std::endl);
- }
- typename itk::Matrix<double, Dimension+1, Dimension+1> matrix;
-
- itk::CenteredEuler3DTransform<double>::Pointer mat = itk::CenteredEuler3DTransform<double>::New();
- itk::CenteredEuler3DTransform<double>::Pointer previous;
- for(uint j=0; j<filename.size(); j++) {
-
- // Open file
- if (verbose) std::cout << "Read elastix parameters in " << filename[j] << std::endl;
- std::ifstream is;
- clitk::openFileForReading(is, filename[j]);
-
- // Check Transform
- std::string s;
- bool b = GetElastixValueFromTag(is, "Transform ", s);
- if (!b) {
- FATAL("Error must read 'Transform' in " << filename[j] << std::endl);
- }
- if (s != "EulerTransform") {
- FATAL("Sorry only 'EulerTransform'" << std::endl);
- }
-
- // FIXME check
- // (InitialTransformParametersFilename[j] "NoInitialTransform")
-
- // Get CenterOfRotationPoint
- GetElastixValueFromTag(is, "CenterOfRotationPoint ", s); // space is needed
- if (!b) {
- FATAL("Error must read 'CenterOfRotationPoint' in " << filename[j] << std::endl);
- }
- std::vector<std::string> cor;
- GetValuesFromValue(s, cor);
-
- // Get Transformparameters
- GetElastixValueFromTag(is, "TransformParameters ", s); // space is needed
- if (!b) {
- FATAL("Error must read 'TransformParameters' in " << filename[j] << std::endl);
- }
- std::vector<std::string> results;
- GetValuesFromValue(s, results);
-
- // construct a stream from the string
- itk::CenteredEuler3DTransform<double>::ParametersType p;
- p.SetSize(9);
- for(uint i=0; i<3; i++)
- p[i] = atof(results[i].c_str()); // Rotation
- for(uint i=0; i<3; i++)
- p[i+3] = atof(cor[i].c_str()); // Centre of rotation
- for(uint i=0; i<3; i++)
- p[i+6] = atof(results[i+3].c_str()); // Translation
- mat->SetParameters(p);
-
- if (verbose) {
- std::cout << "Rotation (deg) : " << rad2deg(p[0]) << " " << rad2deg(p[1]) << " " << rad2deg(p[2]) << std::endl;
- std::cout << "Center of rot (phy) : " << p[3] << " " << p[4] << " " << p[5] << std::endl;
- std::cout << "Translation (phy) : " << p[6] << " " << p[7] << " " << p[8] << std::endl;
- }
-
- // Compose with previous if needed
- if (j!=0) {
- mat->Compose(previous);
- if (verbose) {
- std::cout << "Composed rotation (deg) : " << rad2deg(mat->GetAngleX()) << " " << rad2deg(mat->GetAngleY()) << " " << rad2deg(mat->GetAngleZ()) << std::endl;
- std::cout << "Composed center of rot (phy) : " << mat->GetCenter() << std::endl;
- std::cout << "Compsoed translation (phy) : " << mat->GetTranslation() << std::endl;
- }
- }
- // previous = mat->Clone(); // ITK4
- previous = itk::CenteredEuler3DTransform<double>::New();
- previous->SetParameters(mat->GetParameters());
- }
-
- mat = previous;
- for(uint i=0; i<3; i++)
- for(uint j=0; j<3; j++)
- matrix[i][j] = mat->GetMatrix()[i][j];
- // Offset is -Rc + t + c
- matrix[0][3] = mat->GetOffset()[0];
- matrix[1][3] = mat->GetOffset()[1];
- matrix[2][3] = mat->GetOffset()[2];
- matrix[3][3] = 1;
-
- return matrix;
- }
-
- //-------------------------------------------------------------------
- template<class args_info_type>
- bool
- AffineTransformGenericFilter<args_info_type>::GetElastixValueFromTag(std::ifstream & is,
- std::string tag,
- std::string & value)
- {
- std::string line;
- is.seekg (0, is.beg);
- while(std::getline(is, line)) {
- unsigned pos = line.find(tag);
- if (pos<line.size()) {
- value=line.substr(pos+tag.size(),line.size()-2);// remove last ')'
- value.erase (std::remove (value.begin(), value.end(), '"'), value.end());
- value.erase (std::remove (value.begin(), value.end(), ')'), value.end());
- return true;
- }
- }
- return false;
- }
- //-------------------------------------------------------------------
-
-
- //-------------------------------------------------------------------
- template<class args_info_type>
- void
- AffineTransformGenericFilter<args_info_type>::GetValuesFromValue(const std::string & s,
- std::vector<std::string> & values)
- {
- std::stringstream strstr(s);
- std::istream_iterator<std::string> it(strstr);
- std::istream_iterator<std::string> end;
- std::vector<std::string> results(it, end);
- values.clear();
- values.resize(results.size());
- for(uint i=0; i<results.size(); i++) values[i] = results[i];
- }
- //-------------------------------------------------------------------
-
} //end clitk
// clitk
#include "clitkElastixTransformToMatrix_ggo.h"
#include "clitkAffineTransformGenericFilter.h"
+#include "clitkElastix.h"
+#include "clitkMatrix.h"
//--------------------------------------------------------------------
int main(int argc, char * argv[])
CLITK_INIT;
// Use static fct of AffineTransformGenericFilter
- typedef clitk::AffineTransformGenericFilter<args_info_clitkElastixTransformToMatrix> FilterType;
std::vector<std::string> l;
l.push_back(args_info.input_arg);
- itk::Matrix<double, 4, 4> m =
- FilterType::createMatrixFromElastixFile<3, int>(l, args_info.verbose_flag);
+ itk::Matrix<double, 4, 4> m = clitk::createMatrixFromElastixFile<3>(l, args_info.verbose_flag);
// Print matrix
std::ofstream os;
clitk::openFileForWriting(os, args_info.output_arg);
- for(unsigned int i=0; i<4; i++) {
- for(unsigned int j=0; j<4; j++)
- os << m[i][j] << " ";
- os << std::endl;
- }
- os.close();
+ os << clitk::Get4x4MatrixDoubleAsString(m, 16);
+ os.close();
return EXIT_SUCCESS;
}// end main
--- /dev/null
+/*=========================================================================
+ Program: vv http://www.creatis.insa-lyon.fr/rio/vv
+
+ Authors belong to:
+ - University of LYON http://www.universite-lyon.fr/
+ - Léon Bérard cancer center http://www.centreleonberard.fr
+ - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr
+
+ This software is distributed WITHOUT ANY WARRANTY; without even
+ the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ PURPOSE. See the copyright notices for more information.
+
+ It is distributed under dual licence
+
+ - BSD See included LICENSE.txt file
+ - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
+===========================================================================**/
+
+// clitk
+#include "clitkMatrixInverse_ggo.h"
+#include "clitkTransformUtilities.h"
+#include "clitkIO.h"
+#include "clitkMatrix.h"
+
+//--------------------------------------------------------------------
+int main(int argc, char * argv[])
+{
+ // Init command line
+ GGO(clitkMatrixInverse, args_info);
+ CLITK_INIT;
+
+ // Read matrix
+ itk::Matrix<double, 4, 4> matrix;
+ try {
+ matrix = clitk::ReadMatrix3D(args_info.input_arg);
+ }
+ catch (itk::ExceptionObject & err) {
+ std::cerr << "Error reading " << args_info.input_arg << std::endl;
+ std::cerr << err.GetDescription() << std::endl;
+ exit(-1);
+ }
+
+ matrix = matrix.GetInverse();
+
+ // Print matrix
+ std::ofstream os;
+ clitk::openFileForWriting(os, args_info.output_arg);
+ os << clitk::Get4x4MatrixDoubleAsString(matrix, 16);
+ os.close();
+
+ return EXIT_SUCCESS;
+}// end main
+
+//--------------------------------------------------------------------
--- /dev/null
+#File clitkMatrixToElastixTransform.ggo
+package "clitkMatrixInverse"
+version "1.0"
+purpose ""
+
+option "config" - "Config file" string optional
+option "input" i "Input matrix filename" string required
+option "output" o "Output matrix filename" string required
--- /dev/null
+/*=========================================================================
+ Program: vv http://www.creatis.insa-lyon.fr/rio/vv
+
+ Authors belong to:
+ - University of LYON http://www.universite-lyon.fr/
+ - Léon Bérard cancer center http://www.centreleonberard.fr
+ - CREATIS CNRS laboratory http://www.creatis.insa-lyon.fr
+
+ This software is distributed WITHOUT ANY WARRANTY; without even
+ the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
+ PURPOSE. See the copyright notices for more information.
+
+ It is distributed under dual licence
+
+ - BSD See included LICENSE.txt file
+ - CeCILL-B http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
+===========================================================================**/
+
+// clitk
+#include "clitkMatrixToElastixTransform_ggo.h"
+#include "clitkTransformUtilities.h"
+#include "clitkIO.h"
+
+// itk
+#include <itkEuler3DTransform.h>
+
+//--------------------------------------------------------------------
+int main(int argc, char * argv[])
+{
+ // Init command line
+ GGO(clitkMatrixToElastixTransform, args_info);
+ CLITK_INIT;
+
+ // Read matrix
+ itk::Matrix<double, 4, 4> matrix;
+ try {
+ matrix = clitk::ReadMatrix3D(args_info.input_arg);
+ }
+ catch (itk::ExceptionObject & err) {
+ std::cerr << "Error reading " << args_info.input_arg << std::endl;
+ std::cerr << err.GetDescription() << std::endl;
+ exit(-1);
+ }
+
+ // Compute parameters from transfer using itk Euler transform
+ itk::Euler3DTransform<double>::CenterType center;
+ center.Fill(0.);
+ if(args_info.center_given==3) {
+ center[0] = args_info.center_arg[0];
+ center[1] = args_info.center_arg[1];
+ center[2] = args_info.center_arg[2];
+ }
+ itk::Euler3DTransform<double>::MatrixType rotMat;
+ itk::Euler3DTransform<double>::OutputVectorType transVec;
+ for(int i=0; i<3; i++) {
+ transVec[i] = matrix[i][3];
+ for(int j=0; j<3; j++)
+ rotMat[i][j] = matrix[i][j];
+ }
+ itk::Euler3DTransform<double>::Pointer euler;
+ euler = itk::Euler3DTransform<double>::New();
+ euler->SetCenter(center);
+ euler->SetOffset(transVec);
+ euler->SetComputeZYX(false);
+ try {
+ euler->SetMatrix(rotMat);
+ }
+ catch (itk::ExceptionObject & err) {
+ std::cerr << "Error reading " << args_info.input_arg << std::endl;
+ std::cerr << err.GetDescription() << std::endl;
+ exit(-1);
+ }
+
+ // Write result
+ std::ofstream out;
+ clitk::openFileForWriting(out, args_info.output_arg);
+ out << "(Transform \"EulerTransform\")" << std::endl;
+ out << "(NumberOfParameters 6)" << std::endl;
+ out << "(TransformParameters ";
+ for(unsigned int i=0; i<6; i++)
+ out << euler->GetParameters()[i] << ' ';
+ out << ')' << std::endl;
+ out << "(InitialTransformParametersFileName \"NoInitialTransform\")" << std::endl;
+ out << "(HowToCombineTransforms \"Compose\")" << std::endl;
+
+ out << "// EulerTransform specific" << std::endl;
+ out << "(CenterOfRotationPoint "<< center[0] << ' ' << center[1] << ' ' << center[2] << ')' << std::endl;
+ out << "(ComputeZYX \"false\")" << std::endl;
+
+ // The rest is commented, up to the user to define it manually
+ out << "// Image specific" << std::endl;
+ out << "// (FixedImageDimension 3)" << std::endl;
+ out << "// (MovingImageDimension 3)" << std::endl;
+ out << "// (FixedInternalImagePixelType \"float\")" << std::endl;
+ out << "// (MovingInternalImagePixelType \"float\")" << std::endl;
+ out << "// (Size 1 1 1)" << std::endl;
+ out << "// (Index 0 0 0)" << std::endl;
+ out << "// (Spacing 1 1 1)" << std::endl;
+ out << "// (Origin -0.5 -0.5 -0.5)" << std::endl;
+ out << "// (Direction 1 0 0 0 1 0 0 0 1)" << std::endl;
+ out << "// (UseDirectionCosines \"true\")" << std::endl << std::endl;
+
+ out << "// ResampleInterpolator specific" << std::endl;
+ out << "// (ResampleInterpolator \"FinalBSplineInterpolator\")" << std::endl;
+ out << "// (FinalBSplineInterpolationOrder 3)" << std::endl << std::endl;
+
+ out << "// Resampler specific" << std::endl;
+ out << "// (Resampler \"DefaultResampler\")" << std::endl;
+ out << "// (DefaultPixelValue 0.000000)" << std::endl;
+ out << "// (ResultImageFormat \"mhd\")" << std::endl;
+ out << "// (ResultImagePixelType \"short\")" << std::endl;
+ out << "// (CompressResultImage \"false\")" << std::endl;
+ out.close();
+
+ return EXIT_SUCCESS;
+}// end main
+
+//--------------------------------------------------------------------
--- /dev/null
+#File clitkMatrixToElastixTransform.ggo
+package "clitkMatrixToElastixTransform"
+version "1.0"
+purpose ""
+
+option "config" - "Config file" string optional
+option "verbose" v "Verbose" flag off
+option "input" i "Input matrix filename" string required
+option "output" o "Output elastix filename" string required
+option "center" - "Rotation center" float no multiple(3)
#include "vvSaveState.h"
#include "vvReadState.h"
#include "clitkConfiguration.h"
+#include "clitkMatrix.h"
// ITK include
#include <itkImage.h>
infoPanel->setNPixel(QString::number(NPixel)+" ("+inputSizeInBytes+")");
transformation = imageSelected->GetTransform()[tSlice]->GetMatrix();
- infoPanel->setTransformation(Get4x4MatrixDoubleAsString(transformation));
+ infoPanel->setTransformation(clitk::Get4x4MatrixDoubleAsString(transformation).c_str());
landmarksPanel->SetCurrentLandmarks(mSlicerManagers[index]->GetLandmarks(),
mSlicerManagers[index]->GetTSlice());
}
//------------------------------------------------------------------------------
-//------------------------------------------------------------------------------
-QString vvMainWindow::Get4x4MatrixDoubleAsString(vtkSmartPointer<vtkMatrix4x4> matrix, const int precision)
-{
- std::ostringstream strmatrix;
-
- // Figure out the number of digits of the integer part of the largest absolute value
- // for each column
- unsigned width[4];
- for (unsigned int j = 0; j < 4; j++){
- double absmax = 0.;
- for (unsigned int i = 0; i < 4; i++)
- absmax = std::max(absmax, vnl_math_abs(matrix->GetElement(i, j)));
- unsigned ndigits = (unsigned)std::max(0.,std::log10(absmax))+1;
- width[j] = precision+ndigits+3;
- }
-
- // Output with correct width, aligned to the right
- for (unsigned int i = 0; i < 4; i++) {
- for (unsigned int j = 0; j < 4; j++) {
- strmatrix.setf(ios::fixed,ios::floatfield);
- strmatrix.precision(precision);
- strmatrix.fill(' ');
- strmatrix.width(width[j]);
- strmatrix << std::right << matrix->GetElement(i, j);
- }
- strmatrix << std::endl;
- }
- QString result = strmatrix.str().c_str();
- return result;
-}
-//------------------------------------------------------------------------------
-
//------------------------------------------------------------------------------
QString vvMainWindow::GetVectorDoubleAsString(std::vector<double> vectorDouble)
{
void SaveCurrentStateAs(const std::string& stateFile);
void ReadSavedStateFile(const std::string& stateFile);
void LinkAllImages();
- QString Get4x4MatrixDoubleAsString(vtkSmartPointer<vtkMatrix4x4> matrix, const int precision=3);
virtual void UpdateCurrentSlicer();
virtual QTabWidget * GetTab();
// clitk
#include "clitkTransformUtilities.h"
+#include "clitkMatrix.h"
// qt
#include <QMessageBox>
for(int i=0; i<4; i++)
// TODO SR and BP: check on the list of transforms and not the first only
mInitialMatrix->SetElement(i,j, mCurrentSlicerManager->GetImage()->GetTransform()[0]->GetMatrix()->GetElement(i,j));
- QString origTransformString = dynamic_cast<vvMainWindow*>(mMainWindow)->Get4x4MatrixDoubleAsString(mInitialMatrix);
+ QString origTransformString(clitk::Get4x4MatrixDoubleAsString(mInitialMatrix).c_str());
transformationLabel->setText(origTransformString);
SetTransform(mInitialMatrix);
if (file.open(QFile::WriteOnly | QFile::Truncate)) {
// TODO SR and BP: check on the list of transforms and not the first only
vtkMatrix4x4* matrix = mCurrentSlicerManager->GetImage()->GetTransform()[0]->GetMatrix();
- QString matrixStr = dynamic_cast<vvMainWindow*>(mMainWindow)->Get4x4MatrixDoubleAsString(matrix,16);
+ QString matrixStr = clitk::Get4x4MatrixDoubleAsString(matrix,16).c_str();
QTextStream out(&file);
out << matrixStr;
}