ngio 0.2.0a2__tar.gz → 0.2.0b1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (200) hide show
  1. {ngio-0.2.0a2 → ngio-0.2.0b1}/.gitignore +3 -0
  2. {ngio-0.2.0a2 → ngio-0.2.0b1}/PKG-INFO +4 -1
  3. ngio-0.2.0b1/docs/api/core.md +3 -0
  4. {ngio-0.2.0a2 → ngio-0.2.0b1}/docs/notebooks/basic_usage.ipynb +45 -16
  5. {ngio-0.2.0a2 → ngio-0.2.0b1}/docs/notebooks/image.ipynb +2 -9
  6. {ngio-0.2.0a2 → ngio-0.2.0b1}/pyproject.toml +10 -23
  7. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/__init__.py +4 -4
  8. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/__init__.py +12 -2
  9. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_array_pipe.py +106 -0
  10. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_axes_transforms.py +3 -2
  11. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_dimensions.py +7 -0
  12. ngio-0.2.0b1/src/ngio/common/_masking_roi.py +158 -0
  13. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_pyramid.py +16 -11
  14. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_roi.py +74 -0
  15. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_slicer.py +1 -2
  16. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_zoom.py +5 -3
  17. ngio-0.2.0b1/src/ngio/hcs/__init__.py +5 -0
  18. ngio-0.2.0b1/src/ngio/hcs/plate.py +399 -0
  19. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/images/abstract_image.py +97 -28
  20. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/images/create.py +48 -29
  21. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/images/image.py +121 -57
  22. ngio-0.2.0b1/src/ngio/images/label.py +281 -0
  23. ngio-0.2.0b1/src/ngio/images/masked_image.py +259 -0
  24. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/images/omezarr_container.py +250 -77
  25. ngio-0.2.0b1/src/ngio/ome_zarr_meta/__init__.py +47 -0
  26. ngio-0.2.0b1/src/ngio/ome_zarr_meta/_meta_handlers.py +791 -0
  27. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/__init__.py +8 -0
  28. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/_channels.py +11 -0
  29. ngio-0.2.0b1/src/ngio/ome_zarr_meta/ngio_specs/_ngio_hcs.py +377 -0
  30. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/_ngio_image.py +174 -113
  31. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/_pixel_size.py +35 -3
  32. ngio-0.2.0b1/src/ngio/ome_zarr_meta/v04/__init__.py +23 -0
  33. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/v04/_v04_spec_utils.py +85 -12
  34. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/__init__.py +2 -0
  35. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/_validators.py +2 -4
  36. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/_anndata_utils.py +2 -1
  37. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/_anndata_v1.py +2 -1
  38. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/_json_v1.py +1 -1
  39. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/tables_container.py +12 -2
  40. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/v1/__init__.py +1 -2
  41. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/v1/_feature_table.py +7 -5
  42. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/v1/_generic_table.py +65 -11
  43. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/v1/_roi_table.py +145 -27
  44. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/utils/__init__.py +3 -0
  45. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/utils/_datasets.py +4 -2
  46. ngio-0.2.0b1/src/ngio/utils/_fractal_fsspec_store.py +13 -0
  47. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/utils/_logger.py +3 -1
  48. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/utils/_zarr_utils.py +25 -2
  49. ngio-0.2.0b1/tests/conftest.py +40 -0
  50. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/.zattrs +86 -0
  51. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/.zgroup +3 -0
  52. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/0/.zarray +27 -0
  53. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/1/.zarray +27 -0
  54. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/.zattrs +5 -0
  55. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/.zgroup +3 -0
  56. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/label/.zattrs +59 -0
  57. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/label/.zgroup +3 -0
  58. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/label/0/.zarray +25 -0
  59. ngio-0.2.0b1/tests/data/v04/images/test_image_c1yx.zarr/labels/label/1/.zarray +25 -0
  60. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/.zattrs +79 -0
  61. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/.zgroup +3 -0
  62. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/0/.zarray +25 -0
  63. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/1/.zarray +25 -0
  64. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/.zattrs +5 -0
  65. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/.zgroup +3 -0
  66. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/label/.zattrs +52 -0
  67. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/label/.zgroup +3 -0
  68. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/label/0/.zarray +23 -0
  69. ngio-0.2.0b1/tests/data/v04/images/test_image_cyx.zarr/labels/label/1/.zarray +23 -0
  70. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/.zattrs +86 -0
  71. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/.zgroup +3 -0
  72. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/0/.zarray +27 -0
  73. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/1/.zarray +27 -0
  74. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/.zattrs +5 -0
  75. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/.zgroup +3 -0
  76. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/label/.zattrs +59 -0
  77. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/label/.zgroup +3 -0
  78. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/label/0/.zarray +25 -0
  79. ngio-0.2.0b1/tests/data/v04/images/test_image_czyx.zarr/labels/label/1/.zarray +25 -0
  80. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/.zattrs +86 -0
  81. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/.zgroup +3 -0
  82. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/0/.zarray +27 -0
  83. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/1/.zarray +27 -0
  84. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/.zattrs +5 -0
  85. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/.zgroup +3 -0
  86. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/label/.zattrs +59 -0
  87. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/label/.zgroup +3 -0
  88. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/label/0/.zarray +25 -0
  89. ngio-0.2.0b1/tests/data/v04/images/test_image_tcyx.zarr/labels/label/1/.zarray +25 -0
  90. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/.zattrs +93 -0
  91. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/.zgroup +3 -0
  92. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/0/.zarray +29 -0
  93. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/1/.zarray +29 -0
  94. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/.zattrs +5 -0
  95. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/.zgroup +3 -0
  96. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/label/.zattrs +66 -0
  97. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/label/.zgroup +3 -0
  98. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/label/0/.zarray +27 -0
  99. ngio-0.2.0b1/tests/data/v04/images/test_image_tczyx.zarr/labels/label/1/.zarray +27 -0
  100. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/.zattrs +68 -0
  101. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/.zgroup +3 -0
  102. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/0/.zarray +25 -0
  103. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/1/.zarray +25 -0
  104. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/.zattrs +5 -0
  105. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/.zgroup +3 -0
  106. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/label/.zattrs +59 -0
  107. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/label/.zgroup +3 -0
  108. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/label/0/.zarray +25 -0
  109. ngio-0.2.0b1/tests/data/v04/images/test_image_tyx.zarr/labels/label/1/.zarray +25 -0
  110. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/.zattrs +75 -0
  111. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/.zgroup +3 -0
  112. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/0/.zarray +27 -0
  113. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/1/.zarray +27 -0
  114. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/.zattrs +5 -0
  115. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/.zgroup +3 -0
  116. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/label/.zattrs +66 -0
  117. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/label/.zgroup +3 -0
  118. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/label/0/.zarray +27 -0
  119. ngio-0.2.0b1/tests/data/v04/images/test_image_tzyx.zarr/labels/label/1/.zarray +27 -0
  120. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/.zattrs +61 -0
  121. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/.zgroup +3 -0
  122. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/0/.zarray +23 -0
  123. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/1/.zarray +23 -0
  124. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/.zattrs +5 -0
  125. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/.zgroup +3 -0
  126. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/label/.zattrs +52 -0
  127. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/label/.zgroup +3 -0
  128. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/label/0/.zarray +23 -0
  129. ngio-0.2.0b1/tests/data/v04/images/test_image_yx.zarr/labels/label/1/.zarray +23 -0
  130. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/.zattrs +68 -0
  131. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/.zgroup +3 -0
  132. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/0/.zarray +25 -0
  133. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/1/.zarray +25 -0
  134. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/.zattrs +5 -0
  135. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/.zgroup +3 -0
  136. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/label/.zattrs +59 -0
  137. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/label/.zgroup +3 -0
  138. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/label/0/.zarray +25 -0
  139. ngio-0.2.0b1/tests/data/v04/images/test_image_zyx.zarr/labels/label/1/.zarray +25 -0
  140. ngio-0.2.0b1/tests/unit/hcs/test_plate.py +57 -0
  141. ngio-0.2.0b1/tests/unit/images/test_create.py +128 -0
  142. ngio-0.2.0b1/tests/unit/images/test_images.py +25 -0
  143. ngio-0.2.0b1/tests/unit/images/test_masked_images.py +73 -0
  144. ngio-0.2.0b1/tests/unit/images/test_omezarr_container.py +155 -0
  145. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/tables/test_backends.py +7 -5
  146. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/tables/test_feature_table.py +1 -1
  147. ngio-0.2.0b1/tests/unit/tables/test_generic_table.py +56 -0
  148. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/tables/test_masking_roi_table_v1.py +1 -1
  149. ngio-0.2.0b1/tests/unit/tables/test_table_group.py +34 -0
  150. ngio-0.2.0b1/tests/unit/test_ome_zarr_meta/test_image_handler.py +15 -0
  151. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/test_ome_zarr_meta/test_unit_ngio_specs.py +14 -6
  152. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/test_ome_zarr_meta/test_unit_v04_utils.py +2 -2
  153. ngio-0.2.0a2/docs/api/core.md +0 -8
  154. ngio-0.2.0a2/src/ngio/hcs/__init__.py +0 -60
  155. ngio-0.2.0a2/src/ngio/images/label.py +0 -236
  156. ngio-0.2.0a2/src/ngio/ome_zarr_meta/__init__.py +0 -35
  157. ngio-0.2.0a2/src/ngio/ome_zarr_meta/_generic_handlers.py +0 -320
  158. ngio-0.2.0a2/src/ngio/ome_zarr_meta/_meta_handlers.py +0 -142
  159. ngio-0.2.0a2/src/ngio/ome_zarr_meta/ngio_specs/_ngio_hcs.py +0 -5
  160. ngio-0.2.0a2/src/ngio/ome_zarr_meta/v04/__init__.py +0 -11
  161. ngio-0.2.0a2/src/ngio/ome_zarr_meta/v04/_meta_handlers.py +0 -54
  162. ngio-0.2.0a2/src/ngio/tables/v1/_masking_roi_table.py +0 -175
  163. ngio-0.2.0a2/tests/conftest.py +0 -11
  164. ngio-0.2.0a2/tests/unit/images/test_omezarr_container.py +0 -95
  165. ngio-0.2.0a2/tests/unit/tables/test_generic_table.py +0 -24
  166. ngio-0.2.0a2/tests/unit/tables/test_table_group.py +0 -9
  167. ngio-0.2.0a2/tests/unit/test_ome_zarr_meta/test_image_handler.py +0 -13
  168. {ngio-0.2.0a2 → ngio-0.2.0b1}/.copier-answers.yml +0 -0
  169. {ngio-0.2.0a2 → ngio-0.2.0b1}/.gitattributes +0 -0
  170. {ngio-0.2.0a2 → ngio-0.2.0b1}/.github/ISSUE_TEMPLATE.md +0 -0
  171. {ngio-0.2.0a2 → ngio-0.2.0b1}/.github/TEST_FAIL_TEMPLATE.md +0 -0
  172. {ngio-0.2.0a2 → ngio-0.2.0b1}/.github/dependabot.yml +0 -0
  173. {ngio-0.2.0a2 → ngio-0.2.0b1}/.github/workflows/build_docs.yml +0 -0
  174. {ngio-0.2.0a2 → ngio-0.2.0b1}/.github/workflows/ci.yml +0 -0
  175. {ngio-0.2.0a2 → ngio-0.2.0b1}/.pre-commit-config.yaml +0 -0
  176. {ngio-0.2.0a2 → ngio-0.2.0b1}/LICENSE +0 -0
  177. {ngio-0.2.0a2 → ngio-0.2.0b1}/README.md +0 -0
  178. {ngio-0.2.0a2 → ngio-0.2.0b1}/_typos.toml +0 -0
  179. {ngio-0.2.0a2 → ngio-0.2.0b1}/docs/getting-started.md +0 -0
  180. {ngio-0.2.0a2 → ngio-0.2.0b1}/docs/index.md +0 -0
  181. {ngio-0.2.0a2 → ngio-0.2.0b1}/docs/notebooks/processing.ipynb +0 -0
  182. {ngio-0.2.0a2 → ngio-0.2.0b1}/mkdocs.yml +0 -0
  183. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/common/_common_types.py +0 -0
  184. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/images/__init__.py +0 -0
  185. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/_axes.py +0 -0
  186. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/ome_zarr_meta/ngio_specs/_dataset.py +0 -0
  187. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/__init__.py +0 -0
  188. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/_abstract_backend.py +0 -0
  189. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/tables/backends/_table_backends.py +0 -0
  190. {ngio-0.2.0a2 → ngio-0.2.0b1}/src/ngio/utils/_errors.py +0 -0
  191. {ngio-0.2.0a2/tests/data/meta_v04 → ngio-0.2.0b1/tests/data/v04/meta}/base_ome_zarr_image_meta.json +0 -0
  192. {ngio-0.2.0a2/tests/data/meta_v04 → ngio-0.2.0b1/tests/data/v04/meta}/base_ome_zarr_image_meta_wrong_axis_order.json +0 -0
  193. {ngio-0.2.0a2/tests/data/meta_v04 → ngio-0.2.0b1/tests/data/v04/meta}/base_ome_zarr_label_meta.json +0 -0
  194. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/common/test_dimensions.py +0 -0
  195. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/common/test_pyramid.py +0 -0
  196. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/common/test_roi.py +0 -0
  197. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/tables/test_roi_table_v1.py +0 -0
  198. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/tables/test_validators.py +0 -0
  199. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/utils/test_download_datasets.py +0 -0
  200. {ngio-0.2.0a2 → ngio-0.2.0b1}/tests/unit/utils/test_zarr_utils.py +0 -0
