Skip to content

Commit

Permalink
Enable cropping during write; does not modify internal data
Browse files Browse the repository at this point in the history
  • Loading branch information
annehaley committed Feb 1, 2024
1 parent f8fb42e commit d697920
Showing 1 changed file with 58 additions and 7 deletions.
65 changes: 58 additions & 7 deletions sources/zarr/large_image_source_zarr/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -594,6 +594,31 @@ def addTile(self, tile, x=0, y=0, mask=None, axes=None, **kwargs):
'omero': {'version': '0.5-dev'},
})

@property
def crop(self):
"""
Crop only applies to the output file, not the internal data access.
It consists of x, y, w, h in pixels.
"""
return getattr(self, '_crop', None)

@crop.setter
def crop(self, value):
self._checkEditable()

Check warning on line 608 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L608

Added line #L608 was not covered by tests
if value is None:
self._crop = None
return
x, y, w, h = value
x = int(x)
y = int(y)
w = int(w)
h = int(h)

Check warning on line 616 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L610-L616

Added lines #L610 - L616 were not covered by tests
if x < 0 or y < 0 or w <= 0 or h <= 0:
msg = 'Crop must have non-negative x, y and positive w, h'
raise TileSourceError(msg)
self._crop = (x, y, w, h)

Check warning on line 620 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L618-L620

Added lines #L618 - L620 were not covered by tests

def write(
self,
path,
Expand All @@ -610,30 +635,56 @@ def write(
:param overwriteAllowed: if False, raise an exception if the output
path exists.
"""
# TODO: compute half, quarter, etc. resolutions
if not overwriteAllowed and os.path.exists(path):
raise TileSourceError('Output path exists (%s).' % str(path))

Check warning on line 640 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L640

Added line #L640 was not covered by tests
# TODO: apply cropping
# TODO: compute half, quarter, etc. resolutions

self._validateZarr()
suffix = Path(path).suffix
data_file = self._tempfile
data_store = self._zarr_store

if self.crop:
x, y, w, h = self.crop
current_arrays = dict(self._zarr.arrays())

Check warning on line 649 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L648-L649

Added lines #L648 - L649 were not covered by tests
# create new temp storage for cropped data
data_file = tempfile.NamedTemporaryFile()
data_store = zarr.SQLiteStore(data_file.name)
cropped_zarr = zarr.open(data_store, mode='w')

Check warning on line 653 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L651-L653

Added lines #L651 - L653 were not covered by tests
for arr_name in current_arrays:
arr = np.array(current_arrays[arr_name])
cropped_arr = arr.take(

Check warning on line 656 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L655-L656

Added lines #L655 - L656 were not covered by tests
indices=range(x, x + w),
axis=self._axes.get('x'),
).take(
indices=range(y, y + h),
axis=self._axes.get('y'),
)
cropped_zarr.create_dataset(arr_name, data=cropped_arr, overwrite=True)
cropped_zarr.attrs.update(self._zarr.attrs)

Check warning on line 664 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L663-L664

Added lines #L663 - L664 were not covered by tests

data_file.flush()

if suffix in ['.db', '.sqlite']:
shutil.copy2(self._tempfile.name, path)
shutil.copy2(data_file.name, path)

Check warning on line 669 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L669

Added line #L669 was not covered by tests

elif suffix == '.zip':
zip_store = zarr.storage.ZipStore(path)
zarr.copy_store(self._zarr_store, zip_store)
zarr.copy_store(data_store, zip_store)
zip_store.close()

elif suffix == '.zarr':
dir_store = zarr.storage.DirectoryStore(path)
zarr.copy_store(self._zarr_store, dir_store)
zarr.copy_store(data_store, dir_store)
dir_store.close()

Check warning on line 679 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L677-L679

Added lines #L677 - L679 were not covered by tests

else:
from large_image_converter import convert

Check warning on line 682 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L682

Added line #L682 was not covered by tests

self._tempfile.flush()
convert(self._tempfile.name, path, overwrite=overwriteAllowed)
convert(data_file.name, path, overwrite=overwriteAllowed)

Check warning on line 684 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L684

Added line #L684 was not covered by tests

if self.crop:
data_file.close()

Check warning on line 687 in sources/zarr/large_image_source_zarr/__init__.py

View check run for this annotation

Codecov / codecov/patch

sources/zarr/large_image_source_zarr/__init__.py#L687

Added line #L687 was not covered by tests


def open(*args, **kwargs):
Expand Down

0 comments on commit d697920

Please sign in to comment.