ANTsX / ANTsPy

A fast medical imaging analysis library in Python with algorithms for registration, segmentation, and more.
https://antspyx.readthedocs.io
Apache License 2.0
608 stars 161 forks source link

Inverse Transforms Result in a Blank Image #486

Closed FIrgolitsch closed 1 year ago

FIrgolitsch commented 1 year ago

Hello,

I've been trying to perform inverse transforms of registered volumes. However, everything that I try seems to result in an empty image. My process:

Two volumes: A template and an acquisition of a mouse brain.

I register the acquisition to the template using ants.registration(fixed=template, moving=acquisition), first using Rigid and then using SyN.

This gives me two lists the 'fwdtransforms' and the 'invtransforms'. I apply the 'fwdtransforms' to the acquisition to obtain acqusition_syn.

However, when I try to apply the 'invtransforms' list to acquisition_syn to obtain the original image, I get a blank image instead.

image=acquisition
template=template

rigid_transform = ants.registration(fixed=template, moving=image, mask=mask, type_of_transform='Rigid')
rigid = ants.apply_transforms(fixed=template, moving=image, transformlist=rigid_transform['fwdtransforms'])

mask_rigid = ants.apply_transforms(fixed=template, moving=mask, transformlist=rigid_transform['fwdtransforms'])

syn_transform = ants.registration(fixed=template, moving=rigid, mask=mask_rigid, type_of_transform='SyN')
syn = ants.apply_transforms(fixed=template, moving=rigid,  transformlist=syn_transform['fwdtransforms'])

syn_inv = ants.apply_transforms(fixed=image, moving=syn, transformlist=syn_transform['invtransforms'], whichtoinvert=[False, True])
syn_inv.max()
# 0
cookpa commented 1 year ago

Using type_of_transform='SyN' will do Affine then SyN. If you want to do Rigid and then SyN, the best way is do the rigid registration first, then call registration again with an initial transform:

syn_transform = ants.registration(fixed=template, moving=image,  initial_transform = rigid_transform['fwdtransforms'][0] type_of_transform='SyNOnly')

You can add the mask (in the space of the moving image) as moving_mask if you like.

Then

syn_inv = ants.apply_transforms(fixed=image, moving=template, transformlist=syn_transform['invtransforms'], whichtoinvert=[True, False])

should work

FIrgolitsch commented 1 year ago

I am not asking about the forward transforms, they are working fine. I actually do want rigid > affine > deformable. We have found that by initializing SyN with a rigid registration we get slightly better results.

The problem lies in applying the inverse transform using the 'invtransforms' list (which already includes the rigid registration), which results in a blank image.

EDIT: My apologies I missed your point about the initial transform. That seems to have done the trick. Thank you very much!

cookpa commented 1 year ago

No problem - also be careful about the mask option, the argument mask wants a mask in the fixed space. You can use a mask in the moving space with moving_mask

cookpa commented 1 year ago

Also, you can try type_of_transform = 'SyNRA' to include a rigid transform in one pass