Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
W
win-pytreat
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Container Registry
Model registry
Operate
Environments
Monitor
Incidents
Analyze
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
FSL
win-pytreat
Commits
7ee8c4a3
Commit
7ee8c4a3
authored
5 years ago
by
Paul McCarthy
Browse files
Options
Downloads
Patches
Plain Diff
nifti prac
parent
ede2fe12
No related branches found
No related tags found
No related merge requests found
Changes
2
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
getting_started/05_nifti.ipynb
+26
-19
26 additions, 19 deletions
getting_started/05_nifti.ipynb
getting_started/05_nifti.md
+25
-18
25 additions, 18 deletions
getting_started/05_nifti.md
with
51 additions
and
37 deletions
getting_started/05_nifti.ipynb
+
26
−
19
View file @
7ee8c4a3
...
@@ -12,10 +12,10 @@
...
@@ -12,10 +12,10 @@
"\n",
"\n",
"\n",
"\n",
"Building upon `nibabel`, the\n",
"Building upon `nibabel`, the\n",
"[`fsl
.data
`](https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
fsl.data.html#module-fsl.data)
\n",
"[`fsl
py
`](https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
) library
\n",
"
package
contains a number of FSL-specific classes and functions which you may\n",
"contains a number of FSL-specific classes and functions which you may
find
\n",
"
find
useful.
This is cover
ed in a different
practical
\n",
"useful.
But let's start with `nibabel` - `fslpy` is introduc
ed in a different\n",
"(`advanced_topics/08_fslpy.ipynb`).\n",
"
practical
(`advanced_topics/08_fslpy.ipynb`).\n",
"\n",
"\n",
"\n",
"\n",
"## Contents\n",
"## Contents\n",
...
@@ -50,8 +50,8 @@
...
@@ -50,8 +50,8 @@
"# display header object\n",
"# display header object\n",
"imhdr = imobj.header\n",
"imhdr = imobj.header\n",
"\n",
"\n",
"# extract data (as a
n
numpy array)\n",
"# extract data (as a numpy array)\n",
"imdat = imobj.get_data()
.astype(float)
\n",
"imdat = imobj.get_
f
data()\n",
"print(imdat.shape)"
"print(imdat.shape)"
]
]
},
},
...
@@ -59,26 +59,28 @@
...
@@ -59,26 +59,28 @@
"cell_type": "markdown",
"cell_type": "markdown",
"metadata": {},
"metadata": {},
"source": [
"source": [
"> Make sure you use the full filename, including the .nii.gz extension.\n",
"> Make sure you use the full filename, including the
`
.nii.gz
`
extension.\n",
"\n",
"
> `fslpy` provides FSL-like automatic file suffix detection though.
\n",
"\n",
"\n",
"> We use the expandvars() function above to insert the FSLDIR\n",
"> We use the
`
expandvars()
`
function above to insert the FSLDIR\n",
"> environmental variable into our string. This function is\n",
"> environmental variable into our string. This function is\n",
"> discussed more fully in the file management practical.\n",
"> discussed more fully in the file management practical.\n",
"\n",
"\n",
"Reading the data off the disk is not done until `get_data()` is called.\n",
"Reading the data off the disk is not done until `get_
f
data()` is called.\n",
"\n",
"\n",
"> Pitfall:\n",
"> Pitfall:\n",
">\n",
">\n",
"> The option `mmap=False`
is necessary as turns off memory mapping,
\n",
"> The option `mmap=False`
disables memory mapping, which would otherwise be
\n",
">
which otherwise would be
invoked for uncompressed NIfTI files but not for\n",
"> invoked for uncompressed NIfTI files but not for
compressed files. Since
\n",
">
compressed files. Since
some functionality behaves differently on memory\n",
"> some functionality behaves differently on memory
mapped objects, it is
\n",
">
mapped objects, it is
advisable to turn this off.\n",
"> advisable to turn this off
unless you specifically want it
.\n",
"\n",
"\n",
"Once the data is read into a numpy array then it is easily manipulated.\n",
"Once the data is read into a numpy array then it is easily manipulated.\n",
"\n",
"\n",
"> We recommend converting it to float at the start to avoid problems with\n",
"> The `get_fdata` method will return floating point data, regardless of the\n",
"> integer arithmetic and overflow, though this is not compulsory.\n",
"> underlying image data type. If you want the image data in the type that it\n",
"> is stored (e.g. integer ROI labels), then use\n",
"> `imdat = np.asanyarray(imobj.dataobj)` instead.\n",
"\n",
"\n",
"---\n",
"---\n",
"\n",
"\n",
...
@@ -155,6 +157,7 @@
...
@@ -155,6 +157,7 @@
"<a class=\"anchor\" id=\"writing-images\"></a>\n",
"<a class=\"anchor\" id=\"writing-images\"></a>\n",
"## Writing images\n",
"## Writing images\n",
"\n",
"\n",
"\n",
"If you have created a modified image by making or modifying a numpy array then\n",
"If you have created a modified image by making or modifying a numpy array then\n",
"you need to put this into a NIfTI image object in order to save it to a file.\n",
"you need to put this into a NIfTI image object in order to save it to a file.\n",
"The easiest way to do this is to copy all the header info from an existing\n",
"The easiest way to do this is to copy all the header info from an existing\n",
...
@@ -190,8 +193,9 @@
...
@@ -190,8 +193,9 @@
"> creating an entirely separate image, like a simulation.\n",
"> creating an entirely separate image, like a simulation.\n",
"\n",
"\n",
"If the voxel size of the image is different, then extra modifications will be\n",
"If the voxel size of the image is different, then extra modifications will be\n",
"required. Take a look at the `fslpy` practical for more advanced image\n",
"required. Take a look at the `fslpy` practical for some extra image\n",
"manipulation options (`advanced_topics/08_fslpy.ipynb`).\n",
"manipulation options, including cropping and resampling\n",
"(`advanced_topics/08_fslpy.ipynb`).\n",
"\n",
"\n",
"---\n",
"---\n",
"\n",
"\n",
...
@@ -202,7 +206,10 @@
...
@@ -202,7 +206,10 @@
"\n",
"\n",
"Write some code to read in a 4D fMRI image (you can find one\n",
"Write some code to read in a 4D fMRI image (you can find one\n",
"[here](http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz) if you don't have one\n",
"[here](http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz) if you don't have one\n",
"handy), calculate the tSNR and then save the 3D result."
"handy), calculate the tSNR and then save the 3D result.\n",
"\n",
"> The tSNR of a time series signal is simply its mean divided by its standard\n",
"> deviation."
]
]
},
},
{
{
...
...
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
# NIfTI images and python
# NIfTI images and python
The
[
`nibabel`
](
http://nipy.org/nibabel/
)
module is used to read and write NIfTI
The
[
`nibabel`
](
http://nipy.org/nibabel/
)
module is used to read and write NIfTI
images and also some other medical imaging formats (e.g., ANALYZE, GIFTI,
images and also some other medical imaging formats (e.g., ANALYZE, GIFTI,
MINC, MGH).
`nibabel`
is included within the FSL python environment.
MINC, MGH).
`nibabel`
is included within the FSL python environment.
Building upon
`nibabel`
, the
Building upon
`nibabel`
, the
[
`fsl
.data
`
](
https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
fsl.data.html#module-fsl.data
)
[
`fsl
py
`
](
https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
)
library
package
contains a number of FSL-specific classes and functions which you may
contains a number of FSL-specific classes and functions which you may
find
find
useful.
This is cover
ed in a different
practical
useful.
But let's start with
`nibabel`
-
`fslpy`
is introduc
ed in a different
(
`advanced_topics/08_fslpy.ipynb`
).
practical
(
`advanced_topics/08_fslpy.ipynb`
).
## Contents
## Contents
*
[
Reading images
](
#reading-images
)
*
[
Reading images
](
#reading-images
)
*
[
Header info
](
#header-info
)
*
[
Header info
](
#header-info
)
*
[
Voxel sizes
](
#voxel-sizes
)
*
[
Voxel sizes
](
#voxel-sizes
)
*
[
Coordinate orientations and mappings
](
#orientation-info
)
*
[
Coordinate orientations and mappings
](
#orientation-info
)
*
[
Writing images
](
#writing-images
)
*
[
Writing images
](
#writing-images
)
*
[
Exercise
](
#exercise
)
*
[
Exercise
](
#exercise
)
---
---
<a
class=
"anchor"
id=
"reading-images"
></a>
<a
class=
"anchor"
id=
"reading-images"
></a>
## Reading images
## Reading images
It is easy to read an image:
It is easy to read an image:
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
import numpy as np
import numpy as np
import nibabel as nib
import nibabel as nib
import os.path as op
import os.path as op
filename = op.expandvars('${FSLDIR}/data/standard/MNI152_T1_1mm.nii.gz')
filename = op.expandvars('${FSLDIR}/data/standard/MNI152_T1_1mm.nii.gz')
imobj = nib.load(filename, mmap=False)
imobj = nib.load(filename, mmap=False)
# display header object
# display header object
imhdr = imobj.header
imhdr = imobj.header
# extract data (as a
n
numpy array)
# extract data (as a numpy array)
imdat = imobj.get_data()
.astype(float)
imdat = imobj.get_
f
data()
print(imdat.shape)
print(imdat.shape)
```
```
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
> Make sure you use the full filename, including the .nii.gz extension.
> Make sure you use the full filename, including the
`
.nii.gz
`
extension.
> `fslpy` provides FSL-like automatic file suffix detection though.
> We use the expandvars() function above to insert the FSLDIR
> We use the
`
expandvars()
`
function above to insert the FSLDIR
> environmental variable into our string. This function is
> environmental variable into our string. This function is
> discussed more fully in the file management practical.
> discussed more fully in the file management practical.
Reading the data off the disk is not done until
`get_data()`
is called.
Reading the data off the disk is not done until
`get_
f
data()`
is called.
> Pitfall:
> Pitfall:
>
>
> The option `mmap=False`
is necessary as turns off memory mapping,
> The option `mmap=False`
disables memory mapping, which would otherwise be
>
which otherwise would be
invoked for uncompressed NIfTI files but not for
> invoked for uncompressed NIfTI files but not for
compressed files. Since
>
compressed files. Since
some functionality behaves differently on memory
> some functionality behaves differently on memory
mapped objects, it is
>
mapped objects, it is
advisable to turn this off.
> advisable to turn this off
unless you specifically want it
.
Once the data is read into a numpy array then it is easily manipulated.
Once the data is read into a numpy array then it is easily manipulated.
> We recommend converting it to float at the start to avoid problems with
> The `get_fdata` method will return floating point data, regardless of the
> integer arithmetic and overflow, though this is not compulsory.
> underlying image data type. If you want the image data in the type that it
> is stored (e.g. integer ROI labels), then use
> `imdat = np.asanyarray(imobj.dataobj)` instead.
---
---
<a
class=
"anchor"
id=
"header-info"
></a>
<a
class=
"anchor"
id=
"header-info"
></a>
## Header info
## Header info
There are many methods available on the header object - for example, look at
There are many methods available on the header object - for example, look at
`dir(imhdr)`
or
`help(imhdr)`
or the
[
nibabel webpage about NIfTI
`dir(imhdr)`
or
`help(imhdr)`
or the
[
nibabel webpage about NIfTI
images
](
http://nipy.org/nibabel/nifti_images.html
)
images
](
http://nipy.org/nibabel/nifti_images.html
)
<a
class=
"anchor"
id=
"voxel-sizes"
></a>
<a
class=
"anchor"
id=
"voxel-sizes"
></a>
### Voxel sizes
### Voxel sizes
Dimensions of the voxels, in mm, can be found from:
Dimensions of the voxels, in mm, can be found from:
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
voxsize = imhdr.get_zooms()
voxsize = imhdr.get_zooms()
print(voxsize)
print(voxsize)
```
```
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
<a
class=
"anchor"
id=
"orientation-info"
></a>
<a
class=
"anchor"
id=
"orientation-info"
></a>
### Coordinate orientations and mappings
### Coordinate orientations and mappings
Information about the NIfTI qform and sform matrices can be extracted like this:
Information about the NIfTI qform and sform matrices can be extracted like this:
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
sform = imhdr.get_sform()
sform = imhdr.get_sform()
sformcode = imhdr['sform_code']
sformcode = imhdr['sform_code']
qform = imhdr.get_qform()
qform = imhdr.get_qform()
qformcode = imhdr['qform_code']
qformcode = imhdr['qform_code']
print(qformcode)
print(qformcode)
print(qform)
print(qform)
```
```
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
You can also get both code and matrix together like this:
You can also get both code and matrix together like this:
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
affine, code = imhdr.get_qform(coded=True)
affine, code = imhdr.get_qform(coded=True)
print(affine, code)
print(affine, code)
```
```
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
---
---
<a
class=
"anchor"
id=
"writing-images"
></a>
<a
class=
"anchor"
id=
"writing-images"
></a>
## Writing images
## Writing images
If you have created a modified image by making or modifying a numpy array then
If you have created a modified image by making or modifying a numpy array then
you need to put this into a NIfTI image object in order to save it to a file.
you need to put this into a NIfTI image object in order to save it to a file.
The easiest way to do this is to copy all the header info from an existing
The easiest way to do this is to copy all the header info from an existing
image like this:
image like this:
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
newdata = imdat * imdat
newdata = imdat * imdat
newhdr = imhdr.copy()
newhdr = imhdr.copy()
newobj = nib.nifti1.Nifti1Image(newdata, None, header=newhdr)
newobj = nib.nifti1.Nifti1Image(newdata, None, header=newhdr)
nib.save(newobj, "mynewname.nii.gz")
nib.save(newobj, "mynewname.nii.gz")
```
```
%% Cell type:markdown id: tags:
%% Cell type:markdown id: tags:
where
`newdata`
is the numpy array (the above is a random example only) and
where
`newdata`
is the numpy array (the above is a random example only) and
`imhdr`
is the existing image header (as above).
`imhdr`
is the existing image header (as above).
> It is possible to also just pass in an affine matrix rather than a
> It is possible to also just pass in an affine matrix rather than a
> copied header, but we *strongly* recommend against this if you are
> copied header, but we *strongly* recommend against this if you are
> processing an existing image as otherwise you run the risk of
> processing an existing image as otherwise you run the risk of
> swapping the left-right orientation. Those that have used
> swapping the left-right orientation. Those that have used
> `save_avw` in matlab may well have been bitten in this way in the
> `save_avw` in matlab may well have been bitten in this way in the
> past. Therefore, copy a header from one of the input images
> past. Therefore, copy a header from one of the input images
> whenever possible, and just use the affine matrix option if you are
> whenever possible, and just use the affine matrix option if you are
> creating an entirely separate image, like a simulation.
> creating an entirely separate image, like a simulation.
If the voxel size of the image is different, then extra modifications will be
If the voxel size of the image is different, then extra modifications will be
required. Take a look at the
`fslpy`
practical for more advanced image
required. Take a look at the
`fslpy`
practical for some extra image
manipulation options (
`advanced_topics/08_fslpy.ipynb`
).
manipulation options, including cropping and resampling
(
`advanced_topics/08_fslpy.ipynb`
).
---
---
<a
class=
"anchor"
id=
"exercises"
></a>
<a
class=
"anchor"
id=
"exercises"
></a>
## Exercise
## Exercise
Write some code to read in a 4D fMRI image (you can find one
Write some code to read in a 4D fMRI image (you can find one
[
here
](
http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz
)
if you don't have one
[
here
](
http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz
)
if you don't have one
handy), calculate the tSNR and then save the 3D result.
handy), calculate the tSNR and then save the 3D result.
> The tSNR of a time series signal is simply its mean divided by its standard
> deviation.
%% Cell type:code id: tags:
%% Cell type:code id: tags:
```
```
# Calculate tSNR
# Calculate tSNR
```
```
...
...
This diff is collapsed.
Click to expand it.
getting_started/05_nifti.md
+
25
−
18
View file @
7ee8c4a3
...
@@ -6,10 +6,10 @@ MINC, MGH). `nibabel` is included within the FSL python environment.
...
@@ -6,10 +6,10 @@ MINC, MGH). `nibabel` is included within the FSL python environment.
Building upon
`nibabel`
, the
Building upon
`nibabel`
, the
[
`fsl
.data
`
](
https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
fsl.data.html#module-fsl.data
)
[
`fsl
py
`
](
https://users.fmrib.ox.ac.uk/~paulmc/fsleyes/fslpy/latest/
)
library
package
contains a number of FSL-specific classes and functions which you may
contains a number of FSL-specific classes and functions which you may
find
find
useful.
This is cover
ed in a different
practical
useful.
But let's start with
`nibabel`
-
`fslpy`
is introduc
ed in a different
(
`advanced_topics/08_fslpy.ipynb`
).
practical
(
`advanced_topics/08_fslpy.ipynb`
).
## Contents
## Contents
...
@@ -38,31 +38,33 @@ imobj = nib.load(filename, mmap=False)
...
@@ -38,31 +38,33 @@ imobj = nib.load(filename, mmap=False)
# display header object
# display header object
imhdr = imobj.header
imhdr = imobj.header
# extract data (as a
n
numpy array)
# extract data (as a numpy array)
imdat = imobj.get_data()
.astype(float)
imdat = imobj.get_
f
data()
print(imdat.shape)
print(imdat.shape)
```
```
> Make sure you use the full filename, including the .nii.gz extension.
> Make sure you use the full filename, including the
`
.nii.gz
`
extension.
> `fslpy` provides FSL-like automatic file suffix detection though.
> We use the expandvars() function above to insert the FSLDIR
> We use the
`
expandvars()
`
function above to insert the FSLDIR
> environmental variable into our string. This function is
> environmental variable into our string. This function is
> discussed more fully in the file management practical.
> discussed more fully in the file management practical.
Reading the data off the disk is not done until
`get_data()`
is called.
Reading the data off the disk is not done until
`get_
f
data()`
is called.
> Pitfall:
> Pitfall:
>
>
> The option `mmap=False`
is necessary as turns off memory mapping,
> The option `mmap=False`
disables memory mapping, which would otherwise be
>
which otherwise would be
invoked for uncompressed NIfTI files but not for
> invoked for uncompressed NIfTI files but not for
compressed files. Since
>
compressed files. Since
some functionality behaves differently on memory
> some functionality behaves differently on memory
mapped objects, it is
>
mapped objects, it is
advisable to turn this off.
> advisable to turn this off
unless you specifically want it
.
Once the data is read into a numpy array then it is easily manipulated.
Once the data is read into a numpy array then it is easily manipulated.
> We recommend converting it to float at the start to avoid problems with
> The `get_fdata` method will return floating point data, regardless of the
> integer arithmetic and overflow, though this is not compulsory.
> underlying image data type. If you want the image data in the type that it
> is stored (e.g. integer ROI labels), then use
> `imdat = np.asanyarray(imobj.dataobj)` instead.
---
---
...
@@ -109,6 +111,7 @@ print(affine, code)
...
@@ -109,6 +111,7 @@ print(affine, code)
<a class="anchor" id="writing-images"></a>
<a class="anchor" id="writing-images"></a>
## Writing images
## Writing images
If you have created a modified image by making or modifying a numpy array then
If you have created a modified image by making or modifying a numpy array then
you need to put this into a NIfTI image object in order to save it to a file.
you need to put this into a NIfTI image object in order to save it to a file.
The easiest way to do this is to copy all the header info from an existing
The easiest way to do this is to copy all the header info from an existing
...
@@ -134,8 +137,9 @@ where `newdata` is the numpy array (the above is a random example only) and
...
@@ -134,8 +137,9 @@ where `newdata` is the numpy array (the above is a random example only) and
>
creating an entirely separate image, like a simulation.
>
creating an entirely separate image, like a simulation.
I
f the voxel size of the image is different, then extra modifications will be
I
f the voxel size of the image is different, then extra modifications will be
r
equired. Take a look at the `fslpy` practical for more advanced image
r
equired. Take a look at the `fslpy` practical for some extra image
m
anipulation options (`advanced_topics/08_fslpy.ipynb`).
m
anipulation options, including cropping and resampling
(
`advanced_topics/08_fslpy.ipynb`).
-
--
-
--
...
@@ -148,6 +152,9 @@ Write some code to read in a 4D fMRI image (you can find one
...
@@ -148,6 +152,9 @@ Write some code to read in a 4D fMRI image (you can find one
[
here
](
http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz
)
if you don't have one
[
here
](
http://www.fmrib.ox.ac.uk/~mark/files/av.nii.gz
)
if you don't have one
handy), calculate the tSNR and then save the 3D result.
handy), calculate the tSNR and then save the 3D result.
> The tSNR of a time series signal is simply its mean divided by its standard
> deviation.
```
```
# Calculate tSNR
# Calculate tSNR
```
```
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment