Coverage for tests / test_image.py: 28%
39 statements
« prev ^ index » next coverage.py v7.13.5, created at 2026-03-27 01:47 -0700
« prev ^ index » next coverage.py v7.13.5, created at 2026-03-27 01:47 -0700
1# This file is part of lsst-images.
2#
3# Developed for the LSST Data Management System.
4# This product includes software developed by the LSST Project
5# (https://www.lsst.org).
6# See the COPYRIGHT file at the top-level directory of this distribution
7# for details of code ownership.
8#
9# Use of this source code is governed by a 3-clause BSD-style
10# license that can be found in the LICENSE file.
12from __future__ import annotations
14import os
15import unittest
17import numpy as np
19from lsst.images import Box, Image
20from lsst.images.tests import assert_close, assert_images_equal, compare_image_to_legacy
22DATA_DIR = os.environ.get("TESTDATA_IMAGES_DIR", None)
25class ImageTestCase(unittest.TestCase):
26 """Tests for the Image class."""
28 def test_basics(self):
29 """Test basic constructor patterns."""
30 image = Image(42, shape=(5, 5), metadata={"three": 3})
31 assert_close(self, image.array, np.zeros([5, 5], dtype=np.int64) + 42)
32 self.assertEqual(image.metadata["three"], 3)
34 data = np.array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12]])
35 image = Image(data)
36 subset = image[Box.factory[:3, 1:3]]
37 subset2 = image.absolute[:3, 1:3]
38 assert_images_equal(self, subset2, subset, expect_view=True)
40 assert_images_equal(self, image.copy(), image, expect_view=False)
42 # Add an explicit bounding box and then slice it.
43 image = Image(data, bbox=Box.factory[-2:1, 10:14])
44 with self.assertRaises(IndexError):
45 # Same slice no longer works in absolute slicing because we have
46 # moved origin.
47 image.absolute[:3, 1:3]
48 # That slice does still work in local coordinates.
49 assert_close(self, image.local[:3, 1:3].array, subset2.array)
50 # And we can write an equivalent slice in absolute coordinates.
51 assert_close(self, image.absolute[:0, 11:13].array, np.array([[2, 3], [6, 7]]))
53 @unittest.skipUnless(DATA_DIR is not None, "TESTDATA_IMAGES_DIR is not in the environment.")
54 def test_legacy(self) -> None:
55 """Test Image.read_legacy, Image.to_legacy, and Image.from_legacy."""
56 assert DATA_DIR is not None, "Guaranteed by decorator."
57 filename = os.path.join(DATA_DIR, "dp2", "legacy", "visit_image.fits")
58 image = Image.read_legacy(filename, preserve_quantization=True)
59 try:
60 from lsst.afw.image import MaskedImageFitsReader
61 except ImportError:
62 raise unittest.SkipTest("'lsst.afw.image' could not be imported.") from None
63 reader = MaskedImageFitsReader(filename)
64 legacy_image = reader.readImage()
65 compare_image_to_legacy(self, image, legacy_image, expect_view=False)
66 # Converting back to afw will not share memory, because
67 # preserve_quantization=True makes the array read-only and to_legacy
68 # has to copy in that case.
69 compare_image_to_legacy(self, image, image.to_legacy(), expect_view=False)
70 # Converting from afw will always share memory.
71 image_view = Image.from_legacy(legacy_image)
72 compare_image_to_legacy(self, image_view, legacy_image, expect_view=True)
73 # Converting back to afw from the in-memory view will be another view.
74 compare_image_to_legacy(self, image_view, image_view.to_legacy(), expect_view=True)
77if __name__ == "__main__":
78 unittest.main()