Hi Nick and Hans,

I am sorry that my first email was not clear enough and thanks Hans for 
clarification.

I had done something like you presented in the previous email to get the 
current transform, and it was working; however, my focus was to get the current 
transform without making any changes to the ITK registration framework.

m_outputTransform is updated when optimization is completed, so I tried to get 
the current transform from the optimizer or metric, and I was thinking it would 
return its current transform like generic optimization framework, but it seems 
we have to do some light changes to itkSyNImageRegistrationMethod to finish 
this task.

Also, I think instead of updating the m_outputTransform at each iteration, we 
can add an interface to the optimizer framework of SyN filter to return the 
composer output if it is asked.

Thanks,
Ali

________________________________
From: Nicholas Tustison [[email protected]]
Sent: Sunday, December 02, 2012 2:58 PM
To: Johnson, Hans J
Cc: Ghayoor, Ali; [email protected]
Subject: Re: [Insight-developers] "itkSyNImageRegistrationMethod" cannot return 
its metric's transform properly

Yeah, that should be easy to do and I don't know that it would be a substantive
penalty---just unnecessary for minimum functionality.   It requires two 
instances of the
itkComposeDisplacementFieldsImageFilter.  If you take a look at the 
GenerateData()
function in itkSyNImageRegistrationMethod.hxx starting at line 537 and
going to line 550 you can see what I described in the last email to update
the output transform.

  typedef ComposeDisplacementFieldsImageFilter<DisplacementFieldType, 
DisplacementFieldType> ComposerType;

  typename ComposerType::Pointer composer = ComposerType::New();
  composer->SetDisplacementField( 
this->m_MovingToMiddleTransform->GetInverseDisplacementField() );
  composer->SetWarpingField( 
this->m_FixedToMiddleTransform->GetDisplacementField() );
  composer->Update();

  typename ComposerType::Pointer inverseComposer = ComposerType::New();
  inverseComposer->SetDisplacementField( 
this->m_FixedToMiddleTransform->GetInverseDisplacementField() );
  inverseComposer->SetWarpingField( 
this->m_MovingToMiddleTransform->GetDisplacementField() );
  inverseComposer->Update();

  this->m_OutputTransform->SetDisplacementField( composer->GetOutput() );
  this->m_OutputTransform->SetInverseDisplacementField( 
inverseComposer->GetOutput() );

We create two instances of the composer filter to create the forward and inverse
displacement fields and assign those to the output transform.  We would need to
take that snippet and copy that to wherever you wanted to query for the current
transform.  The iterative optimization all takes place in the 
StartOptimization()
function.  I'm assuming you could copy the snippet to somewhere around line
222 within a conditional where the metric value is assigned and the two 
transforms
to the middle have already been optimized for that iteration.

Nick




On Dec 2, 2012, at 3:31 PM, "Johnson, Hans J" 
<[email protected]<mailto:[email protected]>> wrote:

Nick,

We certainly do NOT want to update the m_OutputTransform at each iteration in 
the normal case, but we do need an option for getting the 
currentIterationTransform if requested (even with a potentially huge 
performance penalty).

Ultimately we need to make a movie of the deformation field at each iteration, 
and I don't care if I take a 20x speed penalty for making the movie.

If you could provide a hint of what needs to be changed (in ITK or ANTS) that 
would be great.

Thanks,
Hans


From: Nick Tustison <[email protected]<mailto:[email protected]>>
Date: Sunday, December 2, 2012 1:14 PM
To: Hans Johnson <[email protected]<mailto:[email protected]>>
Cc: Ali Ghayoor <[email protected]<mailto:[email protected]>>, ITK 
<[email protected]<mailto:[email protected]>>
Subject: Re: [Insight-developers] "itkSyNImageRegistrationMethod" cannot return 
its metric's transform properly

Okay, I figured it was just something I wasn't getting (particularly since
I was attempting an answer late last night).  I thought more about this
and I think I might have an idea of what the issue might be.

The SyNImageRegistrationMethod is used to optimize an itk
DisplacementFieldTransform since SyN doesn't fit in the generic
optimization framework.  The way optimization works is that we
initially create two additional displacement field transforms (in
addition to m_OutputTransform) called something like

fixedToMiddleTransform
movingToMiddleTransform

The first describes the forward and inverse transform from the fixed
image to the middle space.  The second describes the forward and
inverse transform from the moving image to the middle space.  During
the optimization, we strictly optimize just these two transforms.
m_OutputTransform only gets updated at the end of optimization by
composing the correct forward and inverse fields of the
fixed/movingToMiddleTransform(s).  We could potentially do this
composition at each iteration (i.e. update m_OutputTransform) but
that would be unnecessary computation (at least in terms of just getting
the final solution).

Nick


On Dec 2, 2012, at 11:34 AM, "Johnson, Hans J" 
<[email protected]<mailto:[email protected]>> wrote:

Ali,

You original e-mail is vague in its description of how you deterred that the 
displacement field has all zero's at every iteration.
-- Where you using a debugger?
-- How many zero values were listed?

Why do you need the const_cast in this code?  Could that change the behavior?

The use of const_cast is an indication that you are tyring to do something that 
is not supported.  Either ITK is deficient in not providing a const version of 
that member function, or you are trying to do something that has been 
explicitly prohibited.

