| // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef UI_GFX_COLOR_SPACE_H_ |
| #define UI_GFX_COLOR_SPACE_H_ |
| |
| #include <stdint.h> |
| #include <ostream> |
| #include <vector> |
| |
| #include "base/gtest_prod_util.h" |
| #include "base/macros.h" |
| #include "build/build_config.h" |
| #include "third_party/skia/include/core/SkColorSpace.h" |
| #include "third_party/skia/include/core/SkImageInfo.h" |
| #include "ui/gfx/color_space_export.h" |
| |
| namespace IPC { |
| template <class P> |
| struct ParamTraits; |
| } // namespace IPC |
| |
| namespace gfx { |
| |
| class ICCProfile; |
| |
| // Used to represet a color space for the purpose of color conversion. |
| // This is designed to be safe and compact enough to send over IPC |
| // between any processes. |
| class COLOR_SPACE_EXPORT ColorSpace { |
| public: |
| enum class PrimaryID : uint8_t { |
| INVALID, |
| BT709, |
| BT470M, |
| BT470BG, |
| SMPTE170M, |
| SMPTE240M, |
| FILM, |
| BT2020, |
| SMPTEST428_1, |
| SMPTEST431_2, |
| SMPTEST432_1, |
| XYZ_D50, |
| ADOBE_RGB, |
| // Corresponds the the primaries of the "Generic RGB" profile used in the |
| // Apple ColorSync application, used by layout tests on Mac. |
| APPLE_GENERIC_RGB, |
| // A very wide gamut space with rotated primaries. Used by layout tests. |
| WIDE_GAMUT_COLOR_SPIN, |
| // Primaries defined by the primary matrix |custom_primary_matrix_|. |
| CUSTOM, |
| LAST = CUSTOM, |
| }; |
| |
| enum class TransferID : uint8_t { |
| INVALID, |
| BT709, |
| GAMMA18, |
| GAMMA22, |
| GAMMA24, |
| GAMMA28, |
| SMPTE170M, |
| SMPTE240M, |
| LINEAR, |
| LOG, |
| LOG_SQRT, |
| IEC61966_2_4, |
| BT1361_ECG, |
| IEC61966_2_1, |
| BT2020_10, |
| BT2020_12, |
| SMPTEST2084, |
| SMPTEST428_1, |
| ARIB_STD_B67, // AKA hybrid-log gamma, HLG. |
| // This is an ad-hoc transfer function that decodes SMPTE 2084 content |
| // into a [0, 1] range more or less suitable for viewing on a non-hdr |
| // display. |
| SMPTEST2084_NON_HDR, |
| // The same as IEC61966_2_1 on the interval [0, 1], with the nonlinear |
| // segment continuing beyond 1 and point symmetry defining values below 0. |
| IEC61966_2_1_HDR, |
| // The same as LINEAR but is defined for all real values. |
| LINEAR_HDR, |
| // A parametric transfer function defined by |custom_transfer_params_|. |
| CUSTOM, |
| LAST = CUSTOM, |
| }; |
| |
| enum class MatrixID : uint8_t { |
| INVALID, |
| RGB, |
| BT709, |
| FCC, |
| BT470BG, |
| SMPTE170M, |
| SMPTE240M, |
| YCOCG, |
| BT2020_NCL, |
| BT2020_CL, |
| YDZDX, |
| LAST = YDZDX, |
| }; |
| |
| enum class RangeID : uint8_t { |
| INVALID, |
| // Limited Rec. 709 color range with RGB values ranging from 16 to 235. |
| LIMITED, |
| // Full RGB color range with RGB valees from 0 to 255. |
| FULL, |
| // Range is defined by TransferID/MatrixID. |
| DERIVED, |
| LAST = DERIVED, |
| }; |
| |
| ColorSpace(); |
| ColorSpace(PrimaryID primaries, TransferID transfer); |
| ColorSpace(PrimaryID primaries, |
| TransferID transfer, |
| MatrixID matrix, |
| RangeID full_range); |
| ColorSpace(PrimaryID primaries, |
| const SkColorSpaceTransferFn& fn, |
| MatrixID matrix, |
| RangeID full_range); |
| ColorSpace(const ColorSpace& other); |
| ColorSpace(ColorSpace&& other); |
| ColorSpace& operator=(const ColorSpace& other); |
| ~ColorSpace(); |
| |
| // Returns true if this is not the default-constructor object. |
| bool IsValid() const; |
| |
| static ColorSpace CreateSRGB(); |
| static ColorSpace CreateDisplayP3D65(); |
| static ColorSpace CreateCustom(const SkMatrix44& to_XYZD50, |
| TransferID transfer_id); |
| static ColorSpace CreateCustom(const SkMatrix44& to_XYZD50, |
| const SkColorSpaceTransferFn& fn); |
| static ColorSpace CreateXYZD50(); |
| |
| // Extended sRGB matches sRGB for values in [0, 1], and extends the transfer |
| // function to all real values. |
| static ColorSpace CreateExtendedSRGB(); |
| |
| // scRGB uses the same primaries as sRGB but has a linear transfer function |
| // for all real values. |
| static ColorSpace CreateSCRGBLinear(); |
| |
| // TODO: Remove these, and replace with more generic constructors. |
| static ColorSpace CreateJpeg(); |
| static ColorSpace CreateREC601(); |
| static ColorSpace CreateREC709(); |
| |
| // Generates a process global unique ID that can be used to key a color space. |
| static int GetNextId(); |
| |
| bool operator==(const ColorSpace& other) const; |
| bool operator!=(const ColorSpace& other) const; |
| bool operator<(const ColorSpace& other) const; |
| size_t GetHash() const; |
| std::string ToString() const; |
| |
| // Returns true if the decoded values can be outside of the 0.0-1.0 range. |
| bool IsHDR() const; |
| |
| // Returns true if the encoded values can be outside of the 0.0-1.0 range. |
| bool FullRangeEncodedValues() const; |
| |
| // Return a parametric approximation of this color space (if it is not already |
| // parametric). |
| ColorSpace GetParametricApproximation() const; |
| |
| // Return this color space with any range adjust or YUV to RGB conversion |
| // stripped off. |
| ColorSpace GetAsFullRangeRGB() const; |
| |
| // If |this| is the final output color space, return the color space that |
| // would be appropriate for rasterization. |
| ColorSpace GetRasterColorSpace() const; |
| |
| // If |this| is the final output color space, return the color space that |
| // would be appropriate for blending. |
| ColorSpace GetBlendingColorSpace() const; |
| |
| // This will return nullptr for non-RGB spaces, spaces with non-FULL |
| // range, and unspecified spaces. |
| sk_sp<SkColorSpace> ToSkColorSpace() const; |
| |
| // For YUV color spaces, return the closest SkYUVColorSpace. |
| // Returns true if a close match is found. |
| bool ToSkYUVColorSpace(SkYUVColorSpace* out); |
| |
| void GetPrimaryMatrix(SkMatrix44* to_XYZD50) const; |
| bool GetTransferFunction(SkColorSpaceTransferFn* fn) const; |
| bool GetInverseTransferFunction(SkColorSpaceTransferFn* fn) const; |
| |
| // For most formats, this is the RGB to YUV matrix. |
| void GetTransferMatrix(SkMatrix44* matrix) const; |
| void GetRangeAdjustMatrix(SkMatrix44* matrix) const; |
| |
| private: |
| void SetCustomTransferFunction(const SkColorSpaceTransferFn& fn); |
| void SetCustomPrimaries(const SkMatrix44& to_XYZD50); |
| |
| // Returns true if the transfer function is defined by an |
| // SkColorSpaceTransferFn which is extended to all real values. |
| bool HasExtendedSkTransferFn() const; |
| |
| PrimaryID primaries_ = PrimaryID::INVALID; |
| TransferID transfer_ = TransferID::INVALID; |
| MatrixID matrix_ = MatrixID::INVALID; |
| RangeID range_ = RangeID::INVALID; |
| |
| // Only used if primaries_ is PrimaryID::CUSTOM. |
| float custom_primary_matrix_[9] = {0, 0, 0, 0, 0, 0, 0, 0}; |
| |
| // Only used if transfer_ is TransferID::CUSTOM. This array consists of the A |
| // through G entries of the SkColorSpaceTransferFn structure in alphabetical |
| // order. |
| float custom_transfer_params_[7] = {0, 0, 0, 0, 0, 0, 0}; |
| |
| // This is set if and only if this color space is to represent an ICC profile |
| // that cannot be sufficiently accurately represented with a custom primary |
| // matrix and transfer function. It can be used to look up the original |
| // ICCProfile to create a LUT based transform. |
| uint64_t icc_profile_id_ = 0; |
| |
| friend class ICCProfile; |
| friend class ICCProfileCache; |
| friend class ColorTransform; |
| friend class ColorTransformInternal; |
| friend class ColorSpaceWin; |
| friend struct IPC::ParamTraits<ColorSpace>; |
| FRIEND_TEST_ALL_PREFIXES(SimpleColorSpace, GetColorSpace); |
| }; |
| |
| // Stream operator so ColorSpace can be used in assertion statements. |
| COLOR_SPACE_EXPORT std::ostream& operator<<(std::ostream& out, |
| const ColorSpace& color_space); |
| |
| } // namespace gfx |
| |
| #endif // UI_GFX_COLOR_SPACE_H_ |