brainhops.io.transformations.fsl
Readers for FSL transformation formats.
FSL expresses its transformations in scaled-mm coordinates: voxel
indices scaled by pixel size, with the x-axis flipped when the
voxel-to-world affine has a positive determinant. FLIRT stores a linear
transformation as a .mat matrix, and FNIRT stores a non-linear
transformation as a NIfTI warp field or coefficient field.
Classes
FslCoordinateSystem
magic
FslCoordinateSystem(
name: str = "fsl",
axes: tuple[SpaceAxis, SpaceAxis, SpaceAxis] = (
SpaceAxis(name="x", unit="mm"),
SpaceAxis(name="y", unit="mm"),
SpaceAxis(name="z", unit="mm"),
),
)
Bases: SpatialCoordinateSystem3D
The FSL "scaled-mm" coordinate system of an image.
Coordinates are voxel indices scaled by the pixel sizes, with the x-axis flipped when the voxel-to-world affine has a positive determinant. FLIRT and FNIRT express their transformations in this coordinate system. Each image has its own scaled-mm system, because the scaling and the flip depend on that image's pixel sizes and shape.
Attributes
order
class-attribute
instance-attribute
order: Literal['C', 'F'] | None = None
The memory order of the array the coordinates index: "C" (the
last axis changes fastest), "F" (the first axis does), or None
when it is not specified. Only an ArrayCoordinateSystem indexes
an array, so any other system refuses an order; the field is
declared here so that every class can be called with it, and pass it
on to the C- or F-ordered class it selects.
ndim
property
ndim: int | None
The number of axes, or None when the system is open.
A closed system has exactly len(axes) axes. An open system,
whose axes hold ..., has an unknown number of axes, and its
ndim is None. This is
AxisSequence.ndim
of its axes.
Methods:
from_dict
classmethod
Create an instance of the class from a dictionary-like object.
Only keys in the dictionary that match keyword-like fields of
this class, or the keywords its constructor takes without
storing them (its InitVars, such as the matrix= of an
Affine), will be used. Other keys are ignored, but see
from_other,
which refuses them.
Additional positional and/or keyword arguments can be provided, and will take precedence over the values in the dictionary.
A key naming a field that this class fixes (a field that cannot
be passed to its constructor) is checked instead of used: a
dictionary that sets it to anything other than None or the
value of this class is refused with a ValueError.
from_instance
classmethod
Create an instance of the class from an instance of a similar class.
Only attributes of the other instance that match keyword-like
fields of this class will be used. An attribute that is None
is unset, and leaves the default of this class in place.
Additional positional and/or keyword arguments can be provided, and will take precedence over the attributes in the instance.
Unless the other instance is already an instance of this class,
an attribute naming a field that this class fixes (a field that
cannot be passed to its constructor) is checked instead of used:
an instance that sets it to anything other than None or the
value of this class is refused with a ValueError. A
generic Axis whose orientation is right-to-left, for example,
cannot be read as a LeftToRightAxis.
from_other
classmethod
Create an instance of the class from any object that can be interpreted as a dictionary, or an instance of a similar class, or an arguments to be passed to the constructor.
A similar class is this class or one of its parents within the
data model, or another member of a polymorphic family this class
belongs to: calling a polymorphic class such as Axis builds the
subclass its arguments select, so a "generic" axis is usually an
instance of a sibling (a RightToLeftAxis, a TimeAxis) rather
than of a parent. Any other object, including an instance of a
parent that is not a data model (such as a plain object), is
passed to the constructor.
Unlike from_dict,
a dictionary with a key that matches no field of this class is
refused with a TypeError naming the keys, so that a
misspelt key is not silently dropped.
expand
The closed system of ndim axes that this system describes.
The axes are expanded by
AxisSequence.expand:
in an open system, ... is replaced with as many unknown
Axis() as needed to reach ndim axes. The class is called
again with the closed axes, and the other fields, the name
included, are kept: the result is of this class, or of the
subclass that the closed axes select from it (an
ArrayCoordinateSystem closed to two axes is an
ArrayCoordinateSystem2D). Each unknown Axis() is first read as
the type of axis the class declares, so a SpatialCoordinateSystem
closed to three axes has three spatial axes, and is a
SpatialCoordinateSystem3D. Use it once the number of axes is
known, for instance from the shape of the data.
Example
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
ndim
|
int
|
The number of axes. |
required |
Returns:
| Type | Description |
|---|---|
CoordinateSystem
|
A closed system of |
Raises:
| Type | Description |
|---|---|
ValueError
|
If |
TypeError
|
If |
restrict
restrict(refs: Iterable[int | str]) -> CoordinateSystem
The system of the axes at some positions of this system.
The axes are restricted by
AxisSequence.restrict:
a reference is a position in the space or a name, and a position
of an open system that falls among the axes that ... stands
for gives an unknown Axis(). The axes are listed in the order
of refs. The result describes a different space, so the class
and the name of this system are not carried over: it is the
closed system that CoordinateSystem(axes=...) builds from the
restricted axes, which is a CoordinateSystem2D, an
RASCoordinateSystem, ... when the axes select one.
Example
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
refs
|
iterable of int or str
|
The positions or names of the axes to keep. |
required |
Returns:
| Type | Description |
|---|---|
CoordinateSystem
|
A closed system of |
Raises:
| Type | Description |
|---|---|
(ValueError, IndexError, TypeError)
|
As
|
embed
embed(
positions: Iterable[int], ndim: int | None = None
) -> CoordinateSystem
The system of a larger space in which this system's axes sit.
This is the inverse of restrict. The axes are embedded by
AxisSequence.embed:
axis j of this system sits at positions[j] of the result,
and every other position holds an unknown Axis(). The result
describes a different space, so the class and the name of this
system are not carried over: it is the system that
CoordinateSystem(axes=...) builds from the embedded axes -- a
plain, open CoordinateSystem when ndim is not given, and the
closed system the axes select when it is.
Example
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
positions
|
iterable of int
|
The non-negative position of each axis in the larger space. |
required |
ndim
|
int
|
The number of axes of the larger space. When it is not given,
the number is unknown, and the result ends with |
None
|
Returns:
| Type | Description |
|---|---|
CoordinateSystem
|
A system that is closed when |
Raises:
| Type | Description |
|---|---|
(ValueError, TypeError)
|
As
|
compatible_with
compatible_with(other: CoordinateSystem | None) -> bool
Whether self and other could describe the same space.
Two systems are compatible when their axes are
AxisSequence.compatible_with
each other: some choice of the axes that each ... stands for
makes them match axis by axis, each pair being
Axis.compatible_with.
Only the axes are compared, not the names of the systems. None
is read as a system about which nothing is known, which is
compatible with every system.
For two closed systems, this asks for the same number of axes,
pairwise compatible. Unlike ==, an unknown Axis() matches
any axis. The relation is symmetric, but not transitive.
Example
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
other
|
CoordinateSystem or None
|
The system to compare with. |
required |
Returns:
| Type | Description |
|---|---|
bool
|
Whether the two systems could describe the same space. |
Raises:
| Type | Description |
|---|---|
TypeError
|
If |
FlirtTransform
magic
FlirtTransform(flirt_matrix: ArrayLike | None = None, moving: _ImageLike | None = None, reference: _ImageLike | None = None, _matrix: Deactivated[None], *, _input: CoordinateSystem = RASmm(), _output: CoordinateSystem = RASmm())
Bases: FslAffineFormat, FlirtMatrixParser, Affine, FileBasedTransformation
A linear transformation stored in a FLIRT .mat file.
A FLIRT matrix maps moving-image scaled-mm coordinates to
reference-image scaled-mm coordinates. This reader exposes it as an
affine whose matrix maps reference-image world (RAS) coordinates to
moving-image world (RAS) coordinates, which is the direction the data
model uses to resample a moving image onto a reference.
The reference and moving images must be supplied, because the .mat
file carries no image geometry. They may be passed as keyword
arguments to load or from_file (reference=, moving=), or set
on the object before its matrix is read.
Attributes
PREFIXES
class-attribute
PREFIXES: tuple[str, ...] = ()
Filename prefixes required by this parser, e.g. ("y_", "iy_").
An empty tuple means "no constraint". A parser that constrains the prefix is more specific than one that does not, and wins ties.
Declaring EXTENSIONS and PREFIXES separately states the
cross-product implicitly, which is how these conventions actually
work: SPM's four names are {y_, iy_} x {.nii, .nii.gz}.
PRIORITY
class-attribute
PRIORITY: int = 0
Explicit tie-breaker, consulted only when specificity cannot decide.
Higher wins. Leave at 0 unless two parsers genuinely collide.
matrix
property
The affine matrix, of shape (No, Ni + 1), whose last column is
the translation component.
homogeneous_matrix
property
The homogeneous matrix of the affine transformation, of shape
(No + 1, Ni + 1). The last row of the homogeneous matrix is
[0, 0, ..., 1].
flirt_matrix
class-attribute
instance-attribute
The raw (4, 4) FLIRT matrix, as read from the file.
An array-like of shape (4, 4) mapping moving-image scaled-mm
coordinates to reference-image scaled-mm coordinates. It is converted
to a NumPy array and used to build the world-space affine.
moving
class-attribute
instance-attribute
The moving (source) image, a nibabel image or header, or a brainhops image.
reference
class-attribute
instance-attribute
The reference image, a nibabel image or header, or a brainhops image.
data
property
writable
The reference-RAS to moving-RAS affine, as a (3, 4) matrix.
Reading this (or the matrix view) resolves the affine from the
raw FLIRT matrix and the two image geometries. It raises when the
raw matrix is present but either image is missing, because the
affine cannot be placed in world coordinates without both.
Methods:
sniff
classmethod
sniff(
file: FileOrContentLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> type | None
On a dispatcher, identify which registered format would read
file. On a concrete format, score how confident it is that
file, in any supported form, is its own.
sniff_file
classmethod
On a dispatcher, identify which registered format would read the file (path or file-like object). On a concrete format, score how confident it is that the file is its own.
sniff_filename
classmethod
sniff_filename(
filename: FilenameLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> float
Determine if the given filename is of the type that this parser can handle.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
filename
|
FilenameLike
|
The filename to sniff. |
required |
error
|
bool | type[Exception]
|
If not False, raise an error if the filename cannot be sniffed. |
False
|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
float
|
Confidence that the filename is of this type, in |
sniff_fileobj
classmethod
Determine if the given file-like object is of the type that this parser can handle.
A text stream decodes as it is read, so content that is not text -- a binary file that shares an extension with a text format -- fails there. That is a "no", not a failure to sniff.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
file
|
IO
|
A file object open for reading. |
required |
error
|
bool | type[Exception]
|
If not False, raise an error if the file cannot be sniffed. |
False
|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
float
|
Confidence that the file is of this type, in |
sniff_content
classmethod
sniff_content(
content: ContentLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> type | None
On a dispatcher, identify which registered format would read the content (text or bytes). On a concrete format, score how confident it is that the content is its own.
sniff_bytes
classmethod
sniff_bytes(
content: BinaryContentLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> float
Determine if the given bytes are of the type that this parser can
handle, by decoding them to text and delegating to sniff_text.
Bytes that do not decode are not text, so they score NO.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
content
|
BinaryContentLike
|
The content to sniff. |
required |
error
|
bool | type[Exception]
|
If not False, raise an error if the content cannot be sniffed. |
False
|
**kwargs
|
Parser-specific options, plus |
{}
|
Returns:
| Type | Description |
|---|---|
float
|
Confidence that the content is of this type, in |
sniff_text
classmethod
On a dispatcher, identify which registered format would read the text. On a concrete format, score how confident it is that the text is its own.
sniff_line
classmethod
On a dispatcher, identify which registered format would read the line. On a concrete format, score how confident it is that the line is its own.
load
classmethod
load(other: FileOrContentLike, **kwargs) -> Self
On a dispatcher, pick the best-matching registered format and
build an instance of it from other. On a concrete format,
build an instance of this class from other, in any supported
form.
from_spec
classmethod
from_spec(spec: SourceSpec, **kwargs) -> Self
Load a structured source specification through this dispatcher.
from_file
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the file (path or file-like object). On a concrete format, build an instance of this class from the file.
from_filename
classmethod
from_filename(filename: FilenameLike, **kwargs) -> Self
Build an object from a filename.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
filename
|
FilenameLike
|
The filename to parse. |
required |
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
obj
|
The parsed object. |
from_fileobj
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the open file object. On a concrete format, build an instance of this class from the file object.
from_content
classmethod
from_content(content: ContentLike, **kwargs) -> Self
On a dispatcher, pick the best-matching registered format and build an instance of it from the content (text or bytes). On a concrete format, build an instance of this class from the content.
from_bytes
classmethod
from_bytes(content: BinaryContentLike, **kwargs) -> Self
Build an object from bytes, by decoding them to text and
delegating to from_text.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
content
|
BinaryContentLike
|
The content to parse. |
required |
**kwargs
|
Parser-specific options, plus |
{}
|
Returns:
| Type | Description |
|---|---|
obj
|
The parsed object. |
from_text
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the text. On a concrete format, build an instance of this class from the text.
from_line
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the line. On a concrete format, build an instance of this class from the line.
from_dict
classmethod
Create an instance of the class from a dictionary-like object.
Only keys in the dictionary that match keyword-like fields of
this class, or the keywords its constructor takes without
storing them (its InitVars, such as the matrix= of an
Affine), will be used. Other keys are ignored, but see
from_other,
which refuses them.
Additional positional and/or keyword arguments can be provided, and will take precedence over the values in the dictionary.
A key naming a field that this class fixes (a field that cannot
be passed to its constructor) is checked instead of used: a
dictionary that sets it to anything other than None or the
value of this class is refused with a ValueError.
from_instance
classmethod
Create an instance from an instance of a similar class.
See DataModelBase.from_instance. The map of an Affine is copied through
its matrix view, not its stored data, which a lazy wrapper
derives and a tangent (log=True) stores as its logarithm. A
tangent is copied into a tangent through its data.
from_other
classmethod
Create an instance from a file, or from anything the data model reads.
A path (str or os.PathLike), an open file, bytes or a
structured source (SourceSpec)
is read with load: on a dispatcher such as FileBasedImage,
the best-matching registered format reads it, and on a concrete
format, that format does. Any other value is handed to the data
model's own from_other, which reads a mapping field by field,
copies an instance of a similar class, and passes anything else
to the constructor.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
other
|
Any
|
A file, its content, a mapping, or an instance of a similar class. |
required |
*args
|
Constructor arguments. A file is read with keyword options only. |
()
|
|
**kwargs
|
Format-specific options when reading a file, and field values otherwise. |
{}
|
Returns:
| Type | Description |
|---|---|
obj
|
The object that was built. |
Raises:
| Type | Description |
|---|---|
TypeError
|
If positional arguments come with a file to read. |
compute
compute(
mode: ModeLike = True,
*,
simplify: SimplifyLike = "analytic",
factor: bool = False,
) -> Self
Compute the transformation, downcasting it to the cheapest compatible kind.
A concrete transformation holds a parameter, so it simplifies to
the simplest compatible kind, whose compatibility can be detected
with (almost) no overhead. For example, a transformation whose
parameter is set to None is treated as an identity.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
mode
|
[list of] name or type
|
Ignored on a leaf. |
True
|
simplify
|
simplify policy
|
How hard this leaf may be looked at. The resolved
|
"analytic"
|
factor
|
bool
|
Whether to factor this leaf into its axis-group normal form. A leaf factors by wrapping itself in a one-element sequence, so a diagonal affine (say) splits into its per-axis blocks. Off by default. |
False
|
simplify
simplify(
policy: SimplifyLike = "analytic",
*,
compute: ModeLike | bool | None = False,
) -> Self
Simplify this transformation under a per-kind policy.
Convenience sugar for
compute: t.simplify(policy, compute=mode) is
t.compute(mode, simplify=policy).
By default simplify() does no computation at all: compute=False
maps to mode=False, which composes nothing (no matrices multiplied,
no fields sampled, no lazy inverse materialized). It only downcasts
each leaf under policy (analytic by default). Pass an explicit
compute=<mode> to also compose that kind.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
policy
|
simplify policy
|
The simplify policy, in the grammar |
"analytic"
|
compute
|
[list of] name or type
|
The compose mode. The default, |
False
|
square
square(compute: bool = False, **kwargs) -> Transformation
Return the square of this transformation, self @ self.
The square is the sequence [self, self], which composes when it
is computed. It is defined for a transformation that maps a space
to itself.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
compute
|
bool
|
Whether to compute the result now rather than return it lazily. |
False
|
**kwargs
|
Passed to |
{}
|
Raises:
| Type | Description |
|---|---|
DomainError
|
If the transformation does not map a space to itself. |
to
to(
cls: Type[Self] | None = None,
*,
lossy: bool = False,
error: Type[Exception] | Exception | bool = True,
**kwargs,
) -> Self
Convert this transformation to a different type.
Conversion can be
- between type:
linear.to(Affine); or - within type:
displacement.to(coeff=True); or - both:
coords.to(DisplacementField, coeff=True).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
cls
|
type
|
The type to convert to. If |
None
|
lossy
|
bool
|
Whether to allow lossy conversions. |
False
|
error
|
bool or Exception
|
Whether to raise an error if the conversion fails:
|
True
|
**kwargs
|
dict
|
Attributes to override in the converted transform.
This allows transformations to be modified within their type.
For example, a |
{}
|
Returns:
| Type | Description |
|---|---|
Transformation
|
The converted transformation. |
FnirtWarpField
magic
FnirtWarpField(
moving: _ImageLike | None = None,
reference: _ImageLike | None = None,
deformation_type: str | None = None,
)
Bases: FslTransformationFormat, NiftiBasedTransformation, ImmutableSequence
A FNIRT non-linear transformation stored in a NIfTI file.
FNIRT writes its non-linear registration as one of two things, which a NIfTI intent code tells apart. A deformation field stores, per reference voxel, the moving location that the voxel maps to, in FSL scaled-mm coordinates. A coefficient field stores the coefficients of a B-spline basis on a coarse knot grid overlaid on the reference image. A single reader handles both, because both are B-spline fields on a regular grid and differ only in the spline degree, in whether the grid holds coefficients or sampled values, and in where the grid sits.
| Intent | Kind | Degree | Grid |
|---|---|---|---|
| 2006 | deformation | 1 | reference voxels |
| 2007 | cubic coefficients | 3 | knot grid |
| 2009 | quadratic coefficients | 2 | knot grid |
The reader keeps the field on its own grid and returns an
ImmutableSequence
of three transformations -- reference RAS to warp-grid voxels, the
displacement field, and warp-grid voxels to moving RAS -- that maps
reference-image world (RAS) coordinates to moving-image world (RAS)
coordinates. The B-spline basis is evaluated
only when the sequence is computed, so a coefficient field is never
expanded onto the reference grid at read time.
A deformation field carries the reference geometry itself, so only the moving image is required. A coefficient field carries neither image's geometry, so both the reference and the moving image are required. A discrete-cosine-transform coefficient field (intent 2008) is recognized but not supported.
Attributes
PREFIXES
class-attribute
PREFIXES: tuple[str, ...] = ()
Filename prefixes required by this parser, e.g. ("y_", "iy_").
An empty tuple means "no constraint". A parser that constrains the prefix is more specific than one that does not, and wins ties.
Declaring EXTENSIONS and PREFIXES separately states the
cross-product implicitly, which is how these conventions actually
work: SPM's four names are {y_, iy_} x {.nii, .nii.gz}.
PRIORITY
class-attribute
PRIORITY: int = 0
Explicit tie-breaker, consulted only when specificity cannot decide.
Higher wins. Leave at 0 unless two parsers genuinely collide.
header
property
writable
The NIfTI header associated with this object.
If a header was explicitly set by the user (at construction or later), this will be pointing to that header.
Otherwise, if the object was created from a NIfTI header, this will be pointing to that header.
Otherwise, if the object was created from a NIfTI image, this will be pointing to the header of that image.
Example
import nibabel as nb
image1 = nb.load("image1.nii")
image2 = nb.load("image2.nii")
NiftiParser(image1).header # `image1.header`
NiftiParser(header=image2.header).header # `image2.header`
NiftiParser(image1, header=image2.header).header # `image2.header`
obj = NiftiParser(image1)
obj.header = image2.header
obj.header # `image2.header`
data
property
writable
The image data, read lazily from image and cached, unless
it has been set explicitly.
The axes that the intent code marks as irrelevant, such as a singleton axis before a vector's components, are dropped.
system
property
writable
system: CoordinateSystem | None
The voxel coordinate system, derived from header, unless it
has been set explicitly.
The axes that the intent code marks as irrelevant are dropped.
None when there is no header to derive it from.
moving
class-attribute
instance-attribute
The moving (source) image, a nibabel image or header, or a brainhops image.
reference
class-attribute
instance-attribute
The reference image. For a deformation field this defaults to the warp file's own geometry.
deformation_type
class-attribute
instance-attribute
deformation_type: str | None = None
For a deformation field, either "absolute", "relative", or
None to infer it from the data. It has no effect on a coefficient
field.
transformations
property
writable
transformations: tuple[Transformation, ...]
The transformations mapping reference RAS to moving RAS.
Reading this property resolves the chain from the warp data and the image geometries. It raises when a required image is missing. The resolved chain is cached, and the cache is rebuilt when the moving image, the reference image, or the deformation type changes.
It is a tuple, like every chain of an
ImmutableSequence:
the resolved chain is cached and handed out as is, and a list
would let an in-place edit change the cache, leaving the warp
reporting a chain that its data no longer describes.
Methods:
sniff
classmethod
sniff(
file: FileOrContentLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> type | None
On a dispatcher, identify which registered format would read
file. On a concrete format, score how confident it is that
file, in any supported form, is its own.
sniff_file
classmethod
On a dispatcher, identify which registered format would read the file (path or file-like object). On a concrete format, score how confident it is that the file is its own.
sniff_filename
classmethod
sniff_filename(
filename: FilenameLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> float
Determine if the given filename is of the type that this parser can handle.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
filename
|
FilenameLike
|
The filename to sniff. |
required |
error
|
bool | type[Exception]
|
If not False, raise an error if the filename cannot be sniffed. |
False
|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
float
|
Confidence that the filename is of this type, in |
sniff_fileobj
classmethod
sniff_fileobj(
file: IO,
error: bool | Type[Exception] = False,
*,
version: int | None = None,
**kwargs,
) -> float
Score how confident the class is that an open file object
holds a NIfTI-1 or NIfTI-2 header, or a header of the given
version when one is passed.
sniff_content
classmethod
sniff_content(
content: ContentLike,
error: bool | Type[Exception] = False,
**kwargs,
) -> type | None
On a dispatcher, identify which registered format would read the content (text or bytes). On a concrete format, score how confident it is that the content is its own.
sniff_bytes
classmethod
Score how confident the class is that bytes hold a NIfTI-1 or NIfTI-2 header.
sniff_text
classmethod
On a dispatcher, identify which registered format would read the text. On a concrete format, score how confident it is that the text is its own.
sniff_lines
classmethod
sniff_lines(
lines: Iterable[str],
error: bool | Type[Exception] = False,
**kwargs,
) -> type | None
On a dispatcher, identify which registered format would read the lines. On a concrete format, score how confident it is that the lines are its own.
sniff_line
classmethod
On a dispatcher, identify which registered format would read the line. On a concrete format, score how confident it is that the line is its own.
load
classmethod
load(other: FileOrContentLike, **kwargs) -> Self
On a dispatcher, pick the best-matching registered format and
build an instance of it from other. On a concrete format,
build an instance of this class from other, in any supported
form.
from_spec
classmethod
from_spec(spec: SourceSpec, **kwargs) -> Self
Load a structured source specification through this dispatcher.
from_filename
classmethod
from_filename(filename: FilenameLike, **kwargs) -> Self
Build an object from a filename.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
filename
|
FilenameLike
|
The filename to parse. |
required |
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
obj
|
The parsed object. |
from_content
classmethod
from_content(content: ContentLike, **kwargs) -> Self
On a dispatcher, pick the best-matching registered format and build an instance of it from the content (text or bytes). On a concrete format, build an instance of this class from the content.
from_text
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the text. On a concrete format, build an instance of this class from the text.
from_lines
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the lines. On a concrete format, build an instance of this class from the lines.
from_line
classmethod
On a dispatcher, pick the best-matching registered format and build an instance of it from the line. On a concrete format, build an instance of this class from the line.
save
save(file: FileLike, **kwargs) -> None
Write the object to a file (path or file-like object).
This is the generic front door to the to_* family. It is named
save rather than to because to already means something else
on the data models these parsers are mixed into: Transformation.to
converts an object to another type. A writer's to was shadowed
by it on every writable transformation.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
file
|
FileLike
|
The file to write to. |
required |
**kwargs
|
Parser-specific options. |
{}
|
to_file
to_file(file: FileLike, **kwargs) -> None
Write the object to a NIfTI file.
A path is written gzipped when its name ends in .gz: a local
path is handed to nibabel by name, and a remote one is opened
through its own backend. See _save_nifti. A file-like object is
written the uncompressed NIfTI bytes.
to_filename
to_filename(filename: FilenameLike, **kwargs) -> None
Write the object to a filename.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
filename
|
FilenameLike
|
The filename to write to. |
required |
**kwargs
|
Parser-specific options. |
{}
|
to_fileobj
to_fileobj(file: IO, **kwargs) -> None
Write the uncompressed NIfTI-1 encoding of the object to an open file object.
to_text
to_text(**kwargs) -> str
Return a text version of the file.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
str
|
A text version of the file. |
to_lines
Return a text version of the file as an iterable of lines.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
Iterator[str]
|
An iterable of lines representing the object. |
to_line
to_line(**kwargs) -> str
Return a line representing the object.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
**kwargs
|
Parser-specific options. |
{}
|
Returns:
| Type | Description |
|---|---|
str
|
A line representing the object. |
from_dict
classmethod
Create an instance of the class from a dictionary-like object.
Only keys in the dictionary that match keyword-like fields of
this class, or the keywords its constructor takes without
storing them (its InitVars, such as the matrix= of an
Affine), will be used. Other keys are ignored, but see
from_other,
which refuses them.
Additional positional and/or keyword arguments can be provided, and will take precedence over the values in the dictionary.
A key naming a field that this class fixes (a field that cannot
be passed to its constructor) is checked instead of used: a
dictionary that sets it to anything other than None or the
value of this class is refused with a ValueError.
from_instance
classmethod
Create an instance from an instance of a similar class.
The data model copies the fields both classes share, by name.
A field that a file format declares for its own use -- such as
the nibabel image and header of the NIfTI and MGH formats
-- is only copied from an object of that same format: from any
other object, a field of the same name holds something else
(a NIfTI image is no MGH image), so this class's default is
kept instead. Saving a NIfTI image to MGH, or the converse,
therefore converts the data model only, and the format-specific
state is rebuilt by the writer.
from_other
classmethod
Create an instance from a file, or from anything the data model reads.
A path (str or os.PathLike), an open file, bytes or a
structured source (SourceSpec)
is read with load: on a dispatcher such as FileBasedImage,
the best-matching registered format reads it, and on a concrete
format, that format does. Any other value is handed to the data
model's own from_other, which reads a mapping field by field,
copies an instance of a similar class, and passes anything else
to the constructor.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
other
|
Any
|
A file, its content, a mapping, or an instance of a similar class. |
required |
*args
|
Constructor arguments. A file is read with keyword options only. |
()
|
|
**kwargs
|
Format-specific options when reading a file, and field values otherwise. |
{}
|
Returns:
| Type | Description |
|---|---|
obj
|
The object that was built. |
Raises:
| Type | Description |
|---|---|
TypeError
|
If positional arguments come with a file to read. |
from_nibabel
classmethod
from_nibabel(nifti: _NiftiObject, **kwargs) -> Self
Build the object from an already-loaded nibabel header or
image.
to_nibabel
Build the nibabel image that encodes this object.
Each concrete NIfTI format overrides this method to describe how its own contents map onto a NIfTI image. The other writer methods are defined in terms of this one.
sniff_nibabel
classmethod
Score how confident the class is that an already-loaded
nibabel header or image matches this format.
The header's magic number is checked first. A header that passes is then scored for how well it matches this particular format, as opposed to another kind of NIfTI-based format.
compute
compute(
mode: ModeLike = True,
*,
simplify: SimplifyLike = "analytic",
factor: bool = False,
) -> Transformation
Compute the resulting transform of the sequence of transformations.
Assuming that mode=True:
-
If all transformations in the sequence are affine-like transformations,
compute()returns an affine-like transform. -
If the first (= rightmost) transform in the sequence is a coordinate field,
compute()returns a coordinate field. -
If the first (= rightmost) transform in the sequence is an affine-like transform, and the sequence contains at least one non-affine-like transform,
compute()returns a sequence of two transformations: -
the composition of all affine-like transformations that appear before the first non-affine-like transform in the sequence, and
- the composition of all transformations in the sequence, starting from the first non-affine-like transform in the sequence.
Parameters
mode : [list of] name or type, optional
Kinds of transformations to compose.
* If True (default): compose every kind in the sequence.
* If False: compose nothing (simplify-only).
* If a (list of) transformation type(s): compose only pairs
of transformations of these kinds.
simplify : simplify policy, default="analytic"
Whether to simplify sub-transformations prior to composition,
and how hard to try to simplify them.
* "analytic" (the default) looks at the type structure only;
* "numeric" looks at the numeric values of the transformation;
* False/"none"/None disables simplification.
factor : bool, default=False
Whether to rewrite the sequence into its axis-group normal
form [grid?, F_1..F_m, Pi_perm?]: a leading grid (if any),
one axis-preserving subspace factor per group of axes that
transform together, and a trailing reindex permutation. Off
by default, so the result is byte-for-byte the plain
compute() result. Nothing is ever composed across groups;
mode still decides whether the restricted pieces inside a
group compose. A chain that creates or drops axes is left
unfactored. With mode=False nothing is computed, so
factor has nothing to act on and is ignored.
simplify
simplify(
policy: SimplifyLike = "analytic",
*,
compute: ModeLike | bool | None = False,
) -> Self
Simplify this transformation under a per-kind policy.
Convenience sugar for
compute: t.simplify(policy, compute=mode) is
t.compute(mode, simplify=policy).
By default simplify() does no computation at all: compute=False
maps to mode=False, which composes nothing (no matrices multiplied,
no fields sampled, no lazy inverse materialized). It only downcasts
each leaf under policy (analytic by default). Pass an explicit
compute=<mode> to also compose that kind.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
policy
|
simplify policy
|
The simplify policy, in the grammar |
"analytic"
|
compute
|
[list of] name or type
|
The compose mode. The default, |
False
|
square
square(compute: bool = False, **kwargs) -> Transformation
Return the square of this transformation, self @ self.
The square is the sequence [self, self], which composes when it
is computed. It is defined for a transformation that maps a space
to itself.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
compute
|
bool
|
Whether to compute the result now rather than return it lazily. |
False
|
**kwargs
|
Passed to |
{}
|
Raises:
| Type | Description |
|---|---|
DomainError
|
If the transformation does not map a space to itself. |
sqrt
sqrt(compute: bool = False, **kwargs) -> Transformation
Return the principal square root of this chain.
The chain is first simplified, which costs nothing. A chain
[P, *X, P^-1], where P^-1 is the lazy inverse of P, or both
are affines whose product is exactly the identity, is a change of
coordinates around X, and its square root is
[P, sqrt(X), P^-1]: a field stored in voxels between a
world-to-voxel affine and its lazy inverse keeps that form. Any
other chain is composed now, and the square root of the
transformation it composes to is returned.
Raises:
| Type | Description |
|---|---|
DomainError
|
If the chain does not map a space to itself, or if the square root of what it reduces to is not defined. |
NotImplementedError
|
If the chain does not compose to a single transformation. |
to
to(
cls: Type[Transformation] | None = None, **kwargs
) -> Transformation
Convert this chain to a different type or encoding.
See Transformation.to. A chain has no tangent of its own -- the tangent of a
composition is not the sum of the tangents -- so log= re-encodes
the transformation it reduces to, and anything else is refused
before it is computed:
- a chain that simplifies to one transformation is that one;
- a change of coordinates
[P, *X, P^-1](seesqrt) keeps its ends, and re-encodesX: the flow of a velocity commutes with the conjugation, so this is exact. A velocity read between a world-to-voxel affine and its inverse (|svf) is turned into its displacement that way; - a chain of affines is composed, which is cheap and exact.
Any other chain -- one with a field, between ends that do not undo
each other -- raises ConversionError.