Metadata-Version: 2.4
Name: napari-ome-zarr-navigator
Version: 0.4.0
Summary: A plugin to browse OME-Zarr plates by conditions and load images, labels and features from ROIs
Project-URL: Homepage, https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator
Project-URL: Bug Tracker, https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/issues
Project-URL: Documentation, https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator#README.md
Project-URL: Source Code, https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator
Project-URL: User Support, https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/issues
Author-email: Fabio Steffen <fabio.steffen@uzh.ch>, Joel Luethi <joel.luethi@uzh.ch>
License: BSD-3-Clause
License-File: LICENSE
Classifier: Development Status :: 2 - Pre-Alpha
Classifier: Framework :: napari
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: BSD License
Classifier: Operating System :: OS Independent
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Topic :: Scientific/Engineering :: Image Processing
Requires-Python: <3.15,>=3.11
Requires-Dist: magicgui
Requires-Dist: napari-ome-zarr<0.8
Requires-Dist: ngio<0.6,>=0.5
Requires-Dist: numcodecs!=0.14.0,!=0.14.1,!=0.16
Requires-Dist: numpy
Requires-Dist: ome-zarr
Requires-Dist: qtpy
Requires-Dist: scikit-image
Requires-Dist: wget
Provides-Extra: testing
Requires-Dist: napari; extra == 'testing'
Requires-Dist: pyqt6; extra == 'testing'
Requires-Dist: pytest; extra == 'testing'
Requires-Dist: pytest-cov; extra == 'testing'
Requires-Dist: pytest-qt; extra == 'testing'
Requires-Dist: qtpy; extra == 'testing'
Description-Content-Type: text/markdown

# napari-ome-zarr-navigator <img align="right" height="150" src="https://raw.githubusercontent.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/master/docs/images/navigator_logo.png">

