Coverage for models/rgb/tests/test_ictcp.py: 100%

1"""Define the unit tests for the :mod:`colour.models.rgb.ictcp` module."""

2

3 from __future__ import annotations

4

5 from itertools import product

6

7 import numpy as np

8

9 from colour.constants import TOLERANCE_ABSOLUTE_TESTS

10 from colour.models.rgb import ICtCp_to_RGB, ICtCp_to_XYZ, RGB_to_ICtCp, XYZ_to_ICtCp

11 from colour.utilities import domain_range_scale, ignore_numpy_errors

12

13 __author__ = "Colour Developers"

14 __copyright__ = "Copyright 2013 Colour Developers"

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

16 __maintainer__ = "Colour Developers"

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

18 __status__ = "Production"

19

20 __all__ = [

21 "TestRGB_to_ICtCp",

22 "TestICtCp_to_RGB",

23 "TestXYZ_to_ICtCp",

24 "TestICtCp_to_XYZ",

25]

26

27

28 class TestRGB_to_ICtCp:

29 """

30 Define :func:`colour.models.rgb.ictcp.TestRGB_to_ICtCp` definition unit

31 tests methods.

32 """

33

34 def test_RGB_to_ICtCp(self) -> None:

35 """Test :func:`colour.models.rgb.ictcp.RGB_to_ICtCp` definition."""

36

37 np.testing.assert_allclose(

38 RGB_to_ICtCp(np.array([0.45620519, 0.03081071, 0.04091952])),

39 np.array([0.07351364, 0.00475253, 0.09351596]),

40 atol=TOLERANCE_ABSOLUTE_TESTS,

41 )

42

43 np.testing.assert_allclose(

44 RGB_to_ICtCp(np.array([0.45620519, 0.03081071, 0.04091952]), L_p=4000),

45 np.array([0.10516931, 0.00514031, 0.12318730]),

46 atol=TOLERANCE_ABSOLUTE_TESTS,

47 )

48

49 np.testing.assert_allclose(

50 RGB_to_ICtCp(np.array([0.45620519, 0.03081071, 0.04091952]), L_p=1000),

51 np.array([0.17079612, 0.00485580, 0.17431356]),

52 atol=TOLERANCE_ABSOLUTE_TESTS,

53 )

54

55 np.testing.assert_allclose(

56 RGB_to_ICtCp(

57 np.array([0.45620519, 0.03081071, 0.04091952]),

58 method="ITU-R BT.2100-1 PQ",

59 ),

60 np.array([0.07351364, 0.00475253, 0.09351596]),

61 atol=TOLERANCE_ABSOLUTE_TESTS,

62 )

63

64 np.testing.assert_allclose(

65 RGB_to_ICtCp(

66 np.array([0.45620519, 0.03081071, 0.04091952]),

67 method="ITU-R BT.2100-2 PQ",

68 ),

69 np.array([0.07351364, 0.00475253, 0.09351596]),

70 atol=TOLERANCE_ABSOLUTE_TESTS,

71 )

72

73 np.testing.assert_allclose(

74 RGB_to_ICtCp(

75 np.array([0.45620519, 0.03081071, 0.04091952]),

76 method="ITU-R BT.2100-1 HLG",

77 ),

78 np.array([0.62567899, -0.03622422, 0.67786522]),

79 atol=TOLERANCE_ABSOLUTE_TESTS,

80 )

81

82 np.testing.assert_allclose(

83 RGB_to_ICtCp(

84 np.array([0.45620519, 0.03081071, 0.04091952]),

85 method="ITU-R BT.2100-2 HLG",

86 ),

87 np.array([0.62567899, -0.01984490, 0.35911259]),

88 atol=TOLERANCE_ABSOLUTE_TESTS,

89 )

90

91 def test_n_dimensional_RGB_to_ICtCp(self) -> None:

92 """

93 Test :func:`colour.models.rgb.ictcp.RGB_to_ICtCp` definition

94 n-dimensional support.

95 """

96

97 RGB = np.array([0.45620519, 0.03081071, 0.04091952])

98 ICtCp = RGB_to_ICtCp(RGB)

99

100 RGB = np.tile(RGB, (6, 1))

101 ICtCp = np.tile(ICtCp, (6, 1))

102 np.testing.assert_allclose(

103 RGB_to_ICtCp(RGB), ICtCp, atol=TOLERANCE_ABSOLUTE_TESTS

104 )

105

106 RGB = np.reshape(RGB, (2, 3, 3))

