InsightSoftwareConsortium / InsightSoftwareConsortium/ITK

Left-handed orientation is discarded when saving a .dcm file

Open
#1,771 13 comments 1 reaction 0 assignees View on GitHub
status:Use_Milestone_Backlog type:Bug
Dominant language
C++
Stars
1.7k
Forks
748
Avg merge
1d 1h
Merged PRs (30d)
64

Description

### Description
Out of 48 possible orientations for a 3d image, the 24 left-handed orientations are treated incorrectly when saving a multi-frame dicom file or series.

- Examples for right-handed orientations (24 in total):
- RAI
- SAR
- Left-handed (24 in total):
- RAS
- RPI

### Steps to Reproduce

1. Download nih nifti example: [avg152T1_LR_nifti.nii.gz](https://nifti.nimh.nih.gov/nifti-1/data/avg152T1_LR_nifti.nii.gz)
(From: https://nifti.nimh.nih.gov/nifti-1/data)
This nifti's orientation is RPI - left-handed.
2. Run the following code in python:
```python
import itk

nifti_image = itk.imread('avg152T1_LR_nifti.nii.gz')
nifti_direction = itk.array_from_vnl_matrix(
nifti_image.GetDirection().GetVnlMatrix().as_matrix())
# save as a dicom
itk.imwrite(nifti_image, 'avg152T1_LR_nifti.dcm')
# read the saved dicom
dicom_image = itk.imread('avg152T1_LR_nifti.dcm')
dicom_direction = itk.array_from_vnl_matrix(
dicom_image.GetDirection().GetVnlMatrix().as_matrix())

print(nifti_direction)
# [[ 1. 0. 0.]
# [ 0. -1. 0.]
# [ 0. 0. 1.]]

print(dicom_direction)
# [[ 1. 0. 0.]
# [ 0. -1. 0.]
# [ 0. 0. -1.]]

```
3. Open in itk-snap/slicer the original nifti and then the dicom. The dicom is flipped up-down.

### Expected behavior
1. The direction matrix should be the same
2. The saved dicom image should not be flipped up-down

Actually, 1 leads to 2.
I should emphasize that this is not a bug of slicer nor itk-snap. The bug is in our dicom writer.

### Actual behavior

1. The direction matrices are different. The original direction matrix of the nifti (RPI):
```none
[[ 1. 0. 0.]
[ 0. -1. 0.]
[ 0. 0. 1.]]
```
The dicom's direction matrix (corresponding to RPS):
```none
[[ 1. 0. 0.]
[ 0. -1. 0.]
[ 0. 0. -1.]]
```
2. In itk-snap, the original nifti is:
![image](https://user-images.githubusercontent.com/36337649/79563505-9fffd180-80b5-11ea-97de-3b659601b71c.png)
The saved dicom is flipped in S-I axis:
![image](https://user-images.githubusercontent.com/36337649/79563545-ae4ded80-80b5-11ea-9a34-066009148331.png)

### Reproducibility

100% for saving an image with left-handed orientation in multi-frame dicom, both single file (as shown here) and a series of 2d slices.
In general, it's relevant for 3d images with left-handed orientations (50% of all possible orientations).

### Versions
Itk 5.2.0

### Environment
Python 3.9.4, macOS Big Sur (probably irrelevant)

### Additional Information
The issue and some possible solutions have already been discussed here:
https://discourse.itk.org/t/nifti-rpi-orientation-file-exported-to-dicom-wrong-orientation/1612

### Explanation of the bug
The dicom orientation is encoded in the 6 numbers of [*Image Orientation (Patient)*](http://dicom.nema.org/medical/dicom/current/output/chtml/part03/sect_C.7.6.2.html) tag.
These 6 numbers correspond to the first and second column of the direction matrix. Let's call these columns u, v (vectors of length 3).
When saving the dicom, the 3rd column of `nifti_direction` - n, is discarded. When reading the dicom, it is inferred as the cross product of u and v:
* n = u x v

However, in this way it can never be (-n)!

### Possible fixes
1. Raise an error when saving a dicom with a left-handed orientation.
The orientation is easy to check: the determinant of the direction matrix (a rotation matrix) is either +1 or (-1).
+1 - right-handed orientation, go ahead
(-1) - error.
2. As Mihail Isakov [suggested](https://discourse.itk.org/t/nifti-rpi-orientation-file-exported-to-dicom-wrong-orientation/1612/2), if the image is left-handed - reorient it to the nearest right handed orientation.
3. Encode the orientation direction in the sign of [*Spacing Between Slices*](http://dicom.nema.org/medical/dicom/current/output/chtml/part03/sect_C.8.4.15.html) tag

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.