Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

12 load roi id index in order to make classifier work with one trained through the napari ome zarr navigator #15

Merged
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
2 changes: 1 addition & 1 deletion docs/_quarto.yml
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ quartodoc:
- tasks.harmony_to_ome_zarr
- tasks.stardist_segmentation
- tasks.regionprops_measurement
- tasks.label_prediction
- tasks.feature_classification
- tasks.condition_registration
- title: Input/Output
desc: "OME-ZARR reader and writer functions"
Expand Down
2 changes: 1 addition & 1 deletion docs/api/index.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ Modular processing tasks for the Opera/Operetta microscope and drug response pro
| [tasks.harmony_to_ome_zarr](tasks.harmony_to_ome_zarr.qmd#operetta_compose.tasks.harmony_to_ome_zarr) | |
| [tasks.stardist_segmentation](tasks.stardist_segmentation.qmd#operetta_compose.tasks.stardist_segmentation) | |
| [tasks.regionprops_measurement](tasks.regionprops_measurement.qmd#operetta_compose.tasks.regionprops_measurement) | |
| [tasks.label_prediction](tasks.label_prediction.qmd#operetta_compose.tasks.label_prediction) | |
| [tasks.feature_classification](tasks.feature_classification.qmd#operetta_compose.tasks.feature_classification) | |
| [tasks.condition_registration](tasks.condition_registration.qmd#operetta_compose.tasks.condition_registration) | |

## Input/Output
Expand Down
26 changes: 26 additions & 0 deletions docs/api/tasks.feature_classification.qmd
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# tasks.feature_classification { #operetta_compose.tasks.feature_classification }

`tasks.feature_classification`



## Functions

| Name | Description |
| --- | --- |
| [feature_classification](#operetta_compose.tasks.feature_classification.feature_classification) | Classify cells using the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier) and write them to the OME-ZARR |

### feature_classification { #operetta_compose.tasks.feature_classification.feature_classification }

`tasks.feature_classification.feature_classification(zarr_url, classifier_path, table_name='regionprops', label_name='nuclei')`

Classify cells using the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier) and write them to the OME-ZARR

#### Parameters

| Name | Type | Description | Default |
|-------------------|--------|----------------------------------------------------|-----------------|
| `zarr_url` | str | Path to an OME-ZARR Image | _required_ |
| `classifier_path` | str | Path to the pickled scikit-learn classifier | _required_ |
| `table_name` | str | Folder name of the measured regionprobs features | `'regionprops'` |
| `label_name` | str | Name of the labels to use for feature measurements | `'nuclei'` |
6 changes: 5 additions & 1 deletion docs/contributing.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -24,5 +24,9 @@ harmony_to_ome_zarr(
zarr_dir="operetta_plate.zarr"
)
```

:::

### Updating the documentation
1. Make your changes to the documentation under `/docs`
2. Update the function API with `quartodoc build`
3. Preview the documentation with `quarto preview`
2 changes: 1 addition & 1 deletion docs/index.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ Currently the following tasks are part of *operetta-compose*
| harmony_to_ome_zarr | Convert TIFFs which were exported from Harmony (Operetta/Opera, Perkin-Elmer) to OME-ZARR |
| stardist_segmentation | Segment cells with Stardist |
| regionprops_measurement | Take measurements using regionprops and write the features to the OME-ZARR |
| label_prediction | Make predictions on the selected wells and write them to the OME-ZARR |
| feature_classification | Classify cells using the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier) and write them to the OME-ZARR |
| condition_registration | Register the experimental conditions in the OME-ZARR |

 
Expand Down
2 changes: 1 addition & 1 deletion docs/objects.json
Original file line number Diff line number Diff line change
@@ -1 +1 @@
{"project": "operetta_compose", "version": "0.0.9999", "count": 24, "items": [{"name": "operetta_compose.tasks.harmony_to_ome_zarr.harmony_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.harmony_to_ome_zarr.html#operetta_compose.tasks.harmony_to_ome_zarr.harmony_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.tasks.harmony_to_ome_zarr", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.harmony_to_ome_zarr.html#operetta_compose.tasks.harmony_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.tasks.stardist_segmentation.stardist_segmentation", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.stardist_segmentation.html#operetta_compose.tasks.stardist_segmentation.stardist_segmentation", "dispname": "-"}, {"name": "operetta_compose.tasks.stardist_segmentation", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.stardist_segmentation.html#operetta_compose.tasks.stardist_segmentation", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement.feature_table", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement.feature_table", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement.regionprops_measurement", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement.regionprops_measurement", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement", "dispname": "-"}, {"name": "operetta_compose.tasks.label_prediction.label_prediction", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.label_prediction.html#operetta_compose.tasks.label_prediction.label_prediction", "dispname": "-"}, {"name": "operetta_compose.tasks.label_prediction", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.label_prediction.html#operetta_compose.tasks.label_prediction", "dispname": "-"}, {"name": "operetta_compose.tasks.condition_registration.condition_registration", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.condition_registration.html#operetta_compose.tasks.condition_registration.condition_registration", "dispname": "-"}, {"name": "operetta_compose.tasks.condition_registration", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.condition_registration.html#operetta_compose.tasks.condition_registration", "dispname": "-"}, {"name": "operetta_compose.io.OmeZarrUrl", "domain": "py", "role": "class", "priority": "1", "uri": "api/io.OmeZarrUrl.html#operetta_compose.io.OmeZarrUrl", "dispname": "-"}, {"name": "operetta_compose.io.read_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.read_ome_zarr.html#operetta_compose.io.read_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.parse_zarr_url", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.parse_zarr_url.html#operetta_compose.io.parse_zarr_url", "dispname": "-"}, {"name": "operetta_compose.io.convert_ROI_table_to_indices", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.convert_ROI_table_to_indices.html#operetta_compose.io.convert_ROI_table_to_indices", "dispname": "-"}, {"name": "operetta_compose.io.get_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.get_roi.html#operetta_compose.io.get_roi", "dispname": "-"}, {"name": "operetta_compose.io.load_intensity_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.load_intensity_roi.html#operetta_compose.io.load_intensity_roi", "dispname": "-"}, {"name": "operetta_compose.io.load_label_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.load_label_roi.html#operetta_compose.io.load_label_roi", "dispname": "-"}, {"name": "operetta_compose.io.labels_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.labels_to_ome_zarr.html#operetta_compose.io.labels_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.features_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.features_to_ome_zarr.html#operetta_compose.io.features_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.condition_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.condition_to_ome_zarr.html#operetta_compose.io.condition_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.utils.colorbrewer", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.colorbrewer.html#operetta_compose.utils.colorbrewer", "dispname": "-"}, {"name": "operetta_compose.utils.alpha_to_numeric", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.alpha_to_numeric.html#operetta_compose.utils.alpha_to_numeric", "dispname": "-"}, {"name": "operetta_compose.utils.numeric_to_alpha", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.numeric_to_alpha.html#operetta_compose.utils.numeric_to_alpha", "dispname": "-"}]}
{"project": "operetta_compose", "version": "0.0.9999", "count": 24, "items": [{"name": "operetta_compose.tasks.harmony_to_ome_zarr.harmony_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.harmony_to_ome_zarr.html#operetta_compose.tasks.harmony_to_ome_zarr.harmony_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.tasks.harmony_to_ome_zarr", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.harmony_to_ome_zarr.html#operetta_compose.tasks.harmony_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.tasks.stardist_segmentation.stardist_segmentation", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.stardist_segmentation.html#operetta_compose.tasks.stardist_segmentation.stardist_segmentation", "dispname": "-"}, {"name": "operetta_compose.tasks.stardist_segmentation", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.stardist_segmentation.html#operetta_compose.tasks.stardist_segmentation", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement.feature_table", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement.feature_table", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement.regionprops_measurement", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement.regionprops_measurement", "dispname": "-"}, {"name": "operetta_compose.tasks.regionprops_measurement", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.regionprops_measurement.html#operetta_compose.tasks.regionprops_measurement", "dispname": "-"}, {"name": "operetta_compose.tasks.feature_classification.feature_classification", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.feature_classification.html#operetta_compose.tasks.feature_classification.feature_classification", "dispname": "-"}, {"name": "operetta_compose.tasks.feature_classification", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.feature_classification.html#operetta_compose.tasks.feature_classification", "dispname": "-"}, {"name": "operetta_compose.tasks.condition_registration.condition_registration", "domain": "py", "role": "function", "priority": "1", "uri": "api/tasks.condition_registration.html#operetta_compose.tasks.condition_registration.condition_registration", "dispname": "-"}, {"name": "operetta_compose.tasks.condition_registration", "domain": "py", "role": "module", "priority": "1", "uri": "api/tasks.condition_registration.html#operetta_compose.tasks.condition_registration", "dispname": "-"}, {"name": "operetta_compose.io.OmeZarrUrl", "domain": "py", "role": "class", "priority": "1", "uri": "api/io.OmeZarrUrl.html#operetta_compose.io.OmeZarrUrl", "dispname": "-"}, {"name": "operetta_compose.io.read_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.read_ome_zarr.html#operetta_compose.io.read_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.parse_zarr_url", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.parse_zarr_url.html#operetta_compose.io.parse_zarr_url", "dispname": "-"}, {"name": "operetta_compose.io.convert_ROI_table_to_indices", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.convert_ROI_table_to_indices.html#operetta_compose.io.convert_ROI_table_to_indices", "dispname": "-"}, {"name": "operetta_compose.io.get_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.get_roi.html#operetta_compose.io.get_roi", "dispname": "-"}, {"name": "operetta_compose.io.load_intensity_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.load_intensity_roi.html#operetta_compose.io.load_intensity_roi", "dispname": "-"}, {"name": "operetta_compose.io.load_label_roi", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.load_label_roi.html#operetta_compose.io.load_label_roi", "dispname": "-"}, {"name": "operetta_compose.io.labels_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.labels_to_ome_zarr.html#operetta_compose.io.labels_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.features_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.features_to_ome_zarr.html#operetta_compose.io.features_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.io.condition_to_ome_zarr", "domain": "py", "role": "function", "priority": "1", "uri": "api/io.condition_to_ome_zarr.html#operetta_compose.io.condition_to_ome_zarr", "dispname": "-"}, {"name": "operetta_compose.utils.colorbrewer", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.colorbrewer.html#operetta_compose.utils.colorbrewer", "dispname": "-"}, {"name": "operetta_compose.utils.alpha_to_numeric", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.alpha_to_numeric.html#operetta_compose.utils.alpha_to_numeric", "dispname": "-"}, {"name": "operetta_compose.utils.numeric_to_alpha", "domain": "py", "role": "function", "priority": "1", "uri": "api/utils.numeric_to_alpha.html#operetta_compose.utils.numeric_to_alpha", "dispname": "-"}]}
8 changes: 4 additions & 4 deletions src/operetta_compose/__FRACTAL_MANIFEST__.json
Original file line number Diff line number Diff line change
Expand Up @@ -291,8 +291,8 @@
"docs_link": "https://leukemia-kispi.github.io/operetta-compose/"
},
{
"name": "Label prediction",
"executable_parallel": "tasks/label_prediction.py",
"name": "Feature classification",
"executable_parallel": "tasks/feature_classification.py",
"meta_parallel": {
"cpus_per_task": 1,
"mem": 4000
Expand Down Expand Up @@ -328,9 +328,9 @@
"classifier_path"
],
"type": "object",
"title": "LabelPrediction"
"title": "FeatureClassification"
},
"docs_info": "## label_prediction\nMake predictions on the selected wells and write them to the OME-ZARR\n",
"docs_info": "## feature_classification\nClassify cells using the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier)\nand write them to the OME-ZARR\n",
"docs_link": "https://leukemia-kispi.github.io/operetta-compose/"
},
{
Expand Down
4 changes: 2 additions & 2 deletions src/operetta_compose/dev/task_list.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
meta={"cpus_per_task": 1, "mem": 4000},
),
ParallelTask(
name="Label prediction",
executable="tasks/label_prediction.py",
name="Feature classification",
executable="tasks/feature_classification.py",
meta={"cpus_per_task": 1, "mem": 4000},
),
ParallelTask(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,14 @@


@validate_call
def label_prediction(
def feature_classification(
*,
zarr_url: str,
classifier_path: str,
table_name: str = "regionprops",
label_name: str = "nuclei",
) -> None:
"""Make predictions on the selected wells and write them to the OME-ZARR
"""Classify cells using the [napari-feature-classifier](https://github.com/fractal-napari-plugins-collection/napari-feature-classifier) and write them to the OME-ZARR

Args:
zarr_url: Path to an OME-ZARR Image
Expand All @@ -42,11 +42,23 @@ def label_prediction(
f"No measurements exist at the specified zarr URL in the table {table_name}."
)
features = ann_tbl.to_df()
roi_id_cols = ann_tbl.obs.drop(
columns=["roi_id", "label", "prediction"], errors="ignore"
)
if "roi_id" not in ann_tbl.obs.columns:
ann_tbl.obs["roi_id"] = f"{zarr_url}:" + roi_id_cols.astype(str).agg(
":".join, axis=1
)

# Select feature subset in expected order
features = features[clf.get_feature_names()]

# Add index columns
features_with_annotations = pd.concat(
(ann_tbl.obs[["roi_id", "label"]], features), axis=1
)
predictions = clf.predict(features_with_annotations).reset_index()
ann_tbl.obs = predictions
ann_tbl.obs = pd.concat((roi_id_cols.reset_index(drop=True), predictions), axis=1)
ann_tbl.obs_names = ann_tbl.obs.index.map(str)
ann_tbl.write_zarr(f"{zarr_url}/tables/{table_name}")
io.write_table_metadata(zarr_url, "feature_table", table_name, label_name)
Expand All @@ -56,6 +68,6 @@ def label_prediction(
from fractal_tasks_core.tasks._utils import run_fractal_task

run_fractal_task(
task_function=label_prediction,
task_function=feature_classification,
logger_name=logger.name,
)
4 changes: 2 additions & 2 deletions tests/test_compose.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from operetta_compose.tasks.harmony_to_ome_zarr import harmony_to_ome_zarr
from operetta_compose.tasks.stardist_segmentation import stardist_segmentation
from operetta_compose.tasks.regionprops_measurement import regionprops_measurement
from operetta_compose.tasks.label_prediction import label_prediction
from operetta_compose.tasks.feature_classification import feature_classification
from operetta_compose.tasks.condition_registration import condition_registration

from operetta_compose.io import OmeroNgffChannel, OmeroNgffWindow
Expand Down Expand Up @@ -78,7 +78,7 @@ def test_measure():
@pytest.mark.dependency(depends=["test_converter", "test_stardist", "test_measure"])
# @pytest.mark.skip
def test_predict():
label_prediction(
feature_classification(
zarr_url=str(ZARR_DIR.joinpath(PLATE_ZARR, "C", "3", "0")),
classifier_path=str(Path(TEST_DIR).joinpath("fixtures", "classifier.pkl")),
table_name="regionprops",
Expand Down
Loading