16 #ifndef __vtkITKTransformConverter_h 17 #define __vtkITKTransformConverter_h 22 #include <vtkImageData.h> 23 #include <vtkPoints.h> 24 #include <vtkThinPlateSplineTransform.h> 25 #include <vtkTransform.h> 28 #include <itkAffineTransform.h> 29 #include <itkBSplineDeformableTransform.h> 30 #include <itkBSplineTransform.h> 31 #include <itkCompositeTransform.h> 32 #include <itkCompositeTransformIOHelper.h> 33 #include <itkDisplacementFieldTransform.h> 34 #include <itkIdentityTransform.h> 35 #include <itkTransformFileWriter.h> 36 #include <itkTransformFileReader.h> 37 #include <itkImageFileReader.h> 38 #include <itkImageFileWriter.h> 39 #include <itkTranslationTransform.h> 40 #include <itkScaleTransform.h> 41 #include <itkTransformFactory.h> 42 #include <itkThinPlateSplineKernelTransform.h> 66 static vtkAbstractTransform*
CreateVTKTransformFromITK(vtkObject* loggerObject,
typename itk::TransformBaseTemplate<T>::Pointer transformItk);
78 itk::Object::Pointer& secondaryTransformItk,
int preferITKv3CompatibleTransforms,
bool initialize =
true);
80 template <
typename T>
static bool SetVTKBSplineFromITKv3Generic(vtkObject* loggerObject, vtkOrientedBSplineTransform* bsplineVtk,
typename itk::TransformBaseTemplate<T>::Pointer warpTransformItk,
typename itk::TransformBaseTemplate<T>::Pointer bulkTransformItk);
83 static bool SetVTKOrientedGridTransformFromITKImage(vtkObject* loggerObject, vtkOrientedGridTransform* grid_Ras,
typename itk::DisplacementFieldTransform< T, 3 >::DisplacementFieldType::Pointer gridImage_Lps);
89 static bool SetVTKLinearTransformFromITK(vtkObject* loggerObject, vtkMatrix4x4* transformVtk_RAS,
typename itk::TransformBaseTemplate<T>::Pointer transformItk_LPS);
90 static bool SetITKLinearTransformFromVTK(vtkObject* loggerObject, itk::Object::Pointer& transformItk_LPS, vtkMatrix4x4* transformVtk_RAS);
93 static bool SetVTKOrientedGridTransformFromITK(vtkObject* loggerObject, vtkOrientedGridTransform* transformVtk_RAS,
typename itk::TransformBaseTemplate<T>::Pointer transformItk_LPS);
96 static bool SetITKv3BSplineFromVTK(vtkObject* loggerObject, itk::Object::Pointer& warpTransformItk, itk::Object::Pointer& bulkTransformItk, vtkOrientedBSplineTransform* bsplineVtk,
bool alwaysAddBulkTransform);
97 static bool SetITKv4BSplineFromVTK(vtkObject* loggerObject, itk::Object::Pointer& warpTransformItk, vtkOrientedBSplineTransform* bsplineVtk);
100 static bool SetVTKThinPlateSplineTransformFromITK(vtkObject* loggerObject, vtkThinPlateSplineTransform* transformVtk_RAS,
typename itk::TransformBaseTemplate<T>::Pointer transformItk_LPS);
102 vtkThinPlateSplineTransform* transformVtk_RAS,
bool initialize =
true);
106 template <
typename BSplineTransformType>
static bool SetVTKBSplineParametersFromITKGeneric(vtkObject* loggerObject, vtkOrientedBSplineTransform* bsplineVtk,
typename itk::TransformBaseTemplate<typename BSplineTransformType::ScalarType>::Pointer warpTransformItk);
107 template <
typename T>
static bool SetVTKBSplineFromITKv4Generic(vtkObject* loggerObject, vtkOrientedBSplineTransform* bsplineVtk,
typename itk::TransformBaseTemplate<T>::Pointer warpTransformItk);
109 template <
typename BSplineTransformType>
static bool SetITKBSplineParametersFromVTKGeneric(vtkObject* loggerObject,
typename itk::Transform< typename BSplineTransformType::ScalarType,VTKDimension,VTKDimension>::Pointer& warpTransformItk, vtkOrientedBSplineTransform* bsplineVtk);
110 template <
typename T>
static bool SetITKv3BSplineFromVTKGeneric(vtkObject* loggerObject,
typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& warpTransformItk,
typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& bulkTransformItk, vtkOrientedBSplineTransform* bsplineVtk,
bool alwaysAddBulkTransform);
111 template <
typename T>
static bool SetITKv4BSplineFromVTKGeneric(vtkObject* loggerObject,
typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& warpTransformItk, vtkOrientedBSplineTransform* bsplineVtk);
118 itk::TransformFactory<InverseDisplacementFieldTransformFloatType>::RegisterTransform();
119 itk::TransformFactory<InverseDisplacementFieldTransformDoubleType>::RegisterTransform();
121 itk::TransformFactory<InverseBSplineTransformFloatITKv3Type>::RegisterTransform();
122 itk::TransformFactory<InverseBSplineTransformFloatITKv4Type>::RegisterTransform();
123 itk::TransformFactory<InverseBSplineTransformDoubleITKv3Type>::RegisterTransform();
124 itk::TransformFactory<InverseBSplineTransformDoubleITKv4Type>::RegisterTransform();
126 itk::TransformFactory<InverseThinPlateSplineTransformFloatType>::RegisterTransform();
127 itk::TransformFactory<InverseThinPlateSplineTransformDoubleType>::RegisterTransform();
129 typedef itk::ThinPlateSplineKernelTransform<float,3> ThinPlateSplineTransformFloatType;
133 itk::TransformFactory<ThinPlateSplineTransformFloatType>::RegisterTransform();
134 itk::TransformFactory<ThinPlateSplineTransformDoubleType>::RegisterTransform();
141 vtkMatrix4x4* transformVtk_RAS,
142 typename itk::TransformBaseTemplate<T>::Pointer transformItk_LPS)
145 typedef itk::MatrixOffsetTransformBase<T,D,D> LinearTransformType;
146 typedef itk::ScaleTransform<T, D> ScaleTransformType;
147 typedef itk::TranslationTransform<T, D> TranslateTransformType;
149 vtkSmartPointer<vtkMatrix4x4> transformVtk_LPS = vtkSmartPointer<vtkMatrix4x4>::New();
151 bool convertedToVtkMatrix=
false;
153 std::string itkTransformClassName = transformItk_LPS->GetNameOfClass();
172 if (itkTransformClassName.find(
"AffineTransform" ) != std::string::npos ||
173 itkTransformClassName ==
"MatrixOffsetTransformBase" ||
174 itkTransformClassName ==
"Rigid3DTransform" ||
175 itkTransformClassName ==
"Euler3DTransform" ||
176 itkTransformClassName ==
"CenteredEuler3DTransform" ||
177 itkTransformClassName ==
"QuaternionRigidTransform" ||
178 itkTransformClassName ==
"VersorTransform" ||
179 itkTransformClassName ==
"VersorRigid3DTransform" ||
180 itkTransformClassName ==
"ScaleSkewVersor3DTransform" ||
181 itkTransformClassName ==
"ScaleVersor3DTransform" ||
182 itkTransformClassName ==
"Similarity3DTransform" ||
183 itkTransformClassName ==
"ScaleTransform" ||
184 itkTransformClassName ==
"ScaleLogarithmicTransform")
186 typename LinearTransformType::Pointer dlt
187 =
static_cast<LinearTransformType*
>( transformItk_LPS.GetPointer() );
188 convertedToVtkMatrix=
true;
189 for (
unsigned int i=0; i < D; i++)
191 for (
unsigned int j=0; j < D; j++)
193 transformVtk_LPS->SetElement(i, j, dlt->GetMatrix()[i][j]);
195 transformVtk_LPS->SetElement(i, D, dlt->GetOffset()[i]);
200 if (itkTransformClassName ==
"IdentityTransform")
203 convertedToVtkMatrix=
true;
207 if (itkTransformClassName ==
"ScaleTransform")
209 typename ScaleTransformType::Pointer dst
210 =
static_cast<ScaleTransformType*
>( transformItk_LPS.GetPointer() );
211 convertedToVtkMatrix=
true;
212 for (
unsigned int i=0; i < D; i++)
214 transformVtk_LPS->SetElement(i, i, dst->GetScale()[i]);
219 if (itkTransformClassName ==
"TranslationTransform")
221 typename TranslateTransformType::Pointer dtt
222 =
static_cast<TranslateTransformType*
>( transformItk_LPS.GetPointer());
223 convertedToVtkMatrix=
true;
224 for (
unsigned int i=0; i < D; i++)
226 transformVtk_LPS->SetElement(i, D, dtt->GetOffset()[i]);
235 vtkSmartPointer<vtkMatrix4x4> lps2ras = vtkSmartPointer<vtkMatrix4x4>::New();
236 lps2ras->SetElement(0,0,-1);
237 lps2ras->SetElement(1,1,-1);
238 vtkMatrix4x4* ras2lps = lps2ras;
240 vtkMatrix4x4::Multiply4x4(lps2ras, transformVtk_LPS, transformVtk_LPS);
241 vtkMatrix4x4::Multiply4x4(transformVtk_LPS, ras2lps, transformVtk_RAS);
243 return convertedToVtkMatrix;
251 if (transformVtk_RAS==
nullptr)
253 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::SetITKLinearTransformFromVTK failed: invalid input transform");
257 vtkSmartPointer<vtkMatrix4x4> lps2ras = vtkSmartPointer<vtkMatrix4x4>::New();
258 lps2ras->SetElement(0,0,-1);
259 lps2ras->SetElement(1,1,-1);
260 vtkMatrix4x4* ras2lps = lps2ras;
266 vtkSmartPointer<vtkMatrix4x4> vtkmat = vtkSmartPointer<vtkMatrix4x4>::New();
268 vtkMatrix4x4::Multiply4x4(ras2lps, transformVtk_RAS, vtkmat);
269 vtkMatrix4x4::Multiply4x4(vtkmat, lps2ras, vtkmat);
271 typedef AffineTransformType::MatrixType MatrixType;
272 typedef AffineTransformType::OutputVectorType OffsetType;
275 OffsetType itkoffset;
281 itkmat[i][j] = vtkmat->GetElement(i, j);
286 AffineTransformType::Pointer affine = AffineTransformType::New();
287 affine->SetMatrix(itkmat);
288 affine->SetOffset(itkoffset);
290 transformItk_LPS = affine;
297 static double identity[16] = {1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1};
300 for (i = 0; i < 4; i++)
302 for (j = 0; j < 4; j++)
304 if (matrix->GetElement(i,j) != identity[4*i+j])
314 template <
typename BSplineTransformType>
316 vtkObject* loggerObject,
317 vtkOrientedBSplineTransform* bsplineVtk,
318 typename itk::TransformBaseTemplate<typename BSplineTransformType::ScalarType>::Pointer warpTransformItk)
323 typedef typename BSplineTransformType::ScalarType T;
324 if (bsplineVtk==
nullptr)
326 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetVTKBSplineFromITKv4 failed: bsplineVtk is invalid");
329 bool isDoublePrecisionInput=
true;
330 if (
sizeof(T)==
sizeof(
float))
332 isDoublePrecisionInput=
false;
334 else if (
sizeof(T)==
sizeof(
double))
336 isDoublePrecisionInput=
true;
340 vtkErrorWithObjectMacro(loggerObject,
"Unsupported scalar type in BSpline transform file (only float and double are supported)");
344 typename BSplineTransformType::Pointer bsplineItk = BSplineTransformType::New();
345 std::string warpTransformItkName = warpTransformItk->GetNameOfClass();
346 std::string requestedWarpTransformItkName = bsplineItk->GetNameOfClass();
347 if (warpTransformItkName != requestedWarpTransformItkName)
351 if (warpTransformItk->GetOutputSpaceDimension() !=
VTKDimension)
353 vtkErrorWithObjectMacro(loggerObject,
"Unsupported number of dimensions in BSpline transform file (expected = " 354 <<
VTKDimension <<
", actual = " << warpTransformItk->GetOutputSpaceDimension() <<
")");
357 bsplineItk =
static_cast< BSplineTransformType*
>( warpTransformItk.GetPointer() );
365 const typename BSplineTransformType::CoefficientImageArray coefficientImages =
366 bsplineItk->GetCoefficientImages();
370 typename BSplineTransformType::MeshSizeType meshSize =
371 coefficientImages[0]->GetLargestPossibleRegion().GetSize();
374 typename BSplineTransformType::OriginType origin =
375 coefficientImages[0]->GetOrigin();
378 typename BSplineTransformType::SpacingType spacing =
379 coefficientImages[0]->GetSpacing();
382 typename BSplineTransformType::DirectionType direction =
383 coefficientImages[0]->GetDirection();
385 vtkNew<vtkMatrix4x4> gridDirectionMatrix_LPS;
388 for (
unsigned int column=0; column<
VTKDimension; column++)
390 gridDirectionMatrix_LPS->SetElement(row,column,direction[row][column]);
395 bsplineVtk->SetBorderModeToZero();
397 vtkNew<vtkImageData> bsplineCoefficients;
399 bsplineCoefficients->SetExtent(0, meshSize[0]-1, 0, meshSize[1]-1, 0, meshSize[2]-1);
400 bsplineCoefficients->SetSpacing(spacing[0], spacing[1], spacing[2]);
403 vtkNew<vtkMatrix4x4> lpsToRas;
404 lpsToRas->SetElement(0,0,-1);
405 lpsToRas->SetElement(1,1,-1);
407 vtkNew<vtkMatrix4x4> rasToLps;
408 rasToLps->SetElement(0,0,-1);
409 rasToLps->SetElement(1,1,-1);
411 vtkNew<vtkMatrix4x4> gridDirectionMatrix_RAS;
412 vtkMatrix4x4::Multiply4x4(
413 lpsToRas.GetPointer(),
414 gridDirectionMatrix_LPS.GetPointer(),
415 gridDirectionMatrix_RAS.GetPointer());
416 bsplineVtk->SetGridDirectionMatrix(gridDirectionMatrix_RAS.GetPointer());
419 double gridOrigin_RAS[3]={-origin[0], -origin[1], origin[2]};
420 bsplineCoefficients->SetOrigin(gridOrigin_RAS);
422 int bsplineCoefficientsScalarType=VTK_FLOAT;
423 if (isDoublePrecisionInput)
425 bsplineCoefficientsScalarType=VTK_DOUBLE;
428 bsplineCoefficients->AllocateScalars(bsplineCoefficientsScalarType, 3);
430 const unsigned int expectedNumberOfVectors = meshSize[0]*meshSize[1]*meshSize[2];
431 const unsigned int expectedNumberOfParameters = expectedNumberOfVectors*
VTKDimension;
432 const unsigned int actualNumberOfParameters = bsplineItk->GetNumberOfParameters();
434 if( actualNumberOfParameters != expectedNumberOfParameters )
436 vtkErrorWithObjectMacro(loggerObject,
"Mismatch in number of BSpline parameters in the transform file and the MRML node");
439 const T* itkBSplineParams_LPS =
static_cast<const T*
>(bsplineItk->GetParameters().data_block());
440 T* vtkBSplineParams_RAS=
static_cast<T*
>(bsplineCoefficients->GetScalarPointer());
441 for (
unsigned int i=0; i<expectedNumberOfVectors; i++)
443 *(vtkBSplineParams_RAS++) = - (*(itkBSplineParams_LPS ));
444 *(vtkBSplineParams_RAS++) = - (*(itkBSplineParams_LPS+expectedNumberOfVectors ));
445 *(vtkBSplineParams_RAS++) = (*(itkBSplineParams_LPS+expectedNumberOfVectors*2));
446 itkBSplineParams_LPS++;
448 bsplineVtk->SetCoefficientData(bsplineCoefficients.GetPointer());
456 vtkOrientedBSplineTransform* bsplineVtk,
457 typename itk::TransformBaseTemplate<T>::Pointer warpTransformItk,
typename itk::TransformBaseTemplate<T>::Pointer bulkTransformItk)
459 if (bsplineVtk==
nullptr)
461 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetVTKBSplineFromITK failed: bsplineVtk is invalid");
465 bool inverse =
false;
477 vtkDebugWithObjectMacro(loggerObject,
"Not an ITKv3 BSpline transform");
482 if( bulkTransformItk )
484 std::string bulkTransformItkTransformName = bulkTransformItk->GetNameOfClass();
486 typedef itk::AffineTransform<T,3> BulkTransformType;
488 if (bulkTransformItkTransformName ==
"AffineTransform")
490 BulkTransformType* bulkItkAffine =
static_cast<BulkTransformType*
> (bulkTransformItk.GetPointer());
491 vtkNew<vtkMatrix4x4> bulkMatrix_LPS;
496 bulkMatrix_LPS->SetElement(i,j, bulkItkAffine->GetMatrix()[i][j]);
498 bulkMatrix_LPS->SetElement(i,
VTKDimension, bulkItkAffine->GetOffset()[i]);
500 vtkNew<vtkMatrix4x4> lpsToRas;
501 lpsToRas->SetElement(0,0,-1);
502 lpsToRas->SetElement(1,1,-1);
503 vtkNew<vtkMatrix4x4> rasToLps;
504 rasToLps->SetElement(0,0,-1);
505 rasToLps->SetElement(1,1,-1);
506 vtkNew<vtkMatrix4x4> bulkMatrix_RAS;
507 vtkMatrix4x4::Multiply4x4(lpsToRas.GetPointer(), bulkMatrix_LPS.GetPointer(), bulkMatrix_RAS.GetPointer());
508 vtkMatrix4x4::Multiply4x4(bulkMatrix_RAS.GetPointer(), rasToLps.GetPointer(), bulkMatrix_RAS.GetPointer());
509 bsplineVtk->SetBulkTransformMatrix(bulkMatrix_RAS.GetPointer());
511 else if (bulkTransformItkTransformName ==
"IdentityTransform")
517 vtkErrorWithObjectMacro(loggerObject,
"Cannot read the 2nd transform in BSplineTransform (expected AffineTransform_double_3_3 or IdentityTransform)" );
524 bsplineVtk->Inverse();
533 vtkOrientedBSplineTransform* bsplineVtk,
typename itk::TransformBaseTemplate<T>::Pointer warpTransformItk)
535 bool inverse =
false;
547 vtkDebugWithObjectMacro(loggerObject,
"Not an ITKv4 BSpline transform");
552 bsplineVtk->Inverse();
559 typename itk::Transform< typename BSplineTransformType::ScalarType,VTKDimension,VTKDimension>::Pointer& warpTransformItk, vtkOrientedBSplineTransform* bsplineVtk)
561 typedef typename BSplineTransformType::ScalarType T;
562 if (bsplineVtk==
nullptr)
564 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetITKBSplineFromVTK failed: bsplineVtk is invalid");
567 vtkImageData* bsplineCoefficients_RAS=bsplineVtk->GetCoefficientData();
568 if (bsplineCoefficients_RAS==
nullptr)
570 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file: coefficients are not specified");
574 typename BSplineTransformType::Pointer bsplineItk = BSplineTransformType::New();
575 warpTransformItk = bsplineItk;
582 typename BSplineTransformType::FixedParametersType transformFixedParamsItk;
584 transformFixedParamsItk.SetSize(numberOfFixedParameters);
586 int *gridExtent=bsplineCoefficients_RAS->GetExtent();
587 int gridSize[3]={gridExtent[1]-gridExtent[0]+1, gridExtent[3]-gridExtent[2]+1, gridExtent[5]-gridExtent[4]+1};
588 transformFixedParamsItk[0]=gridSize[0];
589 transformFixedParamsItk[1]=gridSize[1];
590 transformFixedParamsItk[2]=gridSize[2];
592 double* gridOrigin_RAS=bsplineCoefficients_RAS->GetOrigin();
593 double gridOrigin_LPS[3]={-gridOrigin_RAS[0], -gridOrigin_RAS[1], gridOrigin_RAS[2]};
594 transformFixedParamsItk[3]=gridOrigin_LPS[0];
595 transformFixedParamsItk[4]=gridOrigin_LPS[1];
596 transformFixedParamsItk[5]=gridOrigin_LPS[2];
598 double* gridSpacing=bsplineCoefficients_RAS->GetSpacing();
599 transformFixedParamsItk[6]=gridSpacing[0];
600 transformFixedParamsItk[7]=gridSpacing[1];
601 transformFixedParamsItk[8]=gridSpacing[2];
603 vtkNew<vtkMatrix4x4> gridDirectionMatrix_RAS;
604 if (bsplineVtk->GetGridDirectionMatrix()!=
nullptr)
606 gridDirectionMatrix_RAS->DeepCopy(bsplineVtk->GetGridDirectionMatrix());
608 vtkNew<vtkMatrix4x4> lpsToRas;
609 lpsToRas->SetElement(0,0,-1);
610 lpsToRas->SetElement(1,1,-1);
611 vtkNew<vtkMatrix4x4> rasToLps;
612 rasToLps->SetElement(0,0,-1);
613 rasToLps->SetElement(1,1,-1);
614 vtkNew<vtkMatrix4x4> gridDirectionMatrix_LPS;
615 vtkMatrix4x4::Multiply4x4(rasToLps.GetPointer(), gridDirectionMatrix_RAS.GetPointer(), gridDirectionMatrix_LPS.GetPointer());
619 for (
unsigned int column=0; column<
VTKDimension; column++)
621 transformFixedParamsItk[fpIndex++]=gridDirectionMatrix_LPS->GetElement(row,column);
625 bsplineItk->SetFixedParameters(transformFixedParamsItk);
629 const unsigned int expectedNumberOfVectors = gridSize[0]*gridSize[1]*gridSize[2];
630 const unsigned int expectedNumberOfParameters = expectedNumberOfVectors*
VTKDimension;
631 if( bsplineItk->GetNumberOfParameters() != expectedNumberOfParameters )
633 vtkErrorWithObjectMacro(loggerObject,
"Mismatch in number of BSpline parameters in the ITK transform and the VTK transform");
637 typename BSplineTransformType::ParametersType transformParamsItk(expectedNumberOfParameters);
638 T* itkBSplineParams_LPS =
static_cast<T*
>(transformParamsItk.data_block());
639 T* vtkBSplineParams_RAS=
static_cast<T*
>(bsplineCoefficients_RAS->GetScalarPointer());
640 double coefficientScale = bsplineVtk->GetDisplacementScale();
641 for (
unsigned int i=0; i<expectedNumberOfVectors; i++)
643 *(itkBSplineParams_LPS ) = -coefficientScale * (*(vtkBSplineParams_RAS++));
644 *(itkBSplineParams_LPS+expectedNumberOfVectors ) = -coefficientScale * (*(vtkBSplineParams_RAS++));
645 *(itkBSplineParams_LPS+expectedNumberOfVectors*2) = coefficientScale * (*(vtkBSplineParams_RAS++));
646 itkBSplineParams_LPS++;
649 bsplineItk->SetParameters(transformParamsItk);
655 typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& warpTransformItk,
656 typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& bulkTransformItk,
657 vtkOrientedBSplineTransform* bsplineVtk,
bool alwaysAddBulkTransform)
659 if (bsplineVtk==
nullptr)
661 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetITKBSplineFromVTK failed: bsplineVtk is invalid");
665 bsplineVtk->Update();
666 bool itkTransformSetSuccessfully =
false;
667 if (bsplineVtk->GetInverseFlag())
669 itkTransformSetSuccessfully = SetITKBSplineParametersFromVTKGeneric< itk::InverseBSplineDeformableTransform< T, VTKDimension, VTKDimension > >(loggerObject, warpTransformItk, bsplineVtk);
673 itkTransformSetSuccessfully = SetITKBSplineParametersFromVTKGeneric< itk::BSplineDeformableTransform< T, VTKDimension, VTKDimension > >(loggerObject, warpTransformItk, bsplineVtk);
675 if (!itkTransformSetSuccessfully)
677 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetITKBSplineFromVTK failed: cannot determine BSpline parameters");
681 vtkMatrix4x4* bulkMatrix_RAS=bsplineVtk->GetBulkTransformMatrix();
682 if (bulkMatrix_RAS || alwaysAddBulkTransform)
684 vtkNew<vtkMatrix4x4> lpsToRas;
685 lpsToRas->SetElement(0,0,-1);
686 lpsToRas->SetElement(1,1,-1);
687 vtkNew<vtkMatrix4x4> rasToLps;
688 rasToLps->SetElement(0,0,-1);
689 rasToLps->SetElement(1,1,-1);
690 vtkNew<vtkMatrix4x4> bulkMatrix_LPS;
693 if (bulkMatrix_RAS!=
nullptr)
695 vtkMatrix4x4::Multiply4x4(rasToLps.GetPointer(), bulkMatrix_RAS, bulkMatrix_LPS.GetPointer());
696 vtkMatrix4x4::Multiply4x4(bulkMatrix_LPS.GetPointer(), lpsToRas.GetPointer(), bulkMatrix_LPS.GetPointer());
698 typedef itk::AffineTransform<T,VTKDimension> BulkTransformType;
699 typename BulkTransformType::Pointer affineItk = BulkTransformType::New();
700 bulkTransformItk = affineItk;
702 typename BulkTransformType::MatrixType affineMatrix;
703 typename BulkTransformType::OffsetType affineOffset;
708 affineMatrix[i][j]=bulkMatrix_LPS->GetElement(i,j);
710 affineOffset[i]=bulkMatrix_LPS->GetElement(i,
VTKDimension);
713 affineItk->SetMatrix(affineMatrix);
714 affineItk->SetOffset(affineOffset);
718 bulkTransformItk=
nullptr;
726 typename itk::Transform<T,VTKDimension,VTKDimension>::Pointer& warpTransformItk,
727 vtkOrientedBSplineTransform* bsplineVtk)
730 bsplineVtk->Update();
731 bool itkTransformSetSuccessfully =
false;
732 if (bsplineVtk->GetInverseFlag())
734 itkTransformSetSuccessfully = SetITKBSplineParametersFromVTKGeneric< itk::InverseBSplineTransform< T, VTKDimension, VTKDimension > >(loggerObject, warpTransformItk, bsplineVtk);
738 itkTransformSetSuccessfully = SetITKBSplineParametersFromVTKGeneric< itk::BSplineTransform< T, VTKDimension, VTKDimension > >(loggerObject, warpTransformItk, bsplineVtk);
740 if (!itkTransformSetSuccessfully)
742 vtkErrorWithObjectMacro(loggerObject,
"vtkMRMLTransformStorageNode::SetITKv4BSplineFromVTKGeneric failed: cannot determine BSpline parameters");
750 itk::Object::Pointer& bulkTransformItk, vtkOrientedBSplineTransform* bsplineVtk,
bool alwaysAddBulkTransform)
752 if (bsplineVtk==
nullptr)
754 vtkErrorWithObjectMacro(loggerObject,
"Cannot retrieve BSpline transform from node");
758 vtkImageData* bsplineCoefficients=bsplineVtk->GetCoefficientData();
760 if (bsplineCoefficients==
nullptr)
762 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file: coefficients are not specified");
766 if (bsplineCoefficients->GetScalarType()==VTK_FLOAT)
768 typedef itk::Transform<float, VTKDimension, VTKDimension > ITKTransformType;
769 ITKTransformType::Pointer floatWarpTransformItk;
770 ITKTransformType::Pointer floatBulkTransformItk;
771 if (!SetITKv3BSplineFromVTKGeneric<float>(loggerObject, floatWarpTransformItk, floatBulkTransformItk, bsplineVtk, alwaysAddBulkTransform))
773 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file");
776 warpTransformItk = floatWarpTransformItk.GetPointer();
777 bulkTransformItk = floatBulkTransformItk.GetPointer();
779 else if (bsplineCoefficients->GetScalarType()==VTK_DOUBLE)
781 typedef itk::Transform<double, VTKDimension, VTKDimension > ITKTransformType;
782 ITKTransformType::Pointer doubleWarpTransformItk;
783 ITKTransformType::Pointer doubleBulkTransformItk;
784 if (!SetITKv3BSplineFromVTKGeneric<double>(loggerObject, doubleWarpTransformItk, doubleBulkTransformItk, bsplineVtk, alwaysAddBulkTransform))
786 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file");
789 warpTransformItk = doubleWarpTransformItk;
790 bulkTransformItk = doubleBulkTransformItk;
794 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file: only float and double coefficient types are supported");
804 if (bsplineVtk==
nullptr)
806 vtkErrorWithObjectMacro(loggerObject,
"Cannot retrieve BSpline transform from node");
810 vtkImageData* bsplineCoefficients=bsplineVtk->GetCoefficientData();
812 if (bsplineCoefficients==
nullptr)
814 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file: coefficients are not specified");
818 if (bsplineCoefficients->GetScalarType()==VTK_FLOAT)
820 typedef itk::Transform<float, VTKDimension, VTKDimension > ITKTransformType;
821 ITKTransformType::Pointer floatWarpTransformItk;
822 if (!SetITKv4BSplineFromVTKGeneric<float>(loggerObject, floatWarpTransformItk, bsplineVtk))
824 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file");
827 warpTransformItk = floatWarpTransformItk.GetPointer();
829 else if (bsplineCoefficients->GetScalarType()==VTK_DOUBLE)
831 typedef itk::Transform<double, VTKDimension, VTKDimension > ITKTransformType;
832 ITKTransformType::Pointer doubleWarpTransformItk;
833 if (!SetITKv4BSplineFromVTKGeneric<double>(loggerObject, doubleWarpTransformItk, bsplineVtk))
835 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file");
838 warpTransformItk = doubleWarpTransformItk;
842 vtkErrorWithObjectMacro(loggerObject,
"Cannot write BSpline transform to file: only float and double coefficient types are supported");
853 typedef itk::DisplacementFieldTransform< T, 3 > DisplacementFieldTransformType;
856 if (!transformItk_LPS)
858 vtkErrorWithObjectMacro(loggerObject,
"Cannot set VTK oriented grid transform from ITK: the input transform is nullptr");
861 if (transformItk_LPS->GetOutputSpaceDimension() !=
VTKDimension)
863 vtkErrorWithObjectMacro(loggerObject,
"Unsupported number of dimensions in oriented grid transform file (expected = " 864 <<
VTKDimension <<
", actual = " << transformItk_LPS->GetOutputSpaceDimension() <<
")");
868 std::string transformItkClassName = transformItk_LPS->GetNameOfClass();
870 bool inverse =
false;
871 typename DisplacementFieldTransformType::DisplacementFieldType* gridImageItk_Lps =
nullptr;
872 if (transformItkClassName ==
"InverseDisplacementFieldTransform")
874 DisplacementFieldTransformType* inverseDisplacementFieldTransform =
static_cast<InverseDisplacementFieldTransformType*
>( transformItk_LPS.GetPointer() );
876 gridImageItk_Lps = inverseDisplacementFieldTransform->GetDisplacementField();
878 else if (transformItkClassName ==
"DisplacementFieldTransform")
880 DisplacementFieldTransformType* displacementFieldTransform =
static_cast<DisplacementFieldTransformType*
>( transformItk_LPS.GetPointer() );
882 gridImageItk_Lps = displacementFieldTransform->GetDisplacementField();
886 vtkDebugWithObjectMacro(loggerObject,
"Not a grid transform");
889 if (!SetVTKOrientedGridTransformFromITKImage<T>(loggerObject, transformVtk_RAS, gridImageItk_Lps))
895 transformVtk_RAS->Inverse();
903 GridImageDoubleType::Pointer gridImageItk_Lps;
906 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::SetITKOrientedGridTransformFromVTK failed: input transform is invalid");
910 transformVtk_RAS->Update();
911 if (transformVtk_RAS->GetInverseFlag())
914 gridTransformItk->SetDisplacementField(gridImageItk_Lps);
915 transformItk_LPS = gridTransformItk;
919 DisplacementFieldTransformDoubleType::Pointer gridTransformItk = DisplacementFieldTransformDoubleType::New();
920 gridTransformItk->SetDisplacementField(gridImageItk_Lps);
921 transformItk_LPS = gridTransformItk;
930 typedef itk::DisplacementFieldTransform< T, 3 > DisplacementFieldTransformType;
931 typedef typename DisplacementFieldTransformType::DisplacementFieldType GridImageType;
933 vtkNew<vtkImageData> gridImage_Ras;
936 gridImage_Ras->SetOrigin( -gridImage_Lps->GetOrigin()[0], -gridImage_Lps->GetOrigin()[1], gridImage_Lps->GetOrigin()[2] );
939 gridImage_Ras->SetSpacing( gridImage_Lps->GetSpacing()[0], gridImage_Lps->GetSpacing()[1], gridImage_Lps->GetSpacing()[2] );
942 vtkNew<vtkMatrix4x4> gridDirectionMatrix_LPS;
945 for (
unsigned int column=0; column<
VTKDimension; column++)
947 gridDirectionMatrix_LPS->SetElement(row,column,gridImage_Lps->GetDirection()(row,column));
950 vtkNew<vtkMatrix4x4> lpsToRas;
951 lpsToRas->SetElement(0,0,-1);
952 lpsToRas->SetElement(1,1,-1);
953 vtkNew<vtkMatrix4x4> gridDirectionMatrix_RAS;
954 vtkMatrix4x4::Multiply4x4(lpsToRas.GetPointer(), gridDirectionMatrix_LPS.GetPointer(), gridDirectionMatrix_RAS.GetPointer());
955 grid_Ras->SetGridDirectionMatrix(gridDirectionMatrix_RAS.GetPointer());
958 typename GridImageType::SizeType size = gridImage_Lps->GetBufferedRegion().GetSize();
959 gridImage_Ras->SetDimensions( size[0], size[1], size[2] );
960 unsigned int numberOfScalarComponents = GridImageType::PixelType::Dimension;
963 vtkErrorWithObjectMacro(loggerObject,
"Cannot load grid transform: the input displacement field expected to contain " 964 <<
VTKDimension <<
" components but it actually contains " << numberOfScalarComponents );
967 gridImage_Ras->AllocateScalars(VTK_DOUBLE, 3);
969 double* displacementVectors_Ras =
reinterpret_cast<double*
>(gridImage_Ras->GetScalarPointer());
970 itk::ImageRegionConstIterator<GridImageType> inputIt(gridImage_Lps, gridImage_Lps->GetRequestedRegion());
972 while( !inputIt.IsAtEnd() )
974 typename GridImageType::PixelType displacementVectorLps=inputIt.Get();
975 *(displacementVectors_Ras++) = -displacementVectorLps[0];
976 *(displacementVectors_Ras++) = -displacementVectorLps[1];
977 *(displacementVectors_Ras++) = displacementVectorLps[2];
981 grid_Ras->SetDisplacementGridData( gridImage_Ras.GetPointer() );
984 grid_Ras->SetInterpolationModeToCubic();
992 if (grid_Ras==
nullptr)
994 vtkErrorWithObjectMacro(loggerObject,
"Cannot save grid transform: the input vtkOrientedGridTransform is invalid");
1001 vtkImageData* gridImage_Ras = grid_Ras->GetDisplacementGrid();
1002 if (gridImage_Ras==
nullptr)
1004 vtkErrorWithObjectMacro(loggerObject,
"Cannot save grid transform: the input vtkOrientedGridTransform does not contain a valid displacement grid");
1007 if (gridImage_Ras->GetNumberOfScalarComponents() !=
static_cast<int>(
VTKDimension))
1009 vtkErrorWithObjectMacro(loggerObject,
"Cannot save grid transform: the input vtkOrientedGridTransform expected to contain " 1010 <<
VTKDimension <<
" components but it actually contains " << gridImage_Ras->GetNumberOfScalarComponents() );
1014 gridImage_Lps = GridImageDoubleType::New();
1017 double* origin_Ras = gridImage_Ras->GetOrigin();
1018 double origin_Lps[3] = { -origin_Ras[0], -origin_Ras[1], origin_Ras[2] };
1019 gridImage_Lps->SetOrigin( origin_Lps );
1022 double* spacing = gridImage_Ras->GetSpacing();
1024 gridImage_Lps->SetSpacing( spacing );
1027 vtkNew<vtkMatrix4x4> gridDirectionMatrix_Ras;
1028 if (grid_Ras->GetGridDirectionMatrix()!=
nullptr)
1030 gridDirectionMatrix_Ras->DeepCopy(grid_Ras->GetGridDirectionMatrix());
1032 vtkNew<vtkMatrix4x4> rasToLps;
1033 rasToLps->SetElement(0,0,-1);
1034 rasToLps->SetElement(1,1,-1);
1035 vtkNew<vtkMatrix4x4> gridDirectionMatrix_Lps;
1036 vtkMatrix4x4::Multiply4x4(rasToLps.GetPointer(), gridDirectionMatrix_Ras.GetPointer(), gridDirectionMatrix_Lps.GetPointer());
1037 GridImageDoubleType::DirectionType gridDirectionMatrixItk_Lps;
1040 for (
unsigned int column=0; column<
VTKDimension; column++)
1042 gridDirectionMatrixItk_Lps(row,column) = gridDirectionMatrix_Lps->GetElement(row,column);
1045 gridImage_Lps->SetDirection(gridDirectionMatrixItk_Lps);
1048 GridImageDoubleType::IndexType start;
1049 start[0] = start[1] = start[2] = 0;
1050 int* Nijk = gridImage_Ras->GetDimensions();
1051 GridImageDoubleType::SizeType size;
1052 size[0] = Nijk[0]; size[1] = Nijk[1]; size[2] = Nijk[2];
1053 GridImageDoubleType::RegionType region;
1054 region.SetSize( size );
1055 region.SetIndex( start );
1056 gridImage_Lps->SetRegions( region );
1057 gridImage_Lps->Allocate();
1058 itk::ImageRegionIterator<GridImageDoubleType> gridImageIt_Lps(gridImage_Lps, region);
1059 gridImageIt_Lps.GoToBegin();
1060 GridImageDoubleType::PixelType displacementVectorLps;
1061 double displacementScale = grid_Ras->GetDisplacementScale();
1062 double displacementShift = grid_Ras->GetDisplacementShift();
1064 if (gridImage_Ras->GetScalarType()==VTK_DOUBLE)
1066 double* displacementVectors_Ras =
reinterpret_cast<double*
>(gridImage_Ras->GetScalarPointer());
1067 while( !gridImageIt_Lps.IsAtEnd() )
1069 displacementVectorLps[0] = -( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1070 displacementVectorLps[1] = -( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1071 displacementVectorLps[2] = ( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1072 gridImageIt_Lps.Set(displacementVectorLps);
1076 else if (gridImage_Ras->GetScalarType()==VTK_FLOAT)
1078 float* displacementVectors_Ras =
reinterpret_cast<float*
>(gridImage_Ras->GetScalarPointer());
1079 while( !gridImageIt_Lps.IsAtEnd() )
1081 displacementVectorLps[0] = -( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1082 displacementVectorLps[1] = -( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1083 displacementVectorLps[2] = ( displacementScale * (*(displacementVectors_Ras++)) + displacementShift );
1084 gridImageIt_Lps.Set(displacementVectorLps);
1090 vtkErrorWithObjectMacro(loggerObject,
"Cannot save grid transform: only float and double scalar types are supported");
1097 template<
typename T>
1100 typedef itk::ThinPlateSplineKernelTransform<T,3> ThinPlateSplineTransformType;
1103 if (transformVtk_RAS==
nullptr)
1105 vtkErrorWithObjectMacro(loggerObject,
"Cannot set VTK thin-plate spline transform from ITK: the output vtkThinPlateSplineTransform is invalid");
1109 if (!transformItk_LPS)
1111 vtkErrorWithObjectMacro(loggerObject,
"Cannot set VTK thin-plate spline transform from ITK: the input transform is nullptr");
1115 if (transformItk_LPS->GetOutputSpaceDimension() !=
VTKDimension)
1117 vtkErrorWithObjectMacro(loggerObject,
"Unsupported number of dimensions in thin-plate spline transform file (expected = " 1118 <<
VTKDimension <<
", actual = " << transformItk_LPS->GetOutputSpaceDimension() <<
")");
1122 std::string transformItkClassName = transformItk_LPS->GetNameOfClass();
1124 bool inverse =
false;
1125 typename ThinPlateSplineTransformType::PointSetType::Pointer sourceLandmarksItk_Lps;
1126 typename ThinPlateSplineTransformType::PointSetType::Pointer targetLandmarksItk_Lps;
1127 if (transformItkClassName ==
"InverseThinPlateSplineKernelTransform")
1129 ThinPlateSplineTransformType* inverseTpsTransform =
static_cast<InverseThinPlateSplineTransformType*
>( transformItk_LPS.GetPointer() );
1131 sourceLandmarksItk_Lps = inverseTpsTransform->GetSourceLandmarks();
1132 targetLandmarksItk_Lps = inverseTpsTransform->GetTargetLandmarks();
1134 else if (transformItkClassName ==
"ThinPlateSplineKernelTransform")
1136 ThinPlateSplineTransformType* tpsTransform =
static_cast<ThinPlateSplineTransformType*
>( transformItk_LPS.GetPointer() );
1138 sourceLandmarksItk_Lps = tpsTransform->GetSourceLandmarks();
1139 targetLandmarksItk_Lps = tpsTransform->GetTargetLandmarks();
1143 vtkDebugWithObjectMacro(loggerObject,
"Not a ThinPlateSpline transform");
1147 vtkNew<vtkPoints> sourceLandmarksVtk_Ras;
1148 unsigned int numberOfSourceLandmarks = sourceLandmarksItk_Lps->GetNumberOfPoints();
1149 for(
unsigned int i = 0; i < numberOfSourceLandmarks; i++)
1151 typename ThinPlateSplineTransformType::InputPointType pointItk_Lps;
1152 bool pointExists = sourceLandmarksItk_Lps->GetPoint(i, &pointItk_Lps);
1157 double pointVtk_Ras[3]={0};
1158 pointVtk_Ras[0] = -pointItk_Lps[0];
1159 pointVtk_Ras[1] = -pointItk_Lps[1];
1160 pointVtk_Ras[2] = pointItk_Lps[2];
1161 sourceLandmarksVtk_Ras->InsertNextPoint(pointVtk_Ras);
1164 vtkNew<vtkPoints> targetLandmarksVtk_Ras;
1165 unsigned int numberOfTargetLandmarks = targetLandmarksItk_Lps->GetNumberOfPoints();
1166 for(
unsigned int i = 0; i < numberOfTargetLandmarks; i++)
1168 typename ThinPlateSplineTransformType::InputPointType pointItk_Lps;
1169 bool pointExists = targetLandmarksItk_Lps->GetPoint(i, &pointItk_Lps);
1174 double pointVtk_Ras[3]={0};
1175 pointVtk_Ras[0] = -pointItk_Lps[0];
1176 pointVtk_Ras[1] = -pointItk_Lps[1];
1177 pointVtk_Ras[2] = pointItk_Lps[2];
1178 targetLandmarksVtk_Ras->InsertNextPoint(pointVtk_Ras);
1181 transformVtk_RAS->SetBasisToR();
1182 transformVtk_RAS->SetSourceLandmarks(sourceLandmarksVtk_Ras.GetPointer());
1183 transformVtk_RAS->SetTargetLandmarks(targetLandmarksVtk_Ras.GetPointer());
1187 transformVtk_RAS->Inverse();
1194 itk::Object::Pointer& transformItk_LPS, vtkThinPlateSplineTransform* transformVtk_RAS,
bool initialize )
1196 if (transformVtk_RAS==
nullptr)
1198 vtkErrorWithObjectMacro(loggerObject,
"Cannot set ITK thin-plate spline transform from VTK: the intput vtkThinPlateSplineTransform is invalid");
1203 transformVtk_RAS->Update();
1205 if (transformVtk_RAS->GetBasis()!=VTK_RBF_R)
1207 vtkErrorWithObjectMacro(loggerObject,
"Cannot set ITK thin-plate spline transform from VTK: basis function must be R." 1208 " Call SetBasisToR() method of the vtkThinPlateSplineTransform object before attempting to write it to file.");
1212 ThinPlateSplineTransformDoubleType::PointSetType::Pointer sourceLandmarksItk_Lps = ThinPlateSplineTransformDoubleType::PointSetType::New();
1213 vtkPoints* sourceLandmarksVtk_Ras=transformVtk_RAS->GetSourceLandmarks();
1214 if (sourceLandmarksVtk_Ras!=
nullptr)
1216 for (
int i=0; i<sourceLandmarksVtk_Ras->GetNumberOfPoints(); i++)
1218 double posVtk_Ras[3]={0};
1219 sourceLandmarksVtk_Ras->GetPoint(i, posVtk_Ras);
1220 ThinPlateSplineTransformDoubleType::InputPointType posItk_Lps;
1221 posItk_Lps[0] = -posVtk_Ras[0];
1222 posItk_Lps[1] = -posVtk_Ras[1];
1223 posItk_Lps[2] = posVtk_Ras[2];
1224 sourceLandmarksItk_Lps->GetPoints()->InsertElement(i,posItk_Lps);
1227 ThinPlateSplineTransformDoubleType::PointSetType::Pointer targetLandmarksItk_Lps = ThinPlateSplineTransformDoubleType::PointSetType::New();
1228 vtkPoints* targetLandmarksVtk_Ras=transformVtk_RAS->GetTargetLandmarks();
1229 if (targetLandmarksVtk_Ras!=
nullptr)
1231 for (
int i=0; i<targetLandmarksVtk_Ras->GetNumberOfPoints(); i++)
1233 double posVtk_Ras[3]={0};
1234 targetLandmarksVtk_Ras->GetPoint(i, posVtk_Ras);
1235 ThinPlateSplineTransformDoubleType::InputPointType posItk_Lps;
1236 posItk_Lps[0] = -posVtk_Ras[0];
1237 posItk_Lps[1] = -posVtk_Ras[1];
1238 posItk_Lps[2] = posVtk_Ras[2];
1239 targetLandmarksItk_Lps->GetPoints()->InsertElement(i,posItk_Lps);
1243 if (transformVtk_RAS->GetInverseFlag())
1246 tpsTransformItk->SetSourceLandmarks(sourceLandmarksItk_Lps);
1247 tpsTransformItk->SetTargetLandmarks(targetLandmarksItk_Lps);
1250 tpsTransformItk->ComputeWMatrix();
1252 transformItk_LPS = tpsTransformItk;
1256 ThinPlateSplineTransformDoubleType::Pointer tpsTransformItk = ThinPlateSplineTransformDoubleType::New();
1257 tpsTransformItk->SetSourceLandmarks(sourceLandmarksItk_Lps);
1258 tpsTransformItk->SetTargetLandmarks(targetLandmarksItk_Lps);
1261 tpsTransformItk->ComputeWMatrix();
1263 transformItk_LPS = tpsTransformItk;
1270 template <
typename T>
1272 vtkObject* loggerObject,
1273 typename itk::TransformBaseTemplate<T>::Pointer transformItk)
1275 bool conversionSuccess =
false;
1278 vtkNew<vtkMatrix4x4> transformMatrixVtk;
1279 conversionSuccess = SetVTKLinearTransformFromITK<T>(loggerObject, transformMatrixVtk.GetPointer(), transformItk);
1280 if (conversionSuccess)
1282 vtkNew<vtkTransform> linearTransformVtk;
1283 linearTransformVtk->SetMatrix(transformMatrixVtk.GetPointer());
1284 linearTransformVtk->Register(
nullptr);
1285 return linearTransformVtk.GetPointer();
1288 vtkNew<vtkOrientedGridTransform> gridTransformVtk;
1289 conversionSuccess = SetVTKOrientedGridTransformFromITK<T>(loggerObject, gridTransformVtk.GetPointer(), transformItk);
1290 if (conversionSuccess)
1292 gridTransformVtk->Register(
nullptr);
1293 return gridTransformVtk.GetPointer();
1296 vtkNew<vtkOrientedBSplineTransform> bsplineTransformVtk;
1297 conversionSuccess = SetVTKBSplineFromITKv4Generic<T>(loggerObject, bsplineTransformVtk.GetPointer(), transformItk);
1298 if (conversionSuccess)
1300 bsplineTransformVtk->Register(
nullptr);
1301 return bsplineTransformVtk.GetPointer();
1304 vtkNew<vtkThinPlateSplineTransform> tpsTransformVtk;
1305 conversionSuccess = SetVTKThinPlateSplineTransformFromITK<T>(loggerObject, tpsTransformVtk.GetPointer(), transformItk);
1306 if (conversionSuccess)
1308 tpsTransformVtk->Register(
nullptr);
1309 return tpsTransformVtk.GetPointer();
1317 vtkAbstractTransform* transformVtk, itk::Object::Pointer& secondaryTransformItk,
int preferITKv3CompatibleTransforms,
bool initialize )
1319 typedef itk::CompositeTransform< double > CompositeTransformType;
1321 if (transformVtk==
nullptr)
1323 vtkErrorWithObjectMacro(loggerObject,
"CreateITKTransformFromVTK failed: invalid VTK transform");
1326 vtkNew<vtkCollection> transformList;
1328 if (transformList->GetNumberOfItems()==0)
1331 vtkNew<vtkTransform> identity;
1332 transformList->AddItem(identity.GetPointer());
1335 itk::Object::Pointer primaryTransformItk;
1336 if (transformList->GetNumberOfItems()==1)
1339 vtkObject* singleTransformVtk = transformList->GetItemAsObject(0);
1341 if (vtkHomogeneousTransform::SafeDownCast(singleTransformVtk))
1343 vtkHomogeneousTransform* linearTransformVtk = vtkHomogeneousTransform::SafeDownCast(singleTransformVtk);
1344 vtkMatrix4x4* transformMatrix = linearTransformVtk->GetMatrix();
1350 return primaryTransformItk;
1353 else if (vtkOrientedBSplineTransform::SafeDownCast(singleTransformVtk))
1355 vtkOrientedBSplineTransform* bsplineTransformVtk = vtkOrientedBSplineTransform::SafeDownCast(singleTransformVtk);
1356 vtkMatrix4x4* bulkMatrix = bsplineTransformVtk->GetBulkTransformMatrix();
1357 if (preferITKv3CompatibleTransforms || (bulkMatrix!=
nullptr && !
IsIdentityMatrix(bulkMatrix)))
1359 if (!
SetITKv3BSplineFromVTK(loggerObject, primaryTransformItk, secondaryTransformItk, bsplineTransformVtk, preferITKv3CompatibleTransforms))
1364 return primaryTransformItk;
1373 return primaryTransformItk;
1377 else if (vtkOrientedGridTransform::SafeDownCast(singleTransformVtk))
1379 vtkOrientedGridTransform* gridTransformVtk = vtkOrientedGridTransform::SafeDownCast(singleTransformVtk);
1385 return primaryTransformItk;
1388 else if (vtkThinPlateSplineTransform::SafeDownCast(singleTransformVtk))
1390 vtkThinPlateSplineTransform* tpsTransformVtk = vtkThinPlateSplineTransform::SafeDownCast(singleTransformVtk);
1396 return primaryTransformItk;
1400 if (singleTransformVtk==
nullptr)
1402 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::CreateITKTransformFromVTK failed: invalid input transform");
1405 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::CreateITKTransformFromVTK failed: conversion of transform type "<<singleTransformVtk->GetClassName()<<
" is not supported");
1413 CompositeTransformType::Pointer compositeTransformItk = CompositeTransformType::New();
1414 primaryTransformItk = compositeTransformItk;
1416 for (
int transformIndex = transformList->GetNumberOfItems()-1; transformIndex>=0; --transformIndex)
1418 vtkAbstractTransform* singleTransformVtk = vtkAbstractTransform::SafeDownCast(transformList->GetItemAsObject(transformIndex));
1419 itk::Object::Pointer secondaryTransformItkTmp;
1423 itk::Object::Pointer singleTransformItk =
CreateITKTransformFromVTK(loggerObject, singleTransformVtk, secondaryTransformItkTmp,
false );
1424 if (secondaryTransformItkTmp.IsNotNull())
1426 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::CreateITKTransformFromVTK failed: composite transforms cannot contain legacy transforms (that contains secondary transforms). Do not harden transforms on legacy ITK transforms to avoid this error.");
1430 if (singleTransformItk.IsNull()
1431 || std::string(singleTransformItk->GetNameOfClass()).find(
"Transform") == std::string::npos)
1433 vtkErrorWithObjectMacro(loggerObject,
"vtkITKTransformConverter::CreateITKTransformFromVTK failed: invalid element found while trying to create a composite transform");
1436 CompositeTransformType::TransformType::Pointer singleTransformItkTypeChecked =
static_cast< CompositeTransformType::TransformType*
>( singleTransformItk.GetPointer() );
1437 compositeTransformItk->AddTransform(singleTransformItkTypeChecked.GetPointer());
1439 return primaryTransformItk;
1444 #endif // __vtkITKTransformConverter_h
itk::AffineTransform< TransformRealType, 3 > AffineTransformType