@@ -116,7 +116,10 @@ ENV/
116
116
  pixi.lock
117
117
  *.egg-info
118
118
 
119
+ # Ignore all .zarr directories
119
120
  *.zarr
121
+ # but allow .zarr in tests/data
122
+ !tests/data/**/**/test_*.zarr
120
123
 
121
124
  # ignore data directory
122
125
  ./data/
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ngio
3
- Version: 0.2.0a2
3
+ Version: 0.2.0b1
4
4
  Summary: Next Generation file format IO
5
5
  Project-URL: homepage, https://github.com/lorenzocerrone/ngio
6
6
  Project-URL: repository, https://github.com/lorenzocerrone/ngio
@@ -29,6 +29,7 @@ Requires-Dist: requests
29
29
  Requires-Dist: xarray
30
30
  Requires-Dist: zarr<3
31
31
  Provides-Extra: dev
32
+ Requires-Dist: devtools; extra == 'dev'
32
33
  Requires-Dist: matplotlib; extra == 'dev'
33
34
  Requires-Dist: mypy; extra == 'dev'
34
35
  Requires-Dist: napari; extra == 'dev'
@@ -38,6 +39,7 @@ Requires-Dist: pre-commit; extra == 'dev'
38
39
  Requires-Dist: pyqt5; extra == 'dev'
