farbraum/spaces/
adobe98.rs1use crate::illuminate::D65;
2use crate::spaces::{Adobe98, CieXyz, Srgb};
3use crate::{Color, Float, Into};
4
5fn linearize(v: Float) -> Float {
6 v.abs().powf(563.0 / 256.0) * v.signum()
7}
8
9impl Into<CieXyz<D65>> for Color<Adobe98> {
10 fn into(self, _: CieXyz<D65>) -> Color<CieXyz<D65>> {
11 let (r, g, b) = self.tuple();
12 let r = linearize(r);
13 let g = linearize(g);
14 let b = linearize(b);
15 Color::of(
16 0.5766690429101305 * r + 0.1855582379065463 * g + 0.1882286462349947 * b,
17 0.29734497525053605 * r + 0.6273635662554661 * g + 0.07529145849399788 * b,
18 0.02703136138641234 * r + 0.07068885253582723 * g + 0.9913375368376388 * b,
19 )
20 }
21}
22
23fn gamma(v: Float) -> Float {
24 v.abs().powf(256.0 / 563.0) * v.signum()
25}
26
27impl Into<Adobe98> for Color<CieXyz<D65>> {
28 fn into(self, _: Adobe98) -> Color<Adobe98> {
29 let (x, y, z) = self.tuple();
30 Color::of(
31 gamma(x * 2.0415879038107465 - y * 0.5650069742788596 - 0.34473135077832956 * z),
32 gamma(x * -0.9692436362808795 + y * 1.8759675015077202 + 0.04155505740717557 * z),
33 gamma(x * 0.013444280632031142 - y * 0.11836239223101838 + 1.0151749943912054 * z),
34 )
35 }
36}
37
38impl Into<Adobe98> for Color<Srgb> {
39 fn into(self, s: Adobe98) -> Color<Adobe98> {
40 self.into(CieXyz(D65)).into(s)
41 }
42}
43
44impl Into<Srgb> for Color<Adobe98> {
45 fn into(self, s: Srgb) -> Color<Srgb> {
46 self.into(CieXyz(D65)).into(s)
47 }
48}
49
50#[cfg(test)]
51mod tests {
52 use crate::spaces::{Adobe98, Srgb};
53 use crate::test_util::round_trips_srgb;
54 use crate::{Color, Float};
55
56 fn rgb(r: Float, g: Float, b: Float) -> Color<Srgb> {
57 Color::of(r, g, b)
58 }
59
60 fn a98(r: Float, g: Float, b: Float) -> Color<Adobe98> {
61 Color::of(r, g, b)
62 }
63
64 #[test]
65 fn test_adobe98() {
66 assert_almost_eq!(
67 rgb(1.0, 1.0, 1.0).into(Adobe98),
68 a98(1.0000487485, 0.9999895104, 0.99989495005),
69 );
70 assert_almost_eq!(rgb(0.0, 0.0, 0.0).into(Adobe98), a98(0.0, 0.0, 0.0));
71 assert_almost_eq!(
72 rgb(1.0, 0.0, 0.0).into(Adobe98),
73 a98(0.85865373273, -0.000124357058167, 0.000221323599465),
74 );
75 }
76
77 #[test]
78 fn test_adobe98_roundtrips() {
79 round_trips_srgb::<Adobe98>();
80 }
81}