Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,11 @@ repos:
args: [--fix, --exit-non-zero-on-fix]
- id: ruff-format
groups: [format]
- repo: https://github.com/jsh9/pydoclint
rev: 0.12.0
hooks:
- id: pydoclint
files: ^src/
- repo: local
hooks:
- id: mypy
Expand Down
15 changes: 15 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -276,9 +276,24 @@ lint.per-file-ignores."tests/*" = [ "B024", "D", "PT" ]
lint.per-file-ignores."tests/conftest.py" = [ "E402" ]
lint.per-file-ignores."tests/test_models/test_models.py" = [ "NPY002" ]
lint.unfixable = [ "B", "BLE", "C4", "RET", "T20", "UP" ]
lint.external = [ "DOC1" ] # pydoclint parameter checks, see [tool.pydoclint]
lint.isort.required-imports = [ "from __future__ import annotations" ]
lint.pydocstyle.convention = "numpy"

[tool.pydoclint]
# Check that documented parameters match the function signature (missing or stale names, #1303),
# and that Returns/Yields sections exist. Types (they live in the signatures), order and raises are not checked.
# Docstrings with only a summary (no Parameters section) are skipped.
style = "numpy"
allow-init-docstring = true
arg-type-hints-in-docstring = false
check-return-types = false
check-yield-types = false
skip-checking-raises = true
check-class-attributes = false
check-arg-order = false
omit-stars-when-documenting-varargs = true