Due to the ambiguity in your original posting, it is hard to figure out what 
your problem is.  You know that the the overall program produces a good result 
at the end, but you are trying to interrogate the process at every iteration, 
and for that you need to get the moving transform at each iteration.

***  I think that the problem you are having is exposing the current transform 
at each iteration to the observer.  ***

The response from Nick does not seem to address your real problem.

Please make a more thorough and very clearly stated problem, and then post 
enough information so that an external developer can replicate your error on 
their machine QUICKLY and EASILY.

Keep these facts in mind when requesting help from the ITK developer community:
1) We are almost all volunteers.  We help out of kindness not financial gain.
2)  If we can not replicate your error on my computer, we can not fix it.
3) Our time is valuable, if we need to guess, work, hard, or decipher code to 
determine how to replicate your problem, we will not have the time or energy 
even to get started
4) Provide both a) A description of the problem, b) description of how to 
replicate the problem, *** c) a description of how you believe the code should 
behave ***, and d) a proposed solution


Hans

PS: Nick Thanks for trying to address this request.  The original request was 
not very clear, and your effort showed that the end result is good (that was 
never in doubt).  The problem is interrogating for the current transform at 
every iteration.


From: Nick Tustison <[email protected]<mailto:[email protected]>>
Date: Saturday, December 1, 2012 8:24 PM
To: Ali Ghayoor <[email protected]<mailto:[email protected]>>
Cc: ITK <[email protected]<mailto:[email protected]>>
Subject: Re: [Insight-developers] "itkSyNImageRegistrationMethod" cannot return 
its metric's transform properly

Hi Ali,

I don't think that there's a deficiency.  I just ran the 
itkSyNImageRegistrationTest
and added the following snippet to write the displacement field to disk starting
at line 275.

  typedef itk::ImageFileWriter<DisplacementFieldType> WriterType2;
  typename WriterType2::Pointer writer2 = WriterType2::New();
  writer2->SetFileName( "/Users/ntustison/Desktop/testDisplacementField.nii.gz" 
);
  writer2->SetInput( outputTransform->GetDisplacementField() );
  writer2->Update();

The result was a non-zero displacement field that looked reasonable based
on the parameters specified by the test.

Nick


On Dec 1, 2012, at 8:30 PM, "Ghayoor, Ali" 
<[email protected]<mailto:[email protected]>> wrote:

Hello Developers,

In a registration framework, at each iteration, I get the current moving 
transform from the metric of the "itkSyNImageRegistrationMethod" filter; 
however, the returned moving transform has a displacement field with all zero 
values at every iteration.

To inspect this deficiency in ITK, I used "itkSyNImageRegistrationTest.cxx", 
and made some modifications in the test code for this purpose.
I added an iteration observer to the SyN registration stage:

    typedef CommandIterationUpdate<DisplacementFieldRegistrationType> 
DisplacementFieldCommandType;
    typename DisplacementFieldCommandType::Pointer DisplacementFieldObserver = 
DisplacementFieldCommandType::New();
    displacementFieldRegistration->AddObserver( itk::IterationEvent(), 
DisplacementFieldObserver );

Then, inside the observer class, I asked for the parameters of the moving 
transform at the current iteration:

   std::cout << " parameters: " << const_cast<TFilter *>( filter 
)->GetMetric()->GetMovingTransform()->GetParameters() << std::endl;
   std::cout << " fixed parameters " << const_cast<TFilter *>( filter 
)->GetMetric()->GetMovingTransform()->GetFixedParameters() << std::endl;

However, the Parameters of the moving transform is an all zero valued 
displacement field at each iteration.
Do you know why the registration filter does not return the right moving 
transform? Could you please help about this problem.

Thanks,
Ali
_______________________________________________
Powered by www.kitware.com<http://www.kitware.com/>

Visit other Kitware open-source projects at
http://www.kitware.com/opensource/opensource.html

Kitware offers ITK Training Courses, for more information visit:
http://kitware.com/products/protraining.php

Please keep messages on-topic and check the ITK FAQ at:
http://www.itk.org/Wiki/ITK_FAQ

Follow this link to subscribe/unsubscribe:
http://www.itk.org/mailman/listinfo/insight-developers



________________________________
Notice: This UI Health Care e-mail (including attachments) is covered by the 
Electronic Communications Privacy Act, 18 U.S.C. 2510-2521, is confidential and 
may be legally privileged.  If you are not the intended recipient, you are 
hereby notified that any retention, dissemination, distribution, or copying of 
this communication is strictly prohibited.  Please reply to the sender that you 
have received the message in error, then delete it.  Thank you.
________________________________




________________________________
Notice: This UI Health Care e-mail (including attachments) is covered by the 
Electronic Communications Privacy Act, 18 U.S.C. 2510-2521, is confidential and 
may be legally privileged.  If you are not the intended recipient, you are 
hereby notified that any retention, dissemination, distribution, or copying of 
this communication is strictly prohibited.  Please reply to the sender that you 
have received the message in error, then delete it.  Thank you.
________________________________

_______________________________________________
Powered by www.kitware.com

Visit other Kitware open-source projects at
http://www.kitware.com/opensource/opensource.html

Kitware offers ITK Training Courses, for more information visit:
http://kitware.com/products/protraining.php

Please keep messages on-topic and check the ITK FAQ at:
http://www.itk.org/Wiki/ITK_FAQ

Follow this link to subscribe/unsubscribe:
http://www.itk.org/mailman/listinfo/insight-developers

Reply via email to