Coverage for colour/recovery/tests/test__init__.py: 100%

26 statements  

« prev     ^ index     » next       coverage.py v7.11.0, created at 2025-11-15 19:01 +1300

1"""Define the unit tests for the :mod:`colour.recovery` module.""" 

2 

3from __future__ import annotations 

4 

5import numpy as np 

6 

7from colour.colorimetry import ( 

8 MSDS_CMFS, 

9 SDS_ILLUMINANTS, 

10 SpectralShape, 

11 reshape_msds, 

12 reshape_sd, 

13 sd_to_XYZ_integration, 

14) 

15from colour.constants import TOLERANCE_ABSOLUTE_TESTS 

16from colour.recovery import XYZ_to_sd 

17from colour.utilities import domain_range_scale, is_scipy_installed 

18 

19__author__ = "Colour Developers" 

20__copyright__ = "Copyright 2013 Colour Developers" 

21__license__ = "BSD-3-Clause - https://opensource.org/licenses/BSD-3-Clause" 

22__maintainer__ = "Colour Developers" 

23__email__ = "colour-developers@colour-science.org" 

24__status__ = "Production" 

25 

26__all__ = [ 

27 "TestXYZ_to_sd", 

28] 

29 

30 

31class TestXYZ_to_sd: 

32 """ 

33 Define :func:`colour.recovery.XYZ_to_sd` definition unit tests 

34 methods. 

35 """ 

36 

37 def setup_method(self) -> None: 

38 """Initialise the common tests attributes.""" 

39 

40 self._cmfs = reshape_msds( 

41 MSDS_CMFS["CIE 1931 2 Degree Standard Observer"], 

42 SpectralShape(360, 780, 10), 

43 ) 

44 

45 self._sd_D65 = reshape_sd(SDS_ILLUMINANTS["D65"], self._cmfs.shape) 

46 

47 def test_domain_range_scale_XYZ_to_sd(self) -> None: 

48 """ 

49 Test :func:`colour.recovery.XYZ_to_sd` definition domain 

50 and range scale support. 

51 """ 

52 

53 if not is_scipy_installed(): # pragma: no cover 

54 return 

55 

56 XYZ = np.array([0.20654008, 0.12197225, 0.05136952]) 

57 m = ( 

58 "Jakob 2019", 

59 "Mallett 2019", 

60 "Meng 2015", 

61 "Otsu 2018", 

62 "Smits 1999", 

63 ) 

64 v = [ 

65 sd_to_XYZ_integration( 

66 XYZ_to_sd(XYZ, method, cmfs=self._cmfs, illuminant=self._sd_D65), 

67 self._cmfs, 

68 self._sd_D65, 

69 ) 

70 for method in m 

71 ] 

72 

73 d_r = (("reference", 1, 1), ("1", 1, 0.01), ("100", 100, 1)) 

74 for method, value in zip(m, v, strict=True): 

75 for scale, factor_a, factor_b in d_r: 

76 with domain_range_scale(scale): 

77 np.testing.assert_allclose( 

78 sd_to_XYZ_integration( 

79 XYZ_to_sd( 

80 XYZ * factor_a, 

81 method, 

82 cmfs=self._cmfs, 

83 illuminant=self._sd_D65, 

84 ), 

85 self._cmfs, 

86 self._sd_D65, 

87 ), 

88 value * factor_b, 

89 atol=TOLERANCE_ABSOLUTE_TESTS, 

90 )