39
40
  Requires-Dist: rich; extra == 'dev'
40
41
  Requires-Dist: ruff; extra == 'dev'
42
+ Requires-Dist: scikit-image; extra == 'dev'
41
43
  Provides-Extra: docs
42
44
  Requires-Dist: mkdocs; extra == 'docs'
43
45
  Requires-Dist: mkdocs-autorefs; extra == 'docs'
@@ -50,6 +52,7 @@ Requires-Dist: scikit-image; extra == 'docs'
50
52
  Provides-Extra: test
51
53
  Requires-Dist: pytest; extra == 'test'
52
54
  Requires-Dist: pytest-cov; extra == 'test'
55
+ Requires-Dist: scikit-image; extra == 'test'
53
56
  Description-Content-Type: text/markdown
54
57
 
55
58
  # NGIO - Next Generation file format IO
@@ -0,0 +1,3 @@
1
+ # ngio
2
+
3
+ Work in progress! Sorry!
@@ -10,15 +10,6 @@
10
10
  "\n",
11
11
  "For this example we will use a small example image that can be downloaded from the following link: [example ome-zarr](https://zenodo.org/records/13305156)\n",
12
12
  "\n",
13
- "## Setup\n",
14
- "\n",
15
- "You can download the example image (on Linux and Mac os) by running the following command:\n",
16
- "\n",
17
- "```bash\n",
18
- "bash setup_data.sh\n",
19
- "```\n",
20
- "from the root of the repository.\n",
21
- "\n",
22
13
  "## OmeZarr Container\n",