107 ICtCp = np.reshape(ICtCp, (2, 3, 3))

108 np.testing.assert_allclose(

109 RGB_to_ICtCp(RGB), ICtCp, atol=TOLERANCE_ABSOLUTE_TESTS

110 )

111

112 def test_domain_range_scale_RGB_to_ICtCp(self) -> None:

113 """

114 Test :func:`colour.models.rgb.ictcp.RGB_to_ICtCp` definition domain

115 and range scale support.

116 """

117

118 RGB = np.array([0.45620519, 0.03081071, 0.04091952])

119 ICtCp = RGB_to_ICtCp(RGB)

120

121 d_r = (("reference", 1), ("1", 1), ("100", 1))

122 for scale, factor in d_r:

123 with domain_range_scale(scale):

124 np.testing.assert_allclose(

125 RGB_to_ICtCp(RGB * factor),

126 ICtCp * factor,

127 atol=TOLERANCE_ABSOLUTE_TESTS,

128 )

129

130 @ignore_numpy_errors

131 def test_nan_RGB_to_ICtCp(self) -> None:

132 """

133 Test :func:`colour.models.rgb.ictcp.RGB_to_ICtCp` definition nan

134 support.

135 """

136

137 cases = [-1.0, 0.0, 1.0, -np.inf, np.inf, np.nan]

138 cases = np.array(list(set(product(cases, repeat=3))))

139 RGB_to_ICtCp(cases)

140

141

142 class TestICtCp_to_RGB:

143 """

144 Define :func:`colour.models.rgb.ictcp.ICtCp_to_RGB` definition unit tests

145 methods.

146 """

147

148 def test_ICtCp_to_RGB(self) -> None:

149 """Test :func:`colour.models.rgb.ictcp.ICtCp_to_RGB` definition."""

150

151 np.testing.assert_allclose(

152 ICtCp_to_RGB(np.array([0.07351364, 0.00475253, 0.09351596])),

153 np.array([0.45620519, 0.03081071, 0.04091952]),

154 atol=TOLERANCE_ABSOLUTE_TESTS,

155 )

156

157 np.testing.assert_allclose(

158 ICtCp_to_RGB(np.array([0.10516931, 0.00514031, 0.12318730]), L_p=4000),

159 np.array([0.45620519, 0.03081071, 0.04091952]),

160 atol=TOLERANCE_ABSOLUTE_TESTS,

161 )

162

163 np.testing.assert_allclose(

164 ICtCp_to_RGB(np.array([0.17079612, 0.00485580, 0.17431356]), L_p=1000),

165 np.array([0.45620519, 0.03081071, 0.04091952]),

166 atol=TOLERANCE_ABSOLUTE_TESTS,

167 )

168

169 np.testing.assert_allclose(

170 ICtCp_to_RGB(

171 np.array([0.07351364, 0.00475253, 0.09351596]),

172 method="ITU-R BT.2100-1 PQ",

173 ),

174 np.array([0.45620519, 0.03081071, 0.04091952]),

175 atol=TOLERANCE_ABSOLUTE_TESTS,

176 )

177

178 np.testing.assert_allclose(

179 ICtCp_to_RGB(

180 np.array([0.07351364, 0.00475253, 0.09351596]),

181 method="ITU-R BT.2100-2 PQ",

182 ),

183 np.array([0.45620519, 0.03081071, 0.04091952]),

184 atol=TOLERANCE_ABSOLUTE_TESTS,

185 )

186

187 np.testing.assert_allclose(

188 ICtCp_to_RGB(

189 np.array([0.62567899, -0.03622422, 0.67786522]),

190 method="ITU-R BT.2100-1 HLG",

191 ),

192 np.array([0.45620519, 0.03081071, 0.04091952]),

193 atol=TOLERANCE_ABSOLUTE_TESTS,

194 )

195

196 np.testing.assert_allclose(

197 ICtCp_to_RGB(

198 np.array([0.62567899, -0.01984490, 0.35911259]),

199 method="ITU-R BT.2100-2 HLG",

200 ),

201 np.array([0.45620519, 0.03081071, 0.04091952]),

202 atol=TOLERANCE_ABSOLUTE_TESTS,

203 )

204

205 def test_n_dimensional_ICtCp_to_RGB(self) -> None:

206 """

207 Test :func:`colour.models.rgb.ictcp.ICtCp_to_RGB` definition

208 n-dimensional support.

209 """

210

211 ICtCp = np.array([0.07351364, 0.00475253, 0.09351596])

212 RGB = ICtCp_to_RGB(ICtCp)

213

214 ICtCp = np.tile(ICtCp, (6, 1))

215 RGB = np.tile(RGB, (6, 1))

216 np.testing.assert_allclose(

217 ICtCp_to_RGB(ICtCp), RGB, atol=TOLERANCE_ABSOLUTE_TESTS

218 )

219

220 ICtCp = np.reshape(ICtCp, (2, 3, 3))

221 RGB = np.reshape(RGB, (2, 3, 3))

222 np.testing.assert_allclose(

223 ICtCp_to_RGB(ICtCp), RGB, atol=TOLERANCE_ABSOLUTE_TESTS

224 )

225

226 def test_domain_range_scale_ICtCp_to_RGB(self) -> None:

227 """

228 Test :func:`colour.models.rgb.ictcp.ICtCp_to_RGB` definition domain

229 and range scale support.

230 """

231

232 ICtCp = np.array([0.07351364, 0.00475253, 0.09351596])

233 RGB = ICtCp_to_RGB(ICtCp)

234

235 d_r = (("reference", 1), ("1", 1), ("100", 1))

236 for scale, factor in d_r:

237 with domain_range_scale(scale):

238 np.testing.assert_allclose(

239 ICtCp_to_RGB(ICtCp * factor),

240 RGB * factor,

241 atol=TOLERANCE_ABSOLUTE_TESTS,

242 )

243

244 @ignore_numpy_errors

245 def test_nan_ICtCp_to_RGB(self) -> None:

246 """

247 Test :func:`colour.models.rgb.ictcp.ICtCp_to_RGB` definition nan

248 support.

249 """

250

251 cases = [-1.0, 0.0, 1.0, -np.inf, np.inf, np.nan]

252 cases = np.array(list(set(product(cases, repeat=3))))

253 ICtCp_to_RGB(cases)

254

255

256 class TestXYZ_to_ICtCp:

257 """

258 Define :func:`colour.models.rgb.ictcp.TestXYZ_to_ICtCp` definition unit

259 tests methods.

260 """

261

262 def test_XYZ_to_ICtCp(self) -> None:

263 """Test :func:`colour.models.rgb.ictcp.XYZ_to_ICtCp` definition."""

264

265 np.testing.assert_allclose(

266 XYZ_to_ICtCp(np.array([0.20654008, 0.12197225, 0.05136952])),

267 np.array([0.06858097, -0.00283842, 0.06020983]),

268 atol=TOLERANCE_ABSOLUTE_TESTS,

269 )

270

271 np.testing.assert_allclose(

272 XYZ_to_ICtCp(

273 np.array([0.20654008, 0.12197225, 0.05136952]),

274 np.array([0.34570, 0.35850]),

275 ),

276 np.array([0.06792437, 0.00452089, 0.05514480]),

277 atol=TOLERANCE_ABSOLUTE_TESTS,

278 )

279

280 np.testing.assert_allclose(

281 XYZ_to_ICtCp(

282 np.array([0.20654008, 0.12197225, 0.05136952]),

283 np.array([0.34570, 0.35850]),

284 chromatic_adaptation_transform="Bradford",

285 ),

286 np.array([0.06783951, 0.00476111, 0.05523093]),

287 atol=TOLERANCE_ABSOLUTE_TESTS,

288 )

289

290 np.testing.assert_allclose(

291 XYZ_to_ICtCp(np.array([0.20654008, 0.12197225, 0.05136952]), L_p=4000),

292 np.array([0.09871102, -0.00447247, 0.07984812]),

293 atol=TOLERANCE_ABSOLUTE_TESTS,

294 )

295

296 np.testing.assert_allclose(

297 XYZ_to_ICtCp(np.array([0.20654008, 0.12197225, 0.05136952]), L_p=1000),

298 np.array([0.16173872, -0.00792543, 0.11409458]),

299 atol=TOLERANCE_ABSOLUTE_TESTS,

300 )

301

302 np.testing.assert_allclose(

303 XYZ_to_ICtCp(

304 np.array([0.20654008, 0.12197225, 0.05136952]),

305 method="ITU-R BT.2100-1 PQ",

306 ),

307 np.array([0.06858097, -0.00283842, 0.06020983]),

308 atol=TOLERANCE_ABSOLUTE_TESTS,

309 )

310

311 np.testing.assert_allclose(

312 XYZ_to_ICtCp(

313 np.array([0.20654008, 0.12197225, 0.05136952]),

314 method="ITU-R BT.2100-2 PQ",

315 ),

316 np.array([0.06858097, -0.00283842, 0.06020983]),

317 atol=TOLERANCE_ABSOLUTE_TESTS,

318 )

319

320 np.testing.assert_allclose(

321 XYZ_to_ICtCp(

322 np.array([0.20654008, 0.12197225, 0.05136952]),

323 method="ITU-R BT.2100-1 HLG",

324 ),

325 np.array([0.59242792, -0.06824263, 0.47421473]),

326 atol=TOLERANCE_ABSOLUTE_TESTS,

327 )

328

329 np.testing.assert_allclose(

330 XYZ_to_ICtCp(

331 np.array([0.20654008, 0.12197225, 0.05136952]),

332 method="ITU-R BT.2100-2 HLG",

333 ),

334 np.array([0.59242792, -0.03740730, 0.25122675]),

335 atol=TOLERANCE_ABSOLUTE_TESTS,

336 )

337

338 def test_n_dimensional_XYZ_to_ICtCp(self) -> None:

339 """

340 Test :func:`colour.models.rgb.ictcp.XYZ_to_ICtCp` definition

341 n-dimensional support.

342 """

343

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

345 ICtCp = XYZ_to_ICtCp(XYZ)

346

347 XYZ = np.tile(XYZ, (6, 1))

348 ICtCp = np.tile(ICtCp, (6, 1))

349 np.testing.assert_allclose(

350 XYZ_to_ICtCp(XYZ), ICtCp, atol=TOLERANCE_ABSOLUTE_TESTS

351 )

352

353 XYZ = np.reshape(XYZ, (2, 3, 3))

354 ICtCp = np.reshape(ICtCp, (2, 3, 3))

355 np.testing.assert_allclose(

356 XYZ_to_ICtCp(XYZ), ICtCp, atol=TOLERANCE_ABSOLUTE_TESTS

357 )

358

359 def test_domain_range_scale_XYZ_to_ICtCp(self) -> None:

360 """

361 Test :func:`colour.models.rgb.ictcp.XYZ_to_ICtCp` definition domain

362 and range scale support.

363 """

364

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

366 ICtCp = XYZ_to_ICtCp(XYZ)

367

368 d_r = (("reference", 1), ("1", 1), ("100", 1))

369 for scale, factor in d_r:

370 with domain_range_scale(scale):

371 np.testing.assert_allclose(

372 XYZ_to_ICtCp(XYZ * factor),

373 ICtCp * factor,

374 atol=TOLERANCE_ABSOLUTE_TESTS,

375 )

376

377 @ignore_numpy_errors

378 def test_nan_XYZ_to_ICtCp(self) -> None:

379 """

380 Test :func:`colour.models.rgb.ictcp.XYZ_to_ICtCp` definition nan

381 support.

382 """

383

384 cases = [-1.0, 0.0, 1.0, -np.inf, np.inf, np.nan]

385 cases = np.array(list(set(product(cases, repeat=3))))

386 XYZ_to_ICtCp(cases)

387

388

389 class TestICtCp_to_XYZ:

390 """

391 Define :func:`colour.models.rgb.ictcp.ICtCp_to_XYZ` definition unit tests

392 methods.

393 """

394

395 def test_ICtCp_to_XYZ(self) -> None:

396 """Test :func:`colour.models.rgb.ictcp.ICtCp_to_XYZ` definition."""

397

398 np.testing.assert_allclose(

399 ICtCp_to_XYZ(np.array([0.06858097, -0.00283842, 0.06020983])),

400 np.array([0.20654008, 0.12197225, 0.05136952]),

401 atol=TOLERANCE_ABSOLUTE_TESTS,

402 )

403

404 np.testing.assert_allclose(

405 ICtCp_to_XYZ(

406 np.array([0.06792437, 0.00452089, 0.05514480]),

407 np.array([0.34570, 0.35850]),

408 ),

409 np.array([0.20654008, 0.12197225, 0.05136952]),

410 atol=TOLERANCE_ABSOLUTE_TESTS,

411 )

412

413 np.testing.assert_allclose(

414 ICtCp_to_XYZ(

415 np.array([0.06783951, 0.00476111, 0.05523093]),

416 np.array([0.34570, 0.35850]),

417 chromatic_adaptation_transform="Bradford",

418 ),

419 np.array([0.20654008, 0.12197225, 0.05136952]),

420 atol=TOLERANCE_ABSOLUTE_TESTS,

421 )

422

423 np.testing.assert_allclose(

424 ICtCp_to_XYZ(np.array([0.09871102, -0.00447247, 0.07984812]), L_p=4000),

425 np.array([0.20654008, 0.12197225, 0.05136952]),

426 atol=TOLERANCE_ABSOLUTE_TESTS,

427 )

428

429 np.testing.assert_allclose(

430 ICtCp_to_XYZ(np.array([0.16173872, -0.00792543, 0.11409458]), L_p=1000),

431 np.array([0.20654008, 0.12197225, 0.05136952]),

432 atol=TOLERANCE_ABSOLUTE_TESTS,

433 )

434

435 np.testing.assert_allclose(

436 ICtCp_to_XYZ(

437 np.array([0.06858097, -0.00283842, 0.06020983]),

438 method="ITU-R BT.2100-1 PQ",

439 ),

440 np.array([0.20654008, 0.12197225, 0.05136952]),

441 atol=TOLERANCE_ABSOLUTE_TESTS,

442 )

443

444 np.testing.assert_allclose(

445 ICtCp_to_XYZ(

446 np.array([0.06858097, -0.00283842, 0.06020983]),

447 method="ITU-R BT.2100-2 PQ",

448 ),

449 np.array([0.20654008, 0.12197225, 0.05136952]),

450 atol=TOLERANCE_ABSOLUTE_TESTS,

451 )

452

453 np.testing.assert_allclose(

454 ICtCp_to_XYZ(

455 np.array([0.59242792, -0.06824263, 0.47421473]),

456 method="ITU-R BT.2100-1 HLG",

457 ),

458 np.array([0.20654008, 0.12197225, 0.05136952]),

459 atol=TOLERANCE_ABSOLUTE_TESTS,

460 )

461

462 np.testing.assert_allclose(

463 ICtCp_to_XYZ(

464 np.array([0.59242792, -0.03740730, 0.25122675]),

465 method="ITU-R BT.2100-2 HLG",

466 ),

467 np.array([0.20654008, 0.12197225, 0.05136952]),

468 atol=TOLERANCE_ABSOLUTE_TESTS,

469 )

470

471 def test_n_dimensional_ICtCp_to_XYZ(self) -> None:

472 """

473 Test :func:`colour.models.rgb.ictcp.ICtCp_to_XYZ` definition

474 n-dimensional support.

475 """

476

477 ICtCp = np.array([0.06858097, -0.00283842, 0.06020983])

478 XYZ = ICtCp_to_XYZ(ICtCp)

479

480 ICtCp = np.tile(ICtCp, (6, 1))

481 XYZ = np.tile(XYZ, (6, 1))

482 np.testing.assert_allclose(

483 ICtCp_to_XYZ(ICtCp), XYZ, atol=TOLERANCE_ABSOLUTE_TESTS

484 )

485

486 ICtCp = np.reshape(ICtCp, (2, 3, 3))

487 XYZ = np.reshape(XYZ, (2, 3, 3))

488 np.testing.assert_allclose(

489 ICtCp_to_XYZ(ICtCp), XYZ, atol=TOLERANCE_ABSOLUTE_TESTS

490 )

491

492 def test_domain_range_scale_ICtCp_to_XYZ(self) -> None:

493 """

494 Test :func:`colour.models.rgb.ictcp.ICtCp_to_XYZ` definition domain

495 and range scale support.

496 """

497

498 ICtCp = np.array([0.06858097, -0.00283842, 0.06020983])

499 XYZ = ICtCp_to_XYZ(ICtCp)

500

501 d_r = (("reference", 1), ("1", 1), ("100", 1))

502 for scale, factor in d_r:

503 with domain_range_scale(scale):

504 np.testing.assert_allclose(

505 ICtCp_to_XYZ(ICtCp * factor),

506 XYZ * factor,

507 atol=TOLERANCE_ABSOLUTE_TESTS,

508 )

509

510 @ignore_numpy_errors

511 def test_nan_ICtCp_to_XYZ(self) -> None:

512 """

513 Test :func:`colour.models.rgb.ictcp.ICtCp_to_XYZ` definition nan

514 support.

515 """

516

517 cases = [-1.0, 0.0, 1.0, -np.inf, np.inf, np.nan]

518 cases = np.array(list(set(product(cases, repeat=3))))

519 ICtCp_to_XYZ(cases)