Skip to content

Commit

Permalink
Fix export of masks with holes (cvat-ai#188)
Browse files Browse the repository at this point in the history
* Fix export of masks with holes in polygons (background class should not introduce a new instance)

* update changelog
  • Loading branch information
Maxim Zhiltsov authored Mar 31, 2021
1 parent ce69969 commit 0f18908
Show file tree
Hide file tree
Showing 3 changed files with 25 additions and 0 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
-

### Fixed
- Instance masks of `background` class no more introduce an instance (<https://github.com/openvinotoolkit/datumaro/pull/188>)
- Added support for label attributes in Datumaro format (<https://github.com/openvinotoolkit/datumaro/pull/192>)

### Security
Expand Down
4 changes: 4 additions & 0 deletions datumaro/components/extractor.py
Original file line number Diff line number Diff line change
Expand Up @@ -264,11 +264,15 @@ def from_instance_masks(instance_masks,
class_map = [0]

m, idx, instance_id, class_id = next(it)
if not class_id:
idx = 0
index_mask = make_index_mask(m, idx)
instance_map.append(instance_id)
class_map.append(class_id)

for m, idx, instance_id, class_id in it:
if not class_id:
idx = 0
index_mask = np.where(m, idx, index_mask)
instance_map.append(instance_id)
class_map.append(class_id)
Expand Down
20 changes: 20 additions & 0 deletions tests/test_voc_format.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
from datumaro.plugins.voc_format.importer import VocImporter
from datumaro.components.dataset import Dataset
from datumaro.util.image import Image
from datumaro.util.mask_tools import load_mask
from datumaro.util.test_utils import (TestDir, compare_datasets,
test_save_and_load)

Expand Down Expand Up @@ -628,6 +629,25 @@ def categories(self):
partial(VocConverter.convert, label_map=label_map),
test_dir, target_dataset=DstExtractor())

def test_background_masks_dont_introduce_instances_but_cover_others(self):
dataset = Dataset.from_iterable([
DatasetItem(1, image=np.zeros((4, 1, 1)), annotations=[
Mask([1, 1, 1, 1], label=1, attributes={'z_order': 1}),
Mask([0, 0, 1, 1], label=2, attributes={'z_order': 2}),
Mask([0, 0, 1, 1], label=0, attributes={'z_order': 3}),
])
], categories=['background', 'a', 'b'])

with TestDir() as test_dir:
VocConverter.convert(dataset, test_dir, apply_colormap=False)

cls_mask = load_mask(
osp.join(test_dir, 'SegmentationClass', '1.png'))
inst_mask = load_mask(
osp.join(test_dir, 'SegmentationObject', '1.png'))
self.assertTrue(np.array_equal([0, 1], np.unique(cls_mask)))
self.assertTrue(np.array_equal([0, 1], np.unique(inst_mask)))

def test_can_save_dataset_with_image_info(self):
class TestExtractor(TestExtractorBase):
def __iter__(self):
Expand Down

0 comments on commit 0f18908

Please sign in to comment.