[![License BSD-3](https://img.shields.io/pypi/l/napari-ome-zarr-navigator.svg?color=green)](https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/raw/main/LICENSE)
[![PyPI](https://img.shields.io/pypi/v/napari-ome-zarr-navigator.svg?color=green)](https://pypi.org/project/napari-ome-zarr-navigator)
[![Python Version](https://img.shields.io/pypi/pyversions/napari-ome-zarr-navigator.svg?color=green)](https://python.org)
[![tests](https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/actions/workflows/test_and_deploy.yml/badge.svg?branch=main)](https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/actions)
[![codecov](https://codecov.io/gh/fractal-napari-plugins-collection/napari-ome-zarr-navigator/graph/badge.svg?token=Mg1081BoRA)](https://codecov.io/gh/fractal-napari-plugins-collection/napari-ome-zarr-navigator)

A plugin to interact with OME-Zarr images and plates. Enables integrating OME-Zarrs & [Fractal tables](https://biovisioncenter.github.io/ngio/stable/table_specs/overview/), browsing plates by conditions, loading ROIs from ROI tables, loading features from feature tables, annotating new ROI tables and saving labels back into OME-Zarr.

<p align="center">
  <a href="https://www.youtube.com/watch?v=aUlbiQJXx_I">
    <img src="https://img.youtube.com/vi/aUlbiQJXx_I/maxresdefault.jpg" width="1080" alt="Watch the demo">
  </a>
</p>
(click the picture above to see the walkthrough video)


## Usage

### Plate Browser

The Plate Browser loads an OME-Zarr plate from the local filesystem or via authenticated HTTPS (e.g. a [Fractal Server](https://fractal-analytics-platform.github.io/) instance). It also auto-detects plates opened via [napari-ome-zarr](https://github.com/ome/napari-ome-zarr). The Plate Browser lets you zoom to a selected well ("Go to well"), which draws a bounding box and centers the camera on that well.

<img width="1624" alt="plate_browser_go_to_well" src="https://github.com/user-attachments/assets/c83c1daf-a5d2-41b7-8685-564f80eb0122" />

Using [ngio condition tables](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/condition_table/), the Plate Browser can filter the well list to any subset defined by one or more conditions. Plate-level condition tables (fast) and image-level condition tables (slower, aggregated on the fly) are both supported.

<img width="1512" alt="plate_browser_filtering" src="https://github.com/user-attachments/assets/7938ed80-31ee-4e58-b896-20ed92ea6508" />

### ROI Loader

The ROI Loader can be launched directly from napari's *Plugins* menu (standalone) or by selecting a well in the Plate Browser ("Select ROI to load"). It supports:

- Loading images from different multiplexing cycles / acquisitions
- Loading any ROI from [ROI tables](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/roi_table/), or the whole image when no ROI table is selected
- Loading label images
- Loading feature measurements from [feature tables](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/feature_table/)
- **Multi-resolution (lazy)** mode — streams a full dask pyramid, optimal for large images and remote data
- **Fixed resolution** mode — loads a single numpy array, optimal for 3D images and downstream tools in napari that don't handle multi-resolution layers (e.g. the label layer needs to be loaded as fixed resolution for using it in the classifier)

Once a ROI has been loaded for one well, "Load selected ROI for additional well(s)" reuses the same settings for any further wells selected in the Plate Browser.

<img width="1624" alt="roi_loader" src="https://github.com/user-attachments/assets/ddd8268f-52ae-4a43-9c00-f52df4422ba3" />

This plugin is tested with OME-Zarr files generated by [Fractal](https://fractal-analytics-platform.github.io/) and is designed to work with any OME-Zarr ≥ v0.4. The feature loading workflow is optimised for use with the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier).

### ROI Annotator

The ROI Annotator can be launched from napari's *Plugins* menu (standalone, for single images), from the ROI Loader, or from the Plate Browser ("Annotate ROIs", for individual wells). It writes [ROI tables](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/roi_table/) and [Masking ROI tables](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/masking_roi_table/) back to the OME-Zarr store using [ngio](https://biovisioncenter.github.io/ngio/stable/).

#### Interactive ROI annotation

Draw rectangular ROIs by hand on any loaded image. Select **Initialize empty ROI layer**, click **Initialize ROI Layer** to create a shapes layer in drawing mode, then draw rectangles. The table name, backend (CSV, JSON, Parquet, AnnData), and overwrite flag can all be configured before saving. Only rectangle annotations are supported.

<img width="1726" alt="interactive_roi_table_creation" src="https://github.com/user-attachments/assets/c91c7496-27a2-4236-a8bd-c13c5002070b" />


> **Limitations (napari shapes layer)**
> - Interactively drawn ROIs are always 2D — napari shapes cannot represent 3D extents.
> - Each ROI covers a single time point — shapes do not span multiple frames.

#### ROI creation from labels (Masking ROI table)

Select **Masking ROI layer**, choose a label layer that has been loaded into the viewer for a given OME-Zarr image (e.g. loaded by the ROI loader above), and click **Calculate masking ROI table**. The annotator computes one bounding-box ROI per labelled object using [ngio's `compute_masking_roi`](https://biovisioncenter.github.io/ngio/stable/) and adds the results as a shapes layer for review. Z-extents are inferred from the label data and stored as shape properties; 3D bounding boxes are supported when the image is 3D. Clicking **Save ROI Table** writes the result as a [Masking ROI table](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/masking_roi_table/) to the OME-Zarr, if a corresponding label is available.

<img width="1726" alt="masking_roi_table_creation" src="https://github.com/user-attachments/assets/0caeea55-f080-4b19-b5e8-da89d6ddf8c2" />


#### Remote OME-Zarr stores

The annotator opens images from local files or authenticated HTTPS stores. Saving back to a remote store is not supported (the store is read-only from the plugin's perspective). When a remote image is loaded, a **Save to folder** picker appears so the table can be written to a local directory instead.


### Save Labels

The Save Labels widget can be launched from napari's *Plugins* menu (standalone, for single images) or from the ROI Loader ("Save label layer to OME-Zarr"). It saves any napari label layer back to an OME-Zarr image as a label image using [ngio](https://biovisioncenter.github.io/ngio/stable/), with optional [Masking ROI table](https://biovisioncenter.github.io/ngio/stable/table_specs/table_types/masking_roi_table/) generation.

Three write modes cover the main use cases:

- **Save as new label** — creates the label for the first time; fails if the label already exists
- **Edit existing label** — patches only the pixels in the currently loaded ROI; every pixel outside that region stays unchanged (intended for proof-reading individual ROIs)
- **Reset existing label** — overwrites the full label with the current layer

#### Creating new labels

Load an image with the ROI Loader, segment or annotate it in napari, then open the Save Labels widget. Select the label layer, choose a name, and click **Save label to OME-Zarr**. The pixel size metadata is taken from the napari label layer. Optionally enable **Save masking ROI table** to derive per-object bounding-box ROIs at the same time.

<img width="1631" alt="save_new_label" src="https://github.com/user-attachments/assets/bda2e077-155c-4a08-a1c1-e79673841ab4" />

#### Proof-reading labels ROI by ROI

Load a single ROI using the ROI Loader, edit the label layer in napari, then switch the write mode to **Edit existing label** and save. Only the pixels within the loaded ROI are written back; the rest of the label is untouched. Importantly, neither the ROI loader nor the label saving perform masking. Thus, if you load masking ROI tables, be aware that labels outside the mask will still load and you should not remove them, otherwise they get removed from the final label image.

<img width="1631" alt="edit_label" src="https://github.com/user-attachments/assets/49495b59-af2c-45d8-b329-90d2236fa020" />

#### Remote OME-Zarr stores

When the source image is on an authenticated remote store (e.g. served by the [Fractal data service](https://github.com/fractal-analytics-platform/fractal-data)), the label cannot be written back to the read-only remote container. In this case a **Local output** folder picker appears and the label is saved there instead.


----------------------------------


## Test data

Test & sample data is available at https://zenodo.org/records/20429951


## Installation

### Via pixi (recommended)

[pixi](https://pixi.sh) manages all Python and system dependencies in a single step:

```bash
git clone https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator
cd napari-ome-zarr-navigator
pixi run napari
```

To launch with the full feature-analysis environment (adds [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier) and [napari-feature-visualization](https://github.com/fractal-napari-plugins-collection/napari-feature-visualization)):

```bash
pixi run --frozen napari-fractal
```

### Via pip

Install into an existing Python ≥ 3.11 environment with [napari] already present:

```bash
pip install napari-ome-zarr-navigator
```

For a fresh environment we recommend [miniforge](https://github.com/conda-forge/miniforge):

```bash
conda create -n napari-ome-zarr python=3.12 napari pyqt -c conda-forge
conda activate napari-ome-zarr
pip install napari-ome-zarr-navigator
napari
```

Optionally also install additional plugins like `napari-feature-classifier` and `napari-feature-visualization`, as in:
```bash
pip install napari-feature-classifier napari-feature-visualization
```

## Contributing

Contributions are very welcome. Tests can be run with `pixi run test`; please ensure coverage stays the same before submitting a pull request.

## License

Distributed under the terms of the [BSD-3] license,
"napari-ome-zarr-navigator" is free and open source software

## Issues

If you encounter any problems, please [file an issue] along with a detailed description.

[napari]: https://github.com/napari/napari
[BSD-3]: http://opensource.org/licenses/BSD-3-Clause
[file an issue]: https://github.com/fractal-napari-plugins-collection/napari-ome-zarr-navigator/issues
[pip]: https://pypi.org/project/pip/
