xref: /aosp_15_r20/external/skia/src/core/SkColorSpacePriv.h (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1 /*
2  * Copyright 2016 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 #ifndef SkColorSpacePriv_DEFINED
8 #define SkColorSpacePriv_DEFINED
9 
10 #include "include/core/SkColorSpace.h"
11 #include "include/private/base/SkTemplates.h"
12 #include "modules/skcms/skcms.h"
13 
14 // A gamut narrower than sRGB, useful for testing.
15 static constexpr skcms_Matrix3x3 gNarrow_toXYZD50 = {{
16     { 0.190974f,  0.404865f,  0.368380f },
17     { 0.114746f,  0.582937f,  0.302318f },
18     { 0.032925f,  0.153615f,  0.638669f },
19 }};
20 
color_space_almost_equal(float a,float b)21 static inline bool color_space_almost_equal(float a, float b) {
22     return SkTAbs(a - b) < 0.01f;
23 }
24 
25 // Let's use a stricter version for transfer functions.  Worst case, these are encoded
26 // in ICC format, which offers 16-bits of fractional precision.
transfer_fn_almost_equal(float a,float b)27 static inline bool transfer_fn_almost_equal(float a, float b) {
28     return SkTAbs(a - b) < 0.001f;
29 }
30 
is_almost_srgb(const skcms_TransferFunction & coeffs)31 static inline bool is_almost_srgb(const skcms_TransferFunction& coeffs) {
32     return transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.a, coeffs.a) &&
33            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.b, coeffs.b) &&
34            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.c, coeffs.c) &&
35            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.d, coeffs.d) &&
36            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.e, coeffs.e) &&
37            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.f, coeffs.f) &&
38            transfer_fn_almost_equal(SkNamedTransferFn::kSRGB.g, coeffs.g);
39 }
40 
is_almost_2dot2(const skcms_TransferFunction & coeffs)41 static inline bool is_almost_2dot2(const skcms_TransferFunction& coeffs) {
42     return transfer_fn_almost_equal(1.0f, coeffs.a) &&
43            transfer_fn_almost_equal(0.0f, coeffs.b) &&
44            transfer_fn_almost_equal(0.0f, coeffs.e) &&
45            transfer_fn_almost_equal(2.2f, coeffs.g) &&
46            coeffs.d <= 0.0f;
47 }
48 
is_almost_linear(const skcms_TransferFunction & coeffs)49 static inline bool is_almost_linear(const skcms_TransferFunction& coeffs) {
50     // OutputVal = InputVal ^ 1.0f
51     const bool linearExp =
52             transfer_fn_almost_equal(1.0f, coeffs.a) &&
53             transfer_fn_almost_equal(0.0f, coeffs.b) &&
54             transfer_fn_almost_equal(0.0f, coeffs.e) &&
55             transfer_fn_almost_equal(1.0f, coeffs.g) &&
56             coeffs.d <= 0.0f;
57 
58     // OutputVal = 1.0f * InputVal
59     const bool linearFn =
60             transfer_fn_almost_equal(1.0f, coeffs.c) &&
61             transfer_fn_almost_equal(0.0f, coeffs.f) &&
62             coeffs.d >= 1.0f;
63 
64     return linearExp || linearFn;
65 }
66 
67 // Return raw pointers to commonly used SkColorSpaces.
68 // No need to ref/unref these, but if you do, do it in pairs.
69 SkColorSpace* sk_srgb_singleton();
70 SkColorSpace* sk_srgb_linear_singleton();
71 
72 #endif  // SkColorSpacePriv_DEFINED
73