23
14
  "\n",
24
15
  "The `OmeZarr Container` provides a high-level interface to read, write and manipulate NGFF images.\n",
@@ -95,8 +86,10 @@
95
86
  "print(image)\n",
96
87
  "\n",
97
88
  "# 3. Get image from a specific pixel size using the pixel_size keyword\n",
98
- "image = omezarr_container.get_image(pixel_size=PixelSize(x=0.65, y=0.65, z=1))\n",
99
- "print(image)"
89
+ "# image = omezarr_container.get_image(\n",
90
+ "# pixel_size=PixelSize(x=0.65, y=0.65, z=1), strict=True\n",
91
+ "# )\n",
92
+ "print(image.pixel_size == PixelSize(x=0.325, y=0.325, z=1))"
100
93
  ]
101
94
  },
102
95
  {
@@ -253,6 +246,32 @@
253
246
  "print(new_omezarr_image)"
254
247
  ]
255
248
  },
249
+ {
250
+ "cell_type": "markdown",
251
+ "metadata": {},
252
+ "source": [
253
+ "# Create an OmeZarr From a Numpy Array\n"
254
+ ]
255
+ },
256
+ {
257
+ "cell_type": "code",
258
+ "execution_count": null,
259
+ "metadata": {},
260
+ "outputs": [],
261
+ "source": [
262
+ "import numpy as np\n",
263
+ "\n",
264
+ "from ngio import create_omezarr_from_array\n",
265
+ "\n",
266
+ "x = np.random.randint(0, 255, (16, 128, 128), dtype=np.uint8)\n",
267
+ "\n",
268
+ "new_omezarr_image = create_omezarr_from_array(\n",
269
+ " store=\"random_ome.zarr\", array=x, xy_pixelsize=0.65, z_spacing=1.0\n",
270
+ ")\n",
271
+ "print(new_omezarr_image)\n",
272
+ "print(new_omezarr_image.get_image())"
273
+ ]
274
+ },
256
275
  {
257
276
  "cell_type": "markdown",
258
277
  "metadata": {},
@@ -268,6 +287,7 @@
268
287
  "metadata": {},
269
288
  "outputs": [],
270
289
  "source": [
290
+ "import fsspec\n",
271
291
  "import fsspec.implementations.http\n",
272
292
  "\n",
273
293
  "url = (\n",
@@ -279,17 +299,26 @@
279
299
  "\n",
280
300
  "fs = fsspec.implementations.http.HTTPFileSystem(client_kwargs={})\n",
281
301
  "store = fs.get_mapper(url)\n",
282
- "\n",
283
302
  "omezarr = open_omezarr_container(store)\n",
284
303
  "omezarr"
285
304
  ]
286
305
  },
287
306
  {
288
- "cell_type": "code",
289
- "execution_count": null,
307
+ "cell_type": "markdown",
290
308
  "metadata": {},
291
- "outputs": [],
292
- "source": []
309
+ "source": [
310
+ "# Streaming an OmeZarr from a Fractal Server\n",
311
+ "\n",
312
+ "Example:\n",
313
+ "\n",
314
+ "```python\n",
315
+ "from ngio.utils import fractal_fsspec_store\n",
316
+ "\n",
317
+ "store = fractal_fsspec_store(url=\"https://fracral_url...\", fractal_token=\"**your_secret_token**\")\n",
318
+ "omezarr = open_omezarr_container(store)\n",
319
+ "omezarr\n",
320
+ "```"
321
+ ]
293
322
  }