[tool.mypy]
# TODO: extend to "tests" once the test suite carries type annotations.
files = [ "src" ]
Expand Down
4 changes: 4 additions & 0 deletions src/spatialdata/_core/centroids.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,10 @@ def get_centroids(
return_background
If True, the centroid of the background label (0) is included in the output.

Returns
-------
The centroids, as a points element (Dask DataFrame) in the given coordinate system.

Notes
-----
For :class:`~shapely.Multipolygon`s, the centroids are the average of the centroids of the polygons that constitute
Expand Down
47 changes: 8 additions & 39 deletions src/spatialdata/_core/data_extent.py
Original file line number Diff line number Diff line change
Expand Up @@ -116,17 +116,8 @@ def get_extent(
----------
e
The SpatialData object or SpatialElement to compute the extent of.

Returns
-------
The bounding box description.

min_coordinate
The minimum coordinate of the bounding box.
max_coordinate
The maximum coordinate of the bounding box.
axes
The names of the dimensions of the bounding box.
coordinate_system
The coordinate system in which the extent is computed.
exact
Whether the extent is computed exactly or not.

Expand All @@ -145,6 +136,10 @@ def get_extent(
elements
If not `None`, only the elements with the given names are included in the computation of the extent.

Returns
-------
The bounding box description: a dictionary mapping each axis name to its `(min, max)` extent.

Notes
-----
The extent of a `SpatialData` object is the extent of the union of the extents of all its elements.
Expand Down Expand Up @@ -178,20 +173,7 @@ def _(
has_shapes: bool = True,
elements: list[str] | None = None,
) -> BoundingBoxDescription:
"""
Get the extent (bounding box) of a SpatialData object.

The resulting extent is the union of the extents of all its elements.

Parameters
----------
e
The SpatialData object.

Returns
-------
The bounding box description.
"""
"""Get the extent of a SpatialData object (the union of the extents of its elements); see :func:`get_extent`."""
new_min_coordinates_dict: dict[str, list[float]] = defaultdict(list)
new_max_coordinates_dict: dict[str, list[float]] = defaultdict(list)
mask = [has_images, has_labels, has_points, has_shapes]
Expand Down Expand Up @@ -256,20 +238,7 @@ def _get_extent_of_shapes(e: GeoDataFrame) -> BoundingBoxDescription:

@get_extent.register
def _(e: GeoDataFrame, coordinate_system: str = "global", exact: bool = True) -> BoundingBoxDescription:
"""
Get the extent (bounding box) of a SpatialData object.

The resulting extent is the union of the extents of all its elements.

Parameters
----------
e
The SpatialData object.

Returns
-------
The bounding box description.
"""
"""Get the extent of a shapes element; see :func:`get_extent`."""
_check_element_has_coordinate_system(element=e, coordinate_system=coordinate_system)
if not exact:
extent = _get_extent_of_shapes(e)
Expand Down
8 changes: 8 additions & 0 deletions src/spatialdata/_core/operations/aggregate.py
Original file line number Diff line number Diff line change
Expand Up @@ -366,6 +366,14 @@ def _aggregate_shapes(
Aggregation function to apply over grouped values. Passed to pandas.DataFrame.groupby.agg.
table_name
Name of the table optionally containing the value_key column.
fractions
Whether to weight the values by the fraction of the `values` region overlapping the `by` region.
buffer_resolution
Resolution parameter passed to the `.buffer()` method when converting circles to polygons.

Returns
-------
An AnnData object with one row per region in `by` and the aggregated values as columns.
"""
from spatialdata._core.operations.vectorize import to_polygons
from spatialdata.models import points_dask_dataframe_to_geopandas
Expand Down
2 changes: 2 additions & 0 deletions src/spatialdata/_core/operations/rasterize.py
Original file line number Diff line number Diff line change
Expand Up @@ -409,6 +409,8 @@ def _get_xarray_data_to_rasterize(
The maximum coordinates of the bounding box for the data to be rasterized.
target_sizes
A dictionary containing the target size (in pixels) of each axis after rasterization.
target_coordinate_system
The coordinate system in which `min_coordinate` and `max_coordinate` are expressed.

Returns
-------
Expand Down
8 changes: 6 additions & 2 deletions src/spatialdata/_core/query/relational_query.py
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,7 @@ def _get_joined_table_indices(

Returns
-------
The indices that of the table that match the SpatialElement indices.
The indices of the table that match the SpatialElement indices.
"""
mask = np.isin(table_instance_key_column.to_numpy(), element_indices)
if joined_indices is None:
Expand Down Expand Up @@ -891,6 +891,10 @@ def match_sdata_to_table(
unfiltered and warns, ``False`` leaves them unfiltered silently. See
:func:`spatialdata.join_spatialelement_table` for details.

Returns
-------
A new SpatialData object containing the table and the matched elements.

Notes
-----
For a graphical representation of the join operations, see the
Expand Down Expand Up @@ -965,7 +969,7 @@ def filter_by_table_query(

Returns
-------
The filtered SpatialData object.
The filtered SpatialData object.

Notes
-----
Expand Down
16 changes: 5 additions & 11 deletions src/spatialdata/_core/query/spatial_query.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,9 +65,9 @@ def _get_bounding_box_corners_in_intrinsic_coordinates(
axes
The axes that min_coordinate and max_coordinate refer to.
min_coordinate
{min_coordinate_docs}
{min_coordinate_docs}
max_coordinate
{max_coordinate_docs}
{max_coordinate_docs}
target_coordinate_system
The coordinate system the bounding box is defined in.

Expand Down Expand Up @@ -406,15 +406,9 @@ def _bounding_box_mask_points(
axes
The axes that min_coordinate and max_coordinate refer to.
min_coordinate
PLACEHOLDER
The upper left hand corners of the bounding boxes (i.e., minimum coordinates along all dimensions).
Shape: (n_boxes, n_axes) or (n_axes,) for a single box.
{min_coordinate_docs}
{min_coordinate_docs}
max_coordinate
The lower right hand corners of the bounding boxes (i.e., the maximum coordinates along all dimensions).
Shape: (n_boxes, n_axes) or (n_axes,) for a single box.
{max_coordinate_docs}

{max_coordinate_docs}

Returns
-------
Expand Down Expand Up @@ -527,7 +521,7 @@ def bounding_box_query(
-----
If the object has `points` element, depending on the number of points, it MAY suffer from performance issues. Please
consider filtering the object before calling this function by calling the `subset()` method of `SpatialData`.
"""
""" # noqa: DOC101, DOC103 (**kwargs only exists for singledispatch; nothing extra is accepted)
raise RuntimeError("Unsupported type for bounding_box_query: " + str(type(element)) + ".")


Expand Down
22 changes: 10 additions & 12 deletions src/spatialdata/_core/spatialdata.py
Original file line number Diff line number Diff line change
Expand Up @@ -2098,7 +2098,7 @@ def _gen_repr(

Returns
-------
The string representation of the SpatialData object.
The string representation of the SpatialData object.
"""
from spatialdata._utils import _natural_keys

Expand Down Expand Up @@ -2247,10 +2247,9 @@ def _gen_spatial_element_values(self) -> Generator[SpatialElement, None, None]:
"""
Generate spatial element objects contained in the SpatialData instance.

Returns
-------
Generator[SpatialElement, None, None]
A generator that yields spatial element objects contained in the SpatialData instance.
Yields
------
The spatial element objects contained in the SpatialData instance.

"""
for _, _, element in self._gen_spatial_elements():
Expand All @@ -2260,9 +2259,9 @@ def _gen_spatial_elements(self) -> Generator[tuple[str, str, SpatialElement], No
"""
Generate the images, labels, points and shapes contained in the SpatialData instance.

Returns
-------
A generator object that returns a tuple containing the type of the element, its name, and the element itself.
Yields
------
Tuples containing the type of the element, its name, and the element itself.
"""
for element_type, elements in (
("images", self.images),
Expand All @@ -2284,10 +2283,9 @@ def _gen_elements(
include_tables
Whether to also generate table elements.

Returns
-------
A generator object that returns a tuple containing the type of the element, its name, and the element
itself.
Yields
------
Tuples containing the type of the element, its name, and the element itself.
"""
yield from self._gen_spatial_elements()
if include_tables:
Expand Down
4 changes: 4 additions & 0 deletions src/spatialdata/_core/validation.py
Original file line number Diff line number Diff line change
Expand Up @@ -295,6 +295,10 @@ def __call__(
Tuple of strings identifying the parent element
expected_exception
The class of the exception to catch. Other exceptions are raised.

Returns
-------
The collector itself, to be used as a context manager.
"""
if isinstance(location, str):
location = (location,)
Expand Down
6 changes: 3 additions & 3 deletions src/spatialdata/_io/_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,12 +59,12 @@ def overwrite_coordinate_transformations_non_raster(

Parameters
----------
group: zarr.Group
group
The zarr group containing the non-raster element for which to write the transformations, e.g. the zarr group
containing sdata['points'].
axes: tuple[ValidAxis_t, ...]
axes
The list with axes names in the same order as the coordinates of the non-raster element.
transformations: MappingToCoordinateSystem_t
transformations
Mapping between names of the coordinate system and the transformations.
"""
_validate_mapping_to_coordinate_system_type(transformations)
Expand Down
10 changes: 9 additions & 1 deletion src/spatialdata/_io/io_raster.py
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,10 @@ def _is_regular_dask_chunk_grid(chunk_grid: Sequence[Sequence[int]]) -> bool:
chunk_grid
Per-axis tuple of chunk sizes, for instance as returned by ``dask_array.chunks``.

Returns
-------
Whether the chunk grid is regular.

Examples
--------
Triggers ``continue`` on the first ``if`` (single or empty axis):
Expand Down Expand Up @@ -319,7 +323,7 @@ def _write_raster(
The raster data to write.
group
The zarr group in the 'image' or 'labels' zarr group to write the raster data to.
name: str
name
The name of the raster element.
raster_format
The format used to write the raster data.
Expand Down Expand Up @@ -561,6 +565,10 @@ def _write_raster_datatree(
Compression settings as a len-1 dictionary with a single key-value {compression: compression level} pair
metadata
Additional metadata for the raster element

Returns
-------
The zarr group the raster data was written to.
"""
write_multi_scale_ngff = write_multiscale_ngff if raster_type == "image" else write_multiscale_labels_ngff
data = get_pyramid_levels(raster_data, attr="data")
Expand Down
8 changes: 8 additions & 0 deletions src/spatialdata/_io/io_shapes.py
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,10 @@ def _write_shapes_v01(shapes: GeoDataFrame, group: zarr.Group, element_format: S
The zarr group in the 'shapes' zarr group to write the shapes element to.
element_format
The format of the shapes element used to store it.

Returns
-------
The attributes (metadata) to write for the shapes element.
"""
# np.array() creates a writable copy, needed for pandas 3.0 CoW compatibility
# https://github.com/geopandas/geopandas/issues/3697
Expand Down Expand Up @@ -186,6 +190,10 @@ def _write_shapes_v02_v03(
geometry_encoding
Whether to use the WKB or geoarrow encoding for GeoParquet. See :meth:`geopandas.GeoDataFrame.to_parquet` for
details.

Returns
-------
The attributes (metadata) to write for the shapes element.
"""
from spatialdata.models._utils import TRANSFORM_KEY

Expand Down
2 changes: 2 additions & 0 deletions src/spatialdata/_io/io_zarr.py
Original file line number Diff line number Diff line change
Expand Up @@ -324,6 +324,8 @@ def _group_for_element_exists(zarr_path: Path, element_type: str, element_name:

Parameters
----------
zarr_path
Path to the Zarr store.
element_type
type of the element; must be in ["images", "labels", "points", "polygons", "shapes", "tables"].
element_name
Expand Down
6 changes: 3 additions & 3 deletions src/spatialdata/_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -200,9 +200,9 @@ def iterate_pyramid_levels(
If `None`, return the data of the pyramid level as a `DataArray`, if not None, return the specified attribute
within the `DataArray` data.

Returns
-------
A generator to iterate over the pyramid levels.
Yields
------
The pyramid levels (or their attribute `attr`, if given).
"""
scale0 = data["scale0"]
assert isinstance(scale0, DataTree)
Expand Down
4 changes: 0 additions & 4 deletions src/spatialdata/dataloader/datasets.py
Original file line number Diff line number Diff line change
Expand Up @@ -101,10 +101,6 @@ class ImageTilesDataset(Dataset[Any]):
Keyword arguments passed to :func:`spatialdata.rasterize` if `rasterize` is `True`.
This argument can be used in particular to choose the pixel dimension of the produced image tiles; please refer
to the :func:`spatialdata.rasterize` documentation for this use case.

Returns
-------
:class:`torch.utils.data.Dataset` for loading tiles from a :class:`spatialdata.SpatialData`.
"""

INSTANCE_KEY = "instance_id"
Expand Down
5 changes: 4 additions & 1 deletion src/spatialdata/datasets.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,8 @@ def blobs(
Extra coordinate space on top of the standard global coordinate space. Will have only identity transform.
n_channels
Number of channels of the image

c_coords
Channel names of the image. If given, overrides `n_channels`.

Returns
-------
Expand Down Expand Up @@ -189,6 +190,8 @@ def __init__(
Extra coordinate space on top of the standard global coordinate space. Will have only identity transform.
n_channels
Number of channels of the image
c_coords
Channel names of the image. If given, overrides `n_channels`.
"""
self.length = length
self.n_points = n_points
Expand Down
Loading
Loading