From f2f9d08acc29150bb0f8a9220ff1632854a8ab08 Mon Sep 17 00:00:00 2001 From: Erwan Rouchet <rouchet@teklia.com> Date: Tue, 23 Nov 2021 15:03:38 +0100 Subject: [PATCH] Add rotation and mirroring to IIIF thumbnail URLs --- arkindex/documents/models.py | 19 +++++-- arkindex/documents/tests/test_element.py | 70 ++++++++++++++++++++++++ 2 files changed, 85 insertions(+), 4 deletions(-) create mode 100644 arkindex/documents/tests/test_element.py diff --git a/arkindex/documents/models.py b/arkindex/documents/models.py index be9bdb05f4..713103e9e5 100644 --- a/arkindex/documents/models.py +++ b/arkindex/documents/models.py @@ -370,11 +370,22 @@ class Element(IndexableModel): @property def iiif_thumbnail_url(self): """ - Same as `iiif_url`, but resized to up to 400 pixels + Same as `iiif_url`, but resized to up to 400 pixels and with rotation and mirroring """ - iiif_url = self.iiif_url - if iiif_url: - return self.iiif_url.replace('full', ',400') + if not self.polygon or not self.image_id: + return + + from arkindex.project.tools import bounding_box + x, y, width, height = bounding_box(self.polygon) + + rotation_param = str(self.rotation_angle) + if self.mirrored: + rotation_param = f'!{rotation_param}' + + return urljoin( + self.image.url + '/', + f'{x},{y},{width},{height}/,400/{rotation_param}/default.jpg' + ) def __str__(self): return '{}: {}'.format(self.type.display_name, self.name) diff --git a/arkindex/documents/tests/test_element.py b/arkindex/documents/tests/test_element.py new file mode 100644 index 0000000000..251da5e06a --- /dev/null +++ b/arkindex/documents/tests/test_element.py @@ -0,0 +1,70 @@ +from arkindex.documents.models import Element +from arkindex.project.tests import FixtureTestCase + + +class TestElement(FixtureTestCase): + + @classmethod + def setUpTestData(cls): + super().setUpTestData() + cls.element_type = cls.corpus.types.first() + cls.image = cls.imgsrv.images.get(path='img1') + + def test_iiif_url(self): + # Rotation and mirroring should be ignored in iiif_url + cases = [ + (0, False), + (0, True), + (180, False), + (180, True), + ] + for rotation_angle, mirrored in cases: + with self.subTest(rotation_angle=rotation_angle, mirrored=mirrored): + element = Element( + name='Something', + type=self.element_type, + image=self.image, + polygon=[ + [10, 20], + [40, 20], + [40, 60], + [10, 60], + [10, 20], + ], + rotation_angle=rotation_angle, + mirrored=mirrored, + ) + self.assertEqual(element.iiif_url, 'http://server/img1/10,20,30,40/full/0/default.jpg') + + def test_iiif_thumbnail_url(self): + cases = [ + (0, False, 'http://server/img1/10,20,30,40/,400/0/default.jpg'), + (0, True, 'http://server/img1/10,20,30,40/,400/!0/default.jpg'), + (180, False, 'http://server/img1/10,20,30,40/,400/180/default.jpg'), + (180, True, 'http://server/img1/10,20,30,40/,400/!180/default.jpg'), + ] + for rotation_angle, mirrored, expected_url in cases: + with self.subTest(rotation_angle=rotation_angle, mirrored=mirrored): + element = Element( + name='Something', + type=self.element_type, + image=self.image, + polygon=[ + [10, 20], + [40, 20], + [40, 60], + [10, 60], + [10, 20], + ], + rotation_angle=rotation_angle, + mirrored=mirrored, + ) + self.assertEqual(element.iiif_thumbnail_url, expected_url) + + def test_no_image_no_url(self): + element = Element( + name='Something', + type=self.element_type, + ) + self.assertIsNone(element.iiif_url) + self.assertIsNone(element.iiif_thumbnail_url) -- GitLab