294
323
  ],
295
324
  "metadata": {
@@ -216,7 +216,7 @@
216
216
  "outputs": [],
217
217
  "source": [
218
218
  "# Create a a new label object and set it to a simple segmentation\n",
219
- "new_label = omezarr.derive_label(\"new_label_2\", overwrite=True)\n",
219
+ "new_label = omezarr.derive_label(\"new_label\", overwrite=True)\n",
220
220
  "\n",
221
221
  "simple_segmentation = image.get_array(c=0) > 100\n",
222
222
  "simple_segmentation = simple_segmentation[0]\n",
@@ -225,7 +225,7 @@
225
225
  "# make a subplot with two image show side by side\n",
226
226
  "fig, axs = plt.subplots(1, 2, figsize=(10, 5))\n",
227
227
  "axs[0].imshow(image.get_array()[0, 0], cmap=\"gray\")\n",
228
- "axs[1].imshow(new_label.get_array()[0], cmap=\"gray\")\n",
228
+ "axs[1].imshow(new_label.get_array()[0])\n",
229
229
  "for ax in axs:\n",
230
230
  " ax.axis(\"off\")\n",
231
231
  "plt.tight_layout()\n",
@@ -327,13 +327,6 @@
327
327
  "feat_table = omezarr.get_table(\"new_feature_table\")\n",
328
328
  "feat_table.dataframe"
329
329
  ]
330
- },
331
- {
332
- "cell_type": "code",
333
- "execution_count": null,
334
- "metadata": {},
335
- "outputs": [],
336
- "source": []
337
330
  }
338
331
  ],
339
332
  "metadata": {
@@ -51,18 +51,20 @@ dependencies = [
51
51
  # https://peps.python.org/pep-0621/#dependencies-optional-dependencies
52
52
  # "extras" (e.g. for `pip install .[test]`)
53
53
  [project.optional-dependencies]
54
- test = ["pytest", "pytest-cov"]
54
+ test = ["pytest", "pytest-cov", "scikit-image"]
55
55
 
56
56
  dev = [
57
57
  "napari",
58
58
  "pyqt5",
59
59
  "matplotlib",
60
+ "devtools",
60
61
  "notebook",
61
62
  "mypy",
62
- "pdbpp", # https://github.com/pdbpp/pdbpp
63
+ "pdbpp", # https://github.com/pdbpp/pdbpp
63
64
  "pre-commit",
64
- "rich", # https://github.com/Textualize/rich
65
+ "rich", # https://github.com/Textualize/rich
65
66
  "ruff",
67
+ "scikit-image",
66
68
  ] # add anything else you like to have in your dev environment here
67
69
 
68
70
  docs = [
@@ -212,18 +214,12 @@ test13 = { features = ["py13", "test"], solve-group = "py13" }
212
214
  # dev env
213
215
  dev = { features = ["dev", "test"], solve-group = "py11" }
214
216
 
215
-
216
- [tool.pixi.feature.py11.tasks]
217
- pytest_test11 = "pytest"
217
+ [tool.pixi.tasks]
218
+ serve_docs = "mkdocs serve"
219
+ run_tests = "pytest"
220
+ clean_nb_data = "rm -rf ./docs/notebooks/**/*.zarr"
218
221
  test_nb = { cmd = "jupyter-execute ./docs/notebooks/*.ipynb" }
219
-
220
- [tool.pixi.feature.py12.tasks]
221
- pytest_test12 = "pytest"
222
-
223
- [tool.pixi.feature.py13.tasks]
224
- pytest_test13 = "pytest"
225
-
226
- [tool.pixi.feature.task-feat.tasks]
222
+ test = { depends-on = ["run_tests", "clean_nb_data", "test_nb"] }
227
223
  pre_commit_install = "pre-commit install"
228
224
 
229
225
  ruff-fix-imports = "ruff check --select I --fix"
@@ -233,12 +229,3 @@ pre-commit = { cmd = "pre-commit run --all-files", depends-on = [
233
229
  "pre_commit_install",
234
230
  "ruff-format",
235
231
  ] }
236
-
237
- [tool.pixi.tasks]
238
- serve_docs = "mkdocs serve"
239
- test = { depends-on = [
240
- "pytest_test11",
241
- "pytest_test12",
242
- "pytest_test13",
243
- "test_nb",
244
- ] }
@@ -10,7 +10,7 @@ __author__ = "Lorenzo Cerrone"
10
10
  __email__ = "lorenzo.cerrone@uzh.ch"
11
11
 
12
12
  from ngio.common import ArrayLike, Dimensions
13
- from ngio.hcs import OmeZarrPlate, OmeZarrWell, open_omezarr_plate, open_omezarr_well
13
+ from ngio.hcs import OmeZarrPlate, create_empty_plate, open_omezarr_plate
14
14
  from ngio.images import (
15
15
  Image,
16
16
  Label,
@@ -20,22 +20,22 @@ from ngio.images import (
20
20
  open_image,
21
21
  open_omezarr_container,
22
22
  )
23
- from ngio.ome_zarr_meta.ngio_specs import AxesSetup, PixelSize
23
+ from ngio.ome_zarr_meta.ngio_specs import AxesSetup, ImageInWellPath, PixelSize
24
24
 
25
25
  __all__ = [
26
26
  "ArrayLike",
27
27
  "AxesSetup",
28
28
  "Dimensions",
29
29
  "Image",
30
+ "ImageInWellPath",
30
31
  "Label",
31
32
  "OmeZarrContainer",
32
33
  "OmeZarrPlate",
33
- "OmeZarrWell",
34
34
  "PixelSize",
35
35
  "create_empty_omezarr",
36
+ "create_empty_plate",
36
37
  "create_omezarr_from_array",
37
38
  "open_image",
38
39
  "open_omezarr_container",
39
40
  "open_omezarr_plate",
40
- "open_omezarr_well",
41
41
  ]
@@ -1,6 +1,11 @@
1
1
  """Common classes and functions that are used across the package."""
2
2
 
3
- from ngio.common._array_pipe import get_pipe, set_pipe
3
+ from ngio.common._array_pipe import (
4
+ get_masked_pipe,
5
+ get_pipe,
6
+ set_masked_pipe,
7
+ set_pipe,
8
+ )
4
9
  from ngio.common._axes_transforms import (
5
10
  transform_dask_array,
6
11
  transform_list,
@@ -8,8 +13,9 @@ from ngio.common._axes_transforms import (
8
13
  )
9
14
  from ngio.common._common_types import ArrayLike
10
15
  from ngio.common._dimensions import Dimensions
16
+ from ngio.common._masking_roi import compute_masking_roi
11
17
  from ngio.common._pyramid import consolidate_pyramid, init_empty_pyramid, on_disk_zoom
12
- from ngio.common._roi import RasterCooROI, WorldCooROI
18
+ from ngio.common._roi import RasterCooROI, WorldCooROI, roi_to_slice_kwargs
13
19
  from ngio.common._slicer import (
14
20
  SliceTransform,
15
21
  compute_and_slices,
@@ -27,16 +33,20 @@ __all__ = [
27
33
  "SliceTransform",
28
34
  "WorldCooROI",
29
35
  "compute_and_slices",
36
+ "compute_masking_roi",
30
37
  "consolidate_pyramid",
31
38
  "dask_get_slice",
32
39
  "dask_set_slice",
33
40
  "dask_zoom",
41
+ "get_masked_pipe",
34
42
  "get_pipe",
35
43
  "init_empty_pyramid",
36
44
  "numpy_get_slice",
37
45
  "numpy_set_slice",
38
46
  "numpy_zoom",
39
47
  "on_disk_zoom",
48
+ "roi_to_slice_kwargs",
49
+ "set_masked_pipe",
40
50
  "set_pipe",
41
51
  "transform_dask_array",
42
52
  "transform_list",
@@ -158,3 +158,109 @@ def set_pipe(
158
158
  )
159
159
  else:
160
160
  raise NgioValueError("Unknown patch type, expected numpy, dask or delayed.")
161
+
162
+
163
+ def _mask_pipe_common(
164
+ array: zarr.Array,
165
+ label_array: zarr.Array,
166
+ label: int,
167
+ *,
168
+ dimensions_array: Dimensions,
169
+ dimensions_label: Dimensions,
170
+ axes_order: Collection[str] | None = None,
171
+ mode: Literal["numpy", "dask", "delayed"] = "numpy",
172
+ **slice_kwargs: slice | int | Iterable[int],
173
+ ):
174
+ array_patch = get_pipe(
175
+ array,
176
+ dimensions=dimensions_array,
177
+ axes_order=axes_order,
178
+ mode=mode,
179
+ **slice_kwargs,
180
+ )
181
+
182
+ if "c" in slice_kwargs.keys():
183
+ # This makes the strong assumption that the
184
+ # user is passing the channel axis as "c"
185
+ # This will fail if the channel axis is queried
186
+ # with a different on-disk name
187
+ slice_kwargs.pop("c")
188
+
189
+ label_patch = get_pipe(
190
+ label_array,
191
+ dimensions=dimensions_label,
192
+ axes_order=axes_order,
193
+ mode=mode,
194
+ **slice_kwargs,
195
+ )
196
+
197
+ if isinstance(array_patch, np.ndarray):
198
+ label_patch = np.broadcast_to(label_patch, array_patch.shape)
199
+ elif isinstance(array_patch, dask.array.Array):
200
+ label_patch = dask.array.broadcast_to(label_patch, array_patch.shape)
201
+ else:
202
+ raise NgioValueError(f"Mode {mode} not yet supported for masked array.")
203
+
204
+ mask = label_patch == label
205
+ return array_patch, mask
206
+
207
+
208
+ def get_masked_pipe(
209
+ array: zarr.Array,
210
+ label_array: zarr.Array,
211
+ label: int,
212
+ *,
213
+ dimensions_array: Dimensions,
214
+ dimensions_label: Dimensions,
215
+ axes_order: Collection[str] | None = None,
216
+ mode: Literal["numpy", "dask", "delayed"] = "numpy",
217
+ **slice_kwargs: slice | int | Iterable[int],
218
+ ):
219
+ array_patch, mask = _mask_pipe_common(
220
+ array=array,
221
+ label_array=label_array,
222
+ label=label,
223
+ dimensions_array=dimensions_array,
224
+ dimensions_label=dimensions_label,
225
+ axes_order=axes_order,
226
+ mode=mode,
227
+ **slice_kwargs,
228
+ )
229
+ array_patch[~mask] = 0
230
+ return array_patch
231
+
232
+
233
+ def set_masked_pipe(
234
+ array: zarr.Array,
235
+ label_array: zarr.Array,
236
+ label: int,
237
+ patch: ArrayLike,
238
+ *,
239
+ dimensions_array: Dimensions,
240
+ dimensions_label: Dimensions,
241
+ axes_order: Collection[str] | None = None,
242
+ **slice_kwargs: slice | int | Iterable[int],
243
+ ):
244
+ if isinstance(patch, dask.array.Array):
245
+ mode = "dask"
246
+ elif isinstance(patch, np.ndarray):
247
+ mode = "numpy"
248
+ else:
249
+ raise NgioValueError(
250
+ "Mode not yet supported for masked array. Expected a numpy or dask array."
251
+ )
252
+
253
+ array_patch, mask = _mask_pipe_common(
254
+ array=array,
255
+ label_array=label_array,
256
+ label=label,
257
+ dimensions_array=dimensions_array,
258
+ dimensions_label=dimensions_label,
259
+ axes_order=axes_order,
260
+ mode=mode,
261
+ **slice_kwargs,
262
+ )
263
+ patch = np.where(mask, patch, array_patch)
264
+ set_pipe(
265
+ array, patch, dimensions=dimensions_array, axes_order=axes_order, **slice_kwargs
266
+ )
@@ -9,6 +9,7 @@ from ngio.ome_zarr_meta.ngio_specs._axes import (
9
9
  AxesTransformation,
10
10
  AxesTranspose,
11
11
  )
12
+ from ngio.utils import NgioValueError
12
13
 
13
14
  T = TypeVar("T")
14
15
 
@@ -44,7 +45,7 @@ def transform_numpy_array(
44
45
  elif isinstance(operation, AxesSqueeze):
45
46
  array = np.squeeze(array, axis=operation.axes)
46
47
  else:
47
- raise ValueError(f"Unknown operation {operation}")
48
+ raise NgioValueError(f"Unknown operation {operation}")
48
49
  return array
49
50
 
50
51
 
@@ -59,5 +60,5 @@ def transform_dask_array(
59
60
  elif isinstance(operation, AxesSqueeze):
60
61
  array = da.squeeze(array, axis=operation.axes)
61
62
  else:
62
- raise ValueError(f"Unknown operation {operation}")
63
+ raise NgioValueError(f"Unknown operation {operation}")
63
64
  return array
@@ -57,6 +57,13 @@ class Dimensions:
57
57
  return 1
58
58
  return self._shape[index]
59
59
 
60
+ def has_axis(self, axis_name: str) -> bool:
61
+ """Return whether the axis exists."""
62
+ index = self._axes_mapper.get_axis(axis_name)
63
+ if index is None:
64
+ return False
65
+ return True
66
+
60
67
  def get_shape(self, axes_order: Collection[str]) -> tuple[int, ...]:
61
68
  """Return the shape in the given axes order."""
62
69
  transforms = self._axes_mapper.to_order(axes_order)
@@ -0,0 +1,158 @@
1
+ """Utilities to build masking regions of interest (ROIs)."""
2
+
3
+ import itertools
4
+
5
+ import dask
6
+ import dask.array as da
7
+ import dask.delayed
8
+ import numpy as np
9
+ import scipy.ndimage as ndi
10
+
11
+ from ngio.common._roi import RasterCooROI, WorldCooROI
12
+ from ngio.ome_zarr_meta import PixelSize
13
+ from ngio.utils import NgioValueError
14
+
15
+
16
+ def _compute_offsets(chunks):
17
+ """Given a chunks tuple, compute cumulative offsets for each axis.
18
+
19
+ Returns a list where each element is a list of offsets for that dimension.
20
+ """
21
+ offsets = []
22
+ for dim_chunks in chunks:
23
+ dim_offsets = [0]
24
+ for size in dim_chunks:
25
+ dim_offsets.append(dim_offsets[-1] + size)
26
+ offsets.append(dim_offsets)
27
+ return offsets
28
+
29
+
30
+ def _adjust_slices(slices, offset):
31
+ """Adjust slices to global coordinates using the provided offset."""
32
+ adjusted_slices = {}
33
+ for label, s in slices.items():
34
+ adjusted = tuple(
35
+ slice(s_dim.start + off, s_dim.stop + off)
36
+ for s_dim, off in zip(s, offset, strict=True)
37
+ )
38
+ adjusted_slices[label] = adjusted
39
+ return adjusted_slices
40
+
41
+
42
+ @dask.delayed
43
+ def _process_chunk(chunk, offset):
44
+ """Process a single chunk.
45
+
46
+ run ndi.find_objects and adjust the slices
47
+ to global coordinates using the provided offset.
48
+ """
49
+ local_slices = compute_slices(chunk)
50
+ local_slices = _adjust_slices(local_slices, offset)
51
+ return local_slices
52
+
53
+
54
+ def _merge_slices(
55
+ slice1: tuple[slice, ...], slice2: tuple[slice, ...]
56
+ ) -> tuple[slice, ...]:
57
+ """Merge two slices."""
58
+ merged = []
59
+ for s1, s2 in zip(slice1, slice2, strict=True):
60
+ start = min(s1.start, s2.start)
61
+ stop = max(s1.stop, s2.stop)
62
+ merged.append(slice(start, stop))
63
+ return tuple(merged)
64
+
65
+
66
+ @dask.delayed
67
+ def _collect_slices(
68
+ local_slices: list[dict[int, tuple[slice, ...]]],
69
+ ) -> dict[int, tuple[slice]]:
70
+ """Collect the slices from the delayed results."""
71
+ global_slices = {}
72
+ for result in local_slices:
73
+ for label, s in result.items():
74
+ if label in global_slices:
75
+ global_slices[label] = _merge_slices(global_slices[label], s)
76
+ else:
77
+ global_slices[label] = s
78
+ return global_slices
79
+
80
+
81
+ def compute_slices(segmentation: np.ndarray) -> dict[int, tuple[slice, ...]]:
82
+ """Compute slices for each label in a segmentation.
83
+
84
+ Args:
85
+ segmentation (ndarray): The segmentation array.
86
+
87
+ Returns:
88
+ dict[int, tuple[slice]]: A dictionary with the label as key
89
+ and the slice as value.
90
+ """
91
+ slices = ndi.find_objects(segmentation)
92
+ slices_dict = {}
93
+ for label, s in enumerate(slices, start=1):
94
+ if s is None:
95
+ continue
96
+ else:
97
+ slices_dict[label] = s
98
+ return slices_dict
99
+
100
+
101
+ def lazy_compute_slices(segmentation: da.Array) -> dict[int, tuple[slice, ...]]:
102
+ """Compute slices for each label in a segmentation."""
103
+ global_offsets = _compute_offsets(segmentation.chunks)
104
+ delayed_chunks = segmentation.to_delayed()
105
+
106
+ grid_shape = tuple(len(c) for c in segmentation.chunks)
107
+
108
+ grid_indices = list(itertools.product(*[range(n) for n in grid_shape]))
109
+ delayed_results = []
110
+ for idx, chunk in zip(grid_indices, np.ravel(delayed_chunks), strict=True):
111
+ offset = tuple(global_offsets[dim][idx[dim]] for dim in range(len(idx)))
112
+ delayed_result = _process_chunk(chunk, offset)
113
+ delayed_results.append(delayed_result)
114
+
115
+ return _collect_slices(delayed_results).compute()
116
+
117
+
118
+ def compute_masking_roi(
119
+ segmentation: np.ndarray | da.Array, pixel_size: PixelSize
120
+ ) -> list[WorldCooROI]:
121
+ """Compute a ROIs for each label in a segmentation.
122
+
123
+ This function expects a 2D or 3D segmentation array.
124
+ And this function expects the axes order to be 'zyx' or 'yx'.
125
+ Other axes orders are not supported.
126
+
127
+ """
128
+ if segmentation.ndim not in [2, 3]:
129
+ raise NgioValueError("Only 2D and 3D segmentations are supported.")
130
+
131
+ if isinstance(segmentation, da.Array):
132
+ slices = lazy_compute_slices(segmentation)
133
+ else:
134
+ slices = compute_slices(segmentation)
135
+
136
+ rois = []
137
+ for label, slice_ in slices.items():
138
+ if len(slice_) == 2:
139
+ min_z, min_y, min_x = 0, slice_[0].start, slice_[1].start
140
+ max_z, max_y, max_x = 1, slice_[0].stop, slice_[1].stop
141
+ elif len(slice_) == 3:
142
+ min_z, min_y, min_x = slice_[0].start, slice_[1].start, slice_[2].start
143
+ max_z, max_y, max_x = slice_[0].stop, slice_[1].stop, slice_[2].stop
144
+ else:
145
+ raise ValueError("Invalid slice length.")
146
+ roi = RasterCooROI(
147
+ name=str(label),
148
+ x_length=max_x - min_x,
149
+ y_length=max_y - min_y,
150
+ z_length=max_z - min_z,
151
+ x=min_x,
152
+ y=min_y,
153
+ z=min_z,
154
+ )
155
+
156
+ roi = roi.to_world_coo_roi(pixel_size)
157
+ rois.append(roi)
158
+ return rois