diff --git a/tests/test_crop_presets.py b/tests/test_crop_presets.py new file mode 100644 index 0000000..e6e039e --- /dev/null +++ b/tests/test_crop_presets.py @@ -0,0 +1,42 @@ +"""Covers the crop presets offered for a Frame TV panel. + +Run with: pytest tests/test_crop_presets.py +""" + +import pytest +from PIL import Image as PILImage + +from utils.crop_image import CROP_PRESETS, CropImageError, get_preset_crop_box + + +@pytest.fixture +def image(tmp_path): + def make(width, height): + path = tmp_path / f"{width}x{height}.png" + PILImage.new("RGB", (width, height), "red").save(path) + return str(path) + return make + + +def test_the_frame_tv_panel_size_is_offered_as_a_preset(): + assert CROP_PRESETS["3840x2160"]["width"] == 3840 + assert CROP_PRESETS["3840x2160"]["height"] == 2160 + + +def test_the_4k_preset_takes_a_centred_panel_sized_crop(image): + x, y, width, height = get_preset_crop_box(image(4200, 2400), "3840x2160") + + assert (width, height) == (3840, 2160), "exactly the panel, no rescaling on the TV" + assert x == (4200 - 3840) // 2 and y == (2400 - 2160) // 2, "centred" + + +def test_a_source_smaller_than_the_panel_is_not_asked_for_more_than_it_has(image): + x, y, width, height = get_preset_crop_box(image(1600, 900), "3840x2160") + + assert (x, y) == (0, 0) + assert (width, height) == (1600, 900), "the whole image, not a box past its edge" + + +def test_an_unknown_preset_is_refused(image): + with pytest.raises(CropImageError): + get_preset_crop_box(image(4200, 2400), "not-a-preset") diff --git a/utils/crop_image.py b/utils/crop_image.py index b8d6a96..e2e5ade 100644 --- a/utils/crop_image.py +++ b/utils/crop_image.py @@ -21,6 +21,9 @@ class CropImageError(Exception): '1024x768': {'width': 1024, 'height': 768, 'label': '1024x768 (4:3)'}, '1280x960': {'width': 1280, 'height': 960, 'label': '1280x960 (4:3)'}, '1920x1080': {'width': 1920, 'height': 1080, 'label': '1920x1080 (16:9)'}, + # A Frame TV reports resolution_type UHD, so this is the one that fills the panel + # without the set having to rescale. + '3840x2160': {'width': 3840, 'height': 2160, 'label': '3840x2160 (4K, Frame TV)'}, }