[Insight-users] forcing pipeline to update - sorry - got it

Jakub Bican jakub.bican at matfyz.cz
Fri Jul 1 10:08:57 EDT 2005


Sorry for bothering you with my mistake.

I analyzed the problem and found out that it was my mistake inside class 
ComposeUniformTransformsTransform - i did not know that i have to 
implement my own GetMTime() method inside my class to check the 
modification time of ivars. I have done it and send the fixed code.

May be, there should be a notice in Developers Guide about this, to 
prevent other users falling into these problems.

Thanks for your cooperation,
regards,
   Jakub


Jakub Bican napsal(a):

>
>
> Hi Karthik,
>
> i have done some tests and here are the results (with the code). I had 
> to change my classes a little bit (to use macros) and i also post a 
> compilable example on which i will be explaining here.
>
> I use the old scenario with resample filter, 
> ComposeUniformTransformsTransform with 3 transforms chained. The 
> example has several steps:
>
> 00) this step only prints the initial state (and "modified" values) of 
> the classes - OK
>
> 01) resample filter's SetTransform methods changes the modification 
> time correctly - OK
>
> 02) and if we change the transform that is already set to the filter, 
> it still works - OK
>
> 03) set composed transform back to resample filter - just maintenance 
> step - OK
>
> 04) change the entire container inside the composed transform - this 
> works OK as i changed the composed transform to use the macros - OK
>
> 05) add a transform (PermuteAxesTransform) to the container set to 
> composed transform in previous step - PROBLEM - container's 
> (VectorContainer) modification time changed, but the 
> composedtransform's not. (this was the same even if i used non-const 
> pointers and macros in the compose transform - if it has any meaning)
>
> 06) set a new permutation to the PermuteAxesTransform from the last 
> step ... PROBLEMS:
> - PermuteAxesTransform is modified although it does not use Set macro 
> or call this->Modified() in Set method
> - VectorContainer containing the PermuteAxesTransform did not get 
> modified although its "member" did
>
>
> So 3 questions:
> 1) Why the modification time of the ComposeUniformTrasformsTransform 
> instance did NOT CHANGE, when there was a new item inserted into its 
> transform container, which modification time was correctly changed by 
> this operation?
>
> 2) Why the modification time of the PermuteAxesTransform instance 
> CHANGED when a new permutation was set in it, even though it does not 
> use the Set macro or call this->Modified() explicitly?
>
> 3) Why the modification time of the VectorContainer instance did NOT 
> CHANGE, when the modification time of one of its members did?
>
>
> I think that if we are able to answer these questions, we would fix 
> the problem. But with my current knowledge, i can't see what should it 
> be.
>
> Thank you again very much for your attention and time that you spent 
> answering my questions and solving my problems.
>
> Cheers,
>     Jakub
>
>
> Karthik Krishnan napsal(a):
>
>> You should be fine with the code... Did you see if Modified() was 
>> called along the way ?..
>>
>> You need to ensure in the transforms you have created that any time 
>> any of the transform's ivars are changed you call this->Modified()
>>
>> The Set/Get macros do this for you automatically... See 
>> Common/itkMacro.h
>>
>> I do not know how you use your VectorContainer of transforms within 
>> this 'ComposeUniformTransformsTransform'. Since VectorContainer is a 
>> subclass of itk::Object, if its contents are modified, it should 
>> update its modification time causing 
>> ComposeUniformTransformsTransform's modification time to change.. but 
>> you might want to check yourself if this is indeed true.
>>
>> HTH
>> Karthik
>>
>> Jakub Bican wrote:
>>
>>>
>>>
>>> AHA! :))
>>>
>>> I have my own transforms that might be doing something wrong so that 
>>> resample filter is not "modified" when the transform is.
>>>
>>> I wrote a ComposeUniformTransformsTransform that has an array of 
>>> transforms and transforms point by consecutively transforming it by 
>>> transforms in the array. "Uniform" in the classname means that the 
>>> transforms should preserve the Dimension (i was not able to program 
>>> such class that can chain transforms with arbitrary dimensionality). 
>>> The meaning of such transform is to avoid chaining several resample 
>>> filters where several successive transforms are neccessary.
>>>
>>> In this my app, i use PolarToCartesianTransform, succeeded by 
>>> PermuteAxesTransform which enables me to use polar coordinates in 
>>> various orthogonal directions. These classes are composed with 
>>> previous class.
>>>
>>> Now - i need resample filter to compute several instances of 
>>> transformed image with various permutations set into 
>>> PermuteAxesTransform - and there was the problem...
>>>
>>> I am attaching sources of mentioned classes - in following days, i 
>>> will try to improve them to support "modified" features correctly. I 
>>> would be grateful, if you take a look at the sources and help me 
>>> with fixing this (and any other problem that you find), or even 
>>> provide some information, what should i follow (in docs, examples, 
>>> etc).
>>>
>>> I am sorry that i did not post the problem as it lays first. I 
>>> wanted to sketch the situation without having obscure with too many 
>>> details which i considered unimportant ;)
>>>
>>> Thanks,
>>>     Jakub
>>>
>>>
>>
>>
>------------------------------------------------------------------------
>
>00 ********************************************
>VectorContainer (00279538)
>  RTTI typeinfo:   class itk::VectorContainer<int,class itk::SmartPointer<class itk::Transform<double,3,3> > >
>  Reference Count: 2
>  Modified Time: 27
>  Debug: Off
>  Observers:
>    none
>PolarToCartesianTransform (00277E00)
>  RTTI typeinfo:   class itk::PolarToCartesianTransform<double,3>
>  Reference Count: 2
>  Modified Time: 16
>  Debug: Off
>  Observers:
>    none
>PermuteAxesTransform (00277F68)
>  RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>  Reference Count: 2
>  Modified Time: 17
>  Debug: Off
>  Observers:
>    none
>  Order: [0, 1, 2]
>  InverseOrder: [0, 1, 2]
>Rigid3DTransform (00279120)
>  RTTI typeinfo:   class itk::Rigid3DTransform<double>
>  Reference Count: 2
>  Modified Time: 21
>  Debug: Off
>  Observers:
>    none
>  Matrix:
>    1 0 0
>    0 1 0
>    0 0 1
>  Offset: [0, 0, 0]
>  Center: [0, 0, 0]
>  Translation: [0, 0, 0]
>  Inverse:
>    1 0 0
>    0 1 0
>    0 0 1
>  Singular: 0
>VectorContainer (00279538)
>  RTTI typeinfo:   class itk::VectorContainer<int,class itk::SmartPointer<class itk::Transform<double,3,3> > >
>  Reference Count: 2
>  Modified Time: 27
>  Debug: Off
>  Observers:
>    none
>ComposeUniformTransformsTransform (00277B90)
>  RTTI typeinfo:   class itk::ComposeUniformTransformsTransform<double,3,class itk::VectorContainer<int,class itk::Smart
>Pointer<class itk::Transform<double,3,3> > > >
>  Reference Count: 2
>  Modified Time: 28
>  Debug: Off
>  Observers:
>    none
>  Transform "0":
>    PolarToCartesianTransform (00277E00)
>      RTTI typeinfo:   class itk::PolarToCartesianTransform<double,3>
>      Reference Count: 2
>      Modified Time: 16
>      Debug: Off
>      Observers:
>        none
>  Transform "1":
>    PermuteAxesTransform (00277F68)
>      RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>      Reference Count: 2
>      Modified Time: 17
>      Debug: Off
>      Observers:
>        none
>      Order: [0, 1, 2]
>      InverseOrder: [0, 1, 2]
>  Transform "2":
>    Rigid3DTransform (00279120)
>      RTTI typeinfo:   class itk::Rigid3DTransform<double>
>      Reference Count: 2
>      Modified Time: 21
>      Debug: Off
>      Observers:
>        none
>      Matrix:
>        1 0 0
>        0 1 0
>        0 0 1
>      Offset: [0, 0, 0]
>      Center: [0, 0, 0]
>      Translation: [0, 0, 0]
>      Inverse:
>        1 0 0
>        0 1 0
>        0 0 1
>      Singular: 0
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 30
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00277B90
>  Interpolator: 00277A20
>01 ********************************************
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 31
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00279120
>  Interpolator: 00277A20
>02 ********************************************
>Rigid3DTransform (00279120)
>  RTTI typeinfo:   class itk::Rigid3DTransform<double>
>  Reference Count: 3
>  Modified Time: 32
>  Debug: Off
>  Observers:
>    none
>  Matrix:
>    1 0 0
>    0 1 0
>    0 0 1
>  Offset: [0, 0, 0]
>  Center: [1, 0, 0]
>  Translation: [0, 0, 0]
>  Inverse:
>    1 0 0
>    0 1 0
>    0 0 1
>  Singular: 0
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 32
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00279120
>  Interpolator: 00277A20
>03 ********************************************
>ComposeUniformTransformsTransform (00277B90)
>  RTTI typeinfo:   class itk::ComposeUniformTransformsTransform<double,3,class itk::VectorContainer<int,class itk::Smart
>Pointer<class itk::Transform<double,3,3> > > >
>  Reference Count: 2
>  Modified Time: 28
>  Debug: Off
>  Observers:
>    none
>  Transform "0":
>    PolarToCartesianTransform (00277E00)
>      RTTI typeinfo:   class itk::PolarToCartesianTransform<double,3>
>      Reference Count: 2
>      Modified Time: 16
>      Debug: Off
>      Observers:
>        none
>  Transform "1":
>    PermuteAxesTransform (00277F68)
>      RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>      Reference Count: 2
>      Modified Time: 17
>      Debug: Off
>      Observers:
>        none
>      Order: [0, 1, 2]
>      InverseOrder: [0, 1, 2]
>  Transform "2":
>    Rigid3DTransform (00279120)
>      RTTI typeinfo:   class itk::Rigid3DTransform<double>
>      Reference Count: 2
>      Modified Time: 32
>      Debug: Off
>      Observers:
>        none
>      Matrix:
>        1 0 0
>        0 1 0
>        0 0 1
>      Offset: [0, 0, 0]
>      Center: [1, 0, 0]
>      Translation: [0, 0, 0]
>      Inverse:
>        1 0 0
>        0 1 0
>        0 0 1
>      Singular: 0
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 33
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00277B90
>  Interpolator: 00277A20
>04 ********************************************
>VectorContainer (00277888)
>  RTTI typeinfo:   class itk::VectorContainer<int,class itk::SmartPointer<class itk::Transform<double,3,3> > >
>  Reference Count: 2
>  Modified Time: 34
>  Debug: Off
>  Observers:
>    none
>ComposeUniformTransformsTransform (00277B90)
>  RTTI typeinfo:   class itk::ComposeUniformTransformsTransform<double,3,class itk::VectorContainer<int,class itk::Smart
>Pointer<class itk::Transform<double,3,3> > > >
>  Reference Count: 2
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00277B90
>  Interpolator: 00277A20
>05 ********************************************
>PermuteAxesTransform (00277F68)
>  RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>  Reference Count: 3
>  Modified Time: 17
>  Debug: Off
>  Observers:
>    none
>  Order: [0, 1, 2]
>  InverseOrder: [0, 1, 2]
>VectorContainer (00277888)
>  RTTI typeinfo:   class itk::VectorContainer<int,class itk::SmartPointer<class itk::Transform<double,3,3> > >
>  Reference Count: 2
>  Modified Time: 37
>  Debug: Off
>  Observers:
>    none
>ComposeUniformTransformsTransform (00277B90)
>  RTTI typeinfo:   class itk::ComposeUniformTransformsTransform<double,3,class itk::VectorContainer<int,class itk::Smart
>Pointer<class itk::Transform<double,3,3> > > >
>  Reference Count: 2
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>  Transform "0":
>    PermuteAxesTransform (00277F68)
>      RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>      Reference Count: 3
>      Modified Time: 17
>      Debug: Off
>      Observers:
>        none
>      Order: [0, 1, 2]
>      InverseOrder: [0, 1, 2]
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00277B90
>  Interpolator: 00277A20
>06 ********************************************
>PermuteAxesTransform (00277F68)
>  RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>  Reference Count: 3
>  Modified Time: 38
>  Debug: Off
>  Observers:
>    none
>  Order: [1, 2, 0]
>  InverseOrder: [2, 0, 1]
>VectorContainer (00277888)
>  RTTI typeinfo:   class itk::VectorContainer<int,class itk::SmartPointer<class itk::Transform<double,3,3> > >
>  Reference Count: 2
>  Modified Time: 37
>  Debug: Off
>  Observers:
>    none
>ComposeUniformTransformsTransform (00277B90)
>  RTTI typeinfo:   class itk::ComposeUniformTransformsTransform<double,3,class itk::VectorContainer<int,class itk::Smart
>Pointer<class itk::Transform<double,3,3> > > >
>  Reference Count: 2
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>  Transform "0":
>    PermuteAxesTransform (00277F68)
>      RTTI typeinfo:   class itk::PermuteAxesTransform<double,3>
>      Reference Count: 3
>      Modified Time: 38
>      Debug: Off
>      Observers:
>        none
>      Order: [1, 2, 0]
>      InverseOrder: [2, 0, 1]
>ResampleImageFilter (002754C0)
>  RTTI typeinfo:   class itk::ResampleImageFilter<class itk::Image<float,3>,class itk::Image<float,3>,double>
>  Reference Count: 1
>  Modified Time: 35
>  Debug: Off
>  Observers:
>    none
>  Number Of Required Inputs: 1
>  Number Of Required Outputs: 1
>  Number Of Threads: 1
>  ReleaseDataFlag: Off
>  ReleaseDataBeforeUpdateFlag: Off
>  No Inputs
>  Output 0: (002774C8)
>  AbortGenerateData: Off
>  Progress: 0
>  Multithreader:
>    RTTI typeinfo:   class itk::MultiThreader
>    Reference Count: 1
>    Modified Time: 2
>    Debug: Off
>    Observers:
>      none
>    Thread Count: 1
>    Global Maximum Number Of Threads: 0
>  DefaultPixelValue: 0
>  Size: [0, 0, 0]
>  OutputStartIndex: [0, 0, 0]
>  OutputSpacing: [1, 1, 1]
>  OutputOrigin: [0, 0, 0]
>  Transform: 00277B90
>  Interpolator: 00277A20
>07 ********************************************
>  
>
>------------------------------------------------------------------------
>
>_______________________________________________
>Insight-users mailing list
>Insight-users at itk.org
>http://www.itk.org/mailman/listinfo/insight-users
>  
>
-------------- next part --------------


#ifndef __itkComposeUniformTransformsTransform_h
#define __itkComposeUniformTransformsTransform_h

#include <iostream>
#include "itkTransform.h"
#include "itkExceptionObject.h"
#include "itkMatrix.h"
#include "itkVectorContainer.h"


namespace itk
{

/** \brief Combines transformations of a vector space (e.g. space coordinates).
 *
 *	Iterates through a container TContainerType and successively transforms 
 *	space coordinates of input point by each transform in the container.
 *
 *	Transforms stored in a container MUST be derived from same type as ::Superclass, 
 *	i.e. Transform<TScalarType,NDimensions,NDimensions> where TScalarType and NDimensions
 *	are same as passed into this class template. Also specified in ::TransformsType.
 *
 *	TContainerType must conform to IndexedContainerInterface and must store transforms
 *	of type Transform< TScalarType, NDimensions, NDimensions >::Pointer (e.g. ::Superclass::Pointer).
 *
 * \author Jakub Bican, Department of Image Processing, Institute of Information Theory and Automation, Academy of Sciences of the Czech Republic.
 *
 * \ingroup Transforms
 */
template <
    class TScalarType = double,          // Data type for scalars (float or double)
    unsigned int NDimensions = 3,        // Number of dimensions
		class TContainerType = VectorContainer< int,typename Transform<TScalarType,NDimensions,NDimensions>::Pointer > >		 // Transforms container type
class ITK_EXPORT ComposeUniformTransformsTransform :
          public Transform< TScalarType, NDimensions, NDimensions >
{
public:
  /** Standard class typedefs. */
  typedef ComposeUniformTransformsTransform Self;
  typedef Transform< TScalarType, NDimensions, NDimensions > Superclass;
  typedef SmartPointer<Self>        Pointer;
  typedef SmartPointer<const Self>  ConstPointer;

  /** New macro for creation of through the object factory.*/
  itkNewMacro( Self );

  /** Run-time type information (and related methods). */
  itkTypeMacro( ComposeUniformTransformsTransform, Transform );

  /** Dimension of the domain space. */
  itkStaticConstMacro(SpaceDimension, unsigned int, NDimensions);
  itkStaticConstMacro(ParametersDimension, unsigned int, 0);

  /** Standard scalar type for this class. */
  typedef typename Superclass::ScalarType ScalarType;

  /** Standard Jacobian container. */
  typedef typename Superclass::JacobianType JacobianType;

  /** Standard vector type for this class. */
  typedef Vector<TScalarType, itkGetStaticConstMacro(SpaceDimension)> InputVectorType;
  typedef Vector<TScalarType, itkGetStaticConstMacro(SpaceDimension)> OutputVectorType;

  /** Standard covariant vector type for this class. */
  typedef CovariantVector<TScalarType, itkGetStaticConstMacro(SpaceDimension)> InputCovariantVectorType;
  typedef CovariantVector<TScalarType, itkGetStaticConstMacro(SpaceDimension)> OutputCovariantVectorType;

  /** Standard vnl_vector type for this class. */
  typedef vnl_vector_fixed<TScalarType, itkGetStaticConstMacro(SpaceDimension)> InputVnlVectorType;
  typedef vnl_vector_fixed<TScalarType, itkGetStaticConstMacro(SpaceDimension)> OutputVnlVectorType;

  /** Standard coordinate point type for this class. */
  typedef Point<TScalarType, itkGetStaticConstMacro(SpaceDimension)> InputPointType;
  typedef Point<TScalarType, itkGetStaticConstMacro(SpaceDimension)> OutputPointType;

	/** Container type for transforms - must conform to IndexedContainerInterface */
	typedef typename TContainerType ContainerType;

	/** Type of transforms to compose 
	 * 	
	 *	Here, the type should be taken from ContainerType::Element. (??!!)
	 *
	 */
	typedef Transform< TScalarType, itkGetStaticConstMacro(SpaceDimension), itkGetStaticConstMacro(SpaceDimension) > TransformType;

  /** Method to transform a point or a vector. */
  OutputPointType     TransformPoint(const InputPointType  &point ) const;
  virtual OutputVectorType TransformVector(const InputVectorType &) const;
  virtual OutputVnlVectorType TransformVector(const InputVnlVectorType &) const;
  virtual OutputCovariantVectorType TransformCovariantVector(
    const InputCovariantVectorType &) const;


  /** This method returns the permutation order of the PermuteAxesTransform. */
  itkSetConstObjectMacro(Transforms,ContainerType);


	
  /** This method returns the permutation order of the PermuteAxesTransform. */
  itkGetConstObjectMacro(Transforms,ContainerType);


  /** Compute the Jacobian Matrix of the transformation at one point - not applicable for this type of transform */
  virtual const JacobianType & GetJacobian(const InputPointType  &point ) const
		{
			itkExceptionMacro(<< "Method not applicable for composed transforms. ");
			return m_Jacobian;
		}

  /** Method Compute the Modified Time based on changed to the components. */
  unsigned long GetMTime( void ) const;

protected:
  ComposeUniformTransformsTransform();
  ~ComposeUniformTransformsTransform();

	/** Print contents of an TranslationTransform. */
  void PrintSelf(std::ostream &os, Indent indent) const;

private:
  ComposeUniformTransformsTransform(const Self&); //purposely not implemented
  void operator=(const Self&); //purposely not implemented

	typename ContainerType::ConstPointer m_Transforms;

}; //class ComposeUniformTransformsTransform


}  // namespace itk


#ifndef ITK_MANUAL_INSTANTIATION
#include "itkComposeUniformTransformsTransform.txx"
#endif

#endif /* __itkComposeUniformTransformsTransform_h */
-------------- next part --------------

#ifndef _itkComposeUniformTransformsTransform_txx
#define _itkComposeUniformTransformsTransform_txx

#include "itkComposeUniformTransformsTransform.h"


namespace itk
{

// Constructor with default arguments
template<class TScalarType,unsigned int NDimensions,class TContainerType>
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
ComposeUniformTransformsTransform():Superclass(NDimensions,0)
{
	m_Transforms = ContainerType::New();
}
    

// Destructor
template<class TScalarType,unsigned int NDimensions,class TContainerType>
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
~ComposeUniformTransformsTransform()
{
	return;
}


// Print self
template<class TScalarType,unsigned int NDimensions,class TContainerType>
void
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
PrintSelf(std::ostream &os, Indent indent) const
{
  Superclass::PrintSelf(os,indent);

	ContainerType::ConstIterator iterator = m_Transforms->Begin();
	ContainerType::ConstIterator end = m_Transforms->End();
	while (iterator != end) 
		{
			os << indent << "Transform \"" << iterator.Index() << "\":" << std::endl;
			iterator.Value()->Print(os,indent.GetNextIndent());
			++iterator;
		}
}


// Transform a point
template<class TScalarType,unsigned int NDimensions,class TContainerType>
typename ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::OutputPointType
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
TransformPoint(const InputPointType &point) const 
{
	OutputPointType opoint(point);

	ContainerType::ConstIterator iterator = m_Transforms->Begin();
	ContainerType::ConstIterator end = m_Transforms->End();
	while (iterator != end) 
		{
			opoint = iterator.Value()->TransformPoint(opoint);
			++iterator;
		}

		return opoint;
}

// Transform a vector
template<class TScalarType,unsigned int NDimensions,class TContainerType>
typename ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::OutputVectorType
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
TransformVector(const InputVectorType &vect) const 
{
	OutputVectorType ovect(vect);

	ContainerType::ConstIterator iterator = m_Transforms->Begin();
	ContainerType::ConstIterator end = m_Transforms->End();
	while (iterator != end) 
		{
			ovect = iterator.Value()->TransformVector(ovect);
			++iterator;
		}

  return  ovect;
}


// Transform a vnl_vector_fixed
template<class TScalarType,unsigned int NDimensions,class TContainerType>
typename ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::OutputVnlVectorType
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
TransformVector(const InputVnlVectorType &vect) const 
{
	OutputVnlVectorType ovect(vect);

	ContainerType::ConstIterator iterator = m_Transforms->Begin();
	ContainerType::ConstIterator end = m_Transforms->End();
	while (iterator != end) 
		{
			ovect = iterator.Value()->TransformVector(ovect);
			++iterator;
		}

  return  ovect;
}


// Transform a CovariantVector
template<class TScalarType,unsigned int NDimensions,class TContainerType>
typename ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::OutputCovariantVectorType
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
TransformCovariantVector(const InputCovariantVectorType &vect) const 
{
	OutputCovariantVectorType ovect(vect);

	ContainerType::ConstIterator iterator = m_Transforms->Begin();
	ContainerType::ConstIterator end = m_Transforms->End();
	while (iterator != end) 
		{
			ovect = iterator.Value()->TransformCovariantVector(ovect);
			++iterator;
		}

  return  ovect;
}

template<class TScalarType,unsigned int NDimensions,class TContainerType>
unsigned long
ComposeUniformTransformsTransform<TScalarType,NDimensions,TContainerType>::
GetMTime( void ) const
{
  unsigned long latestTime = Object::GetMTime(); 

  if( m_Transforms )
    {
    if( latestTime < m_Transforms->GetMTime() )
      {
      latestTime = m_Transforms->GetMTime();
      }

	  ContainerType::ConstIterator iterator = m_Transforms->Begin();
	  ContainerType::ConstIterator end = m_Transforms->End();
	  while (iterator != end) 
		  {
        if (latestTime < iterator.Value()->GetMTime() )
          {
          latestTime = iterator.Value()->GetMTime();
          }
			  ++iterator;
		  }
    }

  return latestTime;
}


} // namespace

#endif


More information about the Insight-users mailing list