Push much of the SkColorSpace_Base interface up to SkColorSpace
Some pieces still remain, but the next step looks less mechanical, so I wanted to land this piece independently. Bug: skia: Change-Id: Ie63afcfa08af2f6e4996911fa2225c43441dbfb2 Reviewed-on: https://skia-review.googlesource.com/84120 Reviewed-by: Mike Klein <mtklein@chromium.org> Commit-Queue: Brian Osman <brianosman@google.com>
This commit is contained in:
parent
09757b29fe
commit
36703d9d36
@ -83,8 +83,7 @@ void ColorCodecBench::onDelayedSetup() {
|
||||
|
||||
if (FLAGS_half) {
|
||||
fDstInfo = fDstInfo.makeColorType(kRGBA_F16_SkColorType);
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(fDstSpace)->type());
|
||||
fDstSpace = static_cast<SkColorSpace_XYZ*>(fDstSpace.get())->makeLinearGamma();
|
||||
fDstSpace = fDstSpace->makeLinearGamma();
|
||||
}
|
||||
|
||||
fDst.reset(fDstInfo.computeMinByteSize());
|
||||
|
@ -919,7 +919,7 @@ static sk_sp<SkColorSpace> adobe_rgb() {
|
||||
}
|
||||
|
||||
static sk_sp<SkColorSpace> rgb_to_gbr() {
|
||||
return as_CSB(SkColorSpace::MakeSRGB())->makeColorSpin();
|
||||
return SkColorSpace::MakeSRGB()->makeColorSpin();
|
||||
}
|
||||
|
||||
static Sink* create_via(const SkString& tag, Sink* wrapped) {
|
||||
|
@ -385,8 +385,7 @@ static bool get_decode_info(SkImageInfo* decodeInfo, SkColorType canvasColorType
|
||||
}
|
||||
|
||||
if (kRGBA_F16_SkColorType == canvasColorType) {
|
||||
sk_sp<SkColorSpace> linearSpace =
|
||||
as_CSB(decodeInfo->colorSpace())->makeLinearGamma();
|
||||
sk_sp<SkColorSpace> linearSpace = decodeInfo->colorSpace()->makeLinearGamma();
|
||||
*decodeInfo = decodeInfo->makeColorSpace(std::move(linearSpace));
|
||||
}
|
||||
|
||||
@ -1083,9 +1082,7 @@ Error ColorCodecSrc::draw(SkCanvas* canvas) const {
|
||||
decodeInfo = decodeInfo.makeAlphaType(kPremul_SkAlphaType);
|
||||
}
|
||||
if (kRGBA_F16_SkColorType == fColorType) {
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(decodeInfo.colorSpace())->type());
|
||||
SkColorSpace_XYZ* csXYZ = static_cast<SkColorSpace_XYZ*>(decodeInfo.colorSpace());
|
||||
decodeInfo = decodeInfo.makeColorSpace(csXYZ->makeLinearGamma());
|
||||
decodeInfo = decodeInfo.makeColorSpace(decodeInfo.colorSpace()->makeLinearGamma());
|
||||
}
|
||||
|
||||
SkImageInfo bitmapInfo = decodeInfo;
|
||||
|
@ -96,7 +96,7 @@ DEF_SIMPLE_GM(color4shader, canvas, 360, 480) {
|
||||
canvas->translate(10, 10);
|
||||
|
||||
auto srgb = SkColorSpace::MakeSRGB();
|
||||
auto spin = as_CSB(srgb)->makeColorSpin(); // RGB -> GBR
|
||||
auto spin = srgb->makeColorSpin(); // RGB -> GBR
|
||||
|
||||
const SkColor4f colors[] {
|
||||
{ 1, 0, 0, 1 },
|
||||
|
@ -48,7 +48,7 @@ protected:
|
||||
kOpaque_SkAlphaType);
|
||||
|
||||
// Test F32 input.
|
||||
srcSpace = as_CSB(srcSpace)->makeLinearGamma();
|
||||
srcSpace = srcSpace->makeLinearGamma();
|
||||
xform = SkColorSpaceXform::New(srcSpace.get(), dstSpace.get());
|
||||
xform->apply(SkColorSpaceXform::kRGBA_F32_ColorFormat, fWideGamutColors1,
|
||||
SkColorSpaceXform::kRGBA_F32_ColorFormat, fSRGBColors, kNumColors,
|
||||
|
@ -31,7 +31,7 @@ sk_sp<SkColorSpace> fix_for_colortype(sk_sp<SkColorSpace> colorSpace, SkColorTyp
|
||||
return SkColorSpace::MakeSRGBLinear();
|
||||
}
|
||||
|
||||
return as_CSB(colorSpace)->makeLinearGamma();
|
||||
return colorSpace->makeLinearGamma();
|
||||
}
|
||||
|
||||
return colorSpace;
|
||||
|
@ -57,7 +57,7 @@ protected:
|
||||
|
||||
sk_sp<SkColorSpace> wideGamut = SkColorSpace::MakeRGB(SkColorSpace::kSRGB_RenderTargetGamma,
|
||||
SkColorSpace::kAdobeRGB_Gamut);
|
||||
sk_sp<SkColorSpace> wideGamutLinear = as_CSB(wideGamut)->makeLinearGamma();
|
||||
sk_sp<SkColorSpace> wideGamutLinear = wideGamut->makeLinearGamma();
|
||||
|
||||
// Lazy images
|
||||
sk_sp<SkImage> opaqueImage = GetResourceAsImage("images/mandrill_128.png");
|
||||
|
@ -41,7 +41,7 @@ static void clamp_if_necessary(const SkImageInfo& info, void* pixels) {
|
||||
|
||||
sk_sp<SkColorSpace> fix_for_colortype(SkColorSpace* colorSpace, SkColorType colorType) {
|
||||
if (kRGBA_F16_SkColorType == colorType) {
|
||||
return as_CSB(colorSpace)->makeLinearGamma();
|
||||
return colorSpace->makeLinearGamma();
|
||||
}
|
||||
|
||||
return sk_ref_sp(colorSpace);
|
||||
|
@ -13,6 +13,13 @@
|
||||
|
||||
class SkData;
|
||||
|
||||
enum SkGammaNamed {
|
||||
kLinear_SkGammaNamed,
|
||||
kSRGB_SkGammaNamed,
|
||||
k2Dot2Curve_SkGammaNamed,
|
||||
kNonStandard_SkGammaNamed,
|
||||
};
|
||||
|
||||
/**
|
||||
* Describes a color gamut with primaries and a white point.
|
||||
*/
|
||||
@ -128,6 +135,8 @@ public:
|
||||
};
|
||||
Type type() const;
|
||||
|
||||
SkGammaNamed gammaNamed() const;
|
||||
|
||||
/**
|
||||
* Returns true if the color space gamma is near enough to be approximated as sRGB.
|
||||
* This includes the canonical sRGB transfer function as well as a 2.2f exponential
|
||||
@ -154,6 +163,49 @@ public:
|
||||
*/
|
||||
bool toXYZD50(SkMatrix44* toXYZD50) const;
|
||||
|
||||
/**
|
||||
* Describes color space gamut as a transformation to XYZ D50.
|
||||
* Returns nullptr if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
const SkMatrix44* toXYZD50() const;
|
||||
|
||||
/**
|
||||
* Describes color space gamut as a transformation from XYZ D50
|
||||
* Returns nullptr if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
const SkMatrix44* fromXYZD50() const;
|
||||
|
||||
/**
|
||||
* Returns a hash of the gamut transofmration to XYZ D50. Allows for fast equality checking
|
||||
* of gamuts, at the (very small) risk of collision.
|
||||
* Returns 0 if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
uint32_t toXYZD50Hash() const;
|
||||
|
||||
/**
|
||||
* Returns a color space with the same gamut as this one, but with a linear gamma.
|
||||
* For color spaces whose gamut can not be described in terms of XYZ D50, returns
|
||||
* linear sRGB.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeLinearGamma() const = 0;
|
||||
|
||||
/**
|
||||
* Returns a color space with the same gamut as this one, with with the sRGB transfer
|
||||
* function. For color spaces whose gamut can not be described in terms of XYZ D50, returns
|
||||
* sRGB.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeSRGBGamma() const = 0;
|
||||
|
||||
/**
|
||||
* Returns a color space with the same transfer function as this one, but with the primary
|
||||
* colors rotated. For any XYZ space, this produces a new color space that maps RGB to GBR
|
||||
* (when applied to a source), and maps RGB to BRG (when applied to a destination). For other
|
||||
* types of color spaces, returns nullptr.
|
||||
*
|
||||
* This is used for testing, to construct color spaces that have severe and testable behavior.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeColorSpin() const { return nullptr; }
|
||||
|
||||
/**
|
||||
* Returns true if the color space is sRGB.
|
||||
* Returns false otherwise.
|
||||
@ -192,6 +244,16 @@ private:
|
||||
SkColorSpace() = default;
|
||||
friend class SkColorSpace_Base;
|
||||
|
||||
virtual const SkMatrix44* onToXYZD50() const = 0;
|
||||
virtual uint32_t onToXYZD50Hash() const = 0;
|
||||
virtual const SkMatrix44* onFromXYZD50() const = 0;
|
||||
|
||||
virtual SkGammaNamed onGammaNamed() const = 0;
|
||||
virtual bool onGammaCloseToSRGB() const = 0;
|
||||
virtual bool onGammaIsLinear() const = 0;
|
||||
virtual bool onIsNumericalTransferFn(SkColorSpaceTransferFn* coeffs) const = 0;
|
||||
virtual bool onIsCMYK() const { return false; }
|
||||
|
||||
using INHERITED = SkRefCnt;
|
||||
};
|
||||
|
||||
|
@ -47,7 +47,7 @@ static constexpr float kSRGB_D50_GamutArea = 0.084f;
|
||||
static bool is_wide_gamut(const SkColorSpace* colorSpace) {
|
||||
// Determine if the source image has a gamut that is wider than sRGB. If so, we
|
||||
// will use P3 as the output color space to avoid clipping the gamut.
|
||||
const SkMatrix44* toXYZD50 = as_CSB(colorSpace)->toXYZD50();
|
||||
const SkMatrix44* toXYZD50 = colorSpace->toXYZD50();
|
||||
if (toXYZD50) {
|
||||
SkPoint rgb[3];
|
||||
load_gamut(rgb, *toXYZD50);
|
||||
|
@ -558,7 +558,7 @@ static inline bool needs_swizzler_to_convert_from_cmyk(J_COLOR_SPACE jpegColorTy
|
||||
return false;
|
||||
}
|
||||
|
||||
bool hasCMYKColorSpace = as_CSB(srcInfo.colorSpace())->onIsCMYK();
|
||||
bool hasCMYKColorSpace = SkColorSpace::kCMYK_Type == srcInfo.colorSpace()->type();
|
||||
return !hasCMYKColorSpace || !hasColorSpaceXform;
|
||||
}
|
||||
|
||||
|
@ -235,27 +235,31 @@ sk_sp<SkColorSpace> SkColorSpace::MakeSRGBLinear() {
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
SkColorSpace::Type SkColorSpace::type() const {
|
||||
SkMatrix44 m(SkMatrix44::kUninitialized_Constructor);
|
||||
if (this->toXYZD50(&m)) {
|
||||
return m.isScale() ? kGray_Type : kRGB_Type;
|
||||
const SkMatrix44* m = this->toXYZD50();
|
||||
if (m) {
|
||||
return m->isScale() ? kGray_Type : kRGB_Type;
|
||||
}
|
||||
return as_CSB(this)->onIsCMYK() ? kCMYK_Type : kRGB_Type;
|
||||
return this->onIsCMYK() ? kCMYK_Type : kRGB_Type;
|
||||
}
|
||||
|
||||
SkGammaNamed SkColorSpace::gammaNamed() const {
|
||||
return this->onGammaNamed();
|
||||
}
|
||||
|
||||
bool SkColorSpace::gammaCloseToSRGB() const {
|
||||
return as_CSB(this)->onGammaCloseToSRGB();
|
||||
return this->onGammaCloseToSRGB();
|
||||
}
|
||||
|
||||
bool SkColorSpace::gammaIsLinear() const {
|
||||
return as_CSB(this)->onGammaIsLinear();
|
||||
return this->onGammaIsLinear();
|
||||
}
|
||||
|
||||
bool SkColorSpace::isNumericalTransferFn(SkColorSpaceTransferFn* fn) const {
|
||||
return as_CSB(this)->onIsNumericalTransferFn(fn);
|
||||
return this->onIsNumericalTransferFn(fn);
|
||||
}
|
||||
|
||||
bool SkColorSpace::toXYZD50(SkMatrix44* toXYZD50) const {
|
||||
const SkMatrix44* matrix = as_CSB(this)->toXYZD50();
|
||||
const SkMatrix44* matrix = this->onToXYZD50();
|
||||
if (matrix) {
|
||||
*toXYZD50 = *matrix;
|
||||
return true;
|
||||
@ -264,6 +268,18 @@ bool SkColorSpace::toXYZD50(SkMatrix44* toXYZD50) const {
|
||||
return false;
|
||||
}
|
||||
|
||||
const SkMatrix44* SkColorSpace::toXYZD50() const {
|
||||
return this->onToXYZD50();
|
||||
}
|
||||
|
||||
const SkMatrix44* SkColorSpace::fromXYZD50() const {
|
||||
return this->onFromXYZD50();
|
||||
}
|
||||
|
||||
uint32_t SkColorSpace::toXYZD50Hash() const {
|
||||
return this->onToXYZD50Hash();
|
||||
}
|
||||
|
||||
bool SkColorSpace::isSRGB() const {
|
||||
return srgb() == this;
|
||||
}
|
||||
@ -331,7 +347,7 @@ size_t SkColorSpace::writeToMemory(void* memory) const {
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(this)->type());
|
||||
const SkColorSpace_XYZ* thisXYZ = static_cast<const SkColorSpace_XYZ*>(this);
|
||||
// If we have a named profile, only write the enum.
|
||||
const SkGammaNamed gammaNamed = thisXYZ->gammaNamed();
|
||||
const SkGammaNamed gammaNamed = this->gammaNamed();
|
||||
if (this == srgb()) {
|
||||
if (memory) {
|
||||
*((ColorSpaceHeader*) memory) = ColorSpaceHeader::Pack(
|
||||
@ -362,7 +378,7 @@ size_t SkColorSpace::writeToMemory(void* memory) const {
|
||||
ColorSpaceHeader::Pack(k0_Version, 0, gammaNamed,
|
||||
ColorSpaceHeader::kMatrix_Flag);
|
||||
memory = SkTAddOffset<void>(memory, sizeof(ColorSpaceHeader));
|
||||
thisXYZ->toXYZD50()->as3x4RowMajorf((float*) memory);
|
||||
this->toXYZD50()->as3x4RowMajorf((float*) memory);
|
||||
}
|
||||
return sizeof(ColorSpaceHeader) + 12 * sizeof(float);
|
||||
}
|
||||
@ -377,7 +393,7 @@ size_t SkColorSpace::writeToMemory(void* memory) const {
|
||||
|
||||
if (memory) {
|
||||
*((ColorSpaceHeader*) memory) =
|
||||
ColorSpaceHeader::Pack(k0_Version, 0, thisXYZ->fGammaNamed,
|
||||
ColorSpaceHeader::Pack(k0_Version, 0, gammaNamed,
|
||||
ColorSpaceHeader::kTransferFn_Flag);
|
||||
memory = SkTAddOffset<void>(memory, sizeof(ColorSpaceHeader));
|
||||
|
||||
@ -390,7 +406,7 @@ size_t SkColorSpace::writeToMemory(void* memory) const {
|
||||
*(((float*) memory) + 6) = gammas->params(0).fG;
|
||||
memory = SkTAddOffset<void>(memory, 7 * sizeof(float));
|
||||
|
||||
thisXYZ->fToXYZD50.as3x4RowMajorf((float*) memory);
|
||||
this->toXYZD50()->as3x4RowMajorf((float*) memory);
|
||||
}
|
||||
|
||||
return sizeof(ColorSpaceHeader) + 19 * sizeof(float);
|
||||
@ -517,21 +533,17 @@ bool SkColorSpace::Equals(const SkColorSpace* src, const SkColorSpace* dst) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// profiles are mandatory for A2B0 color spaces
|
||||
SkASSERT(as_CSB(src)->type() == SkColorSpace_Base::Type::kXYZ);
|
||||
const SkColorSpace_XYZ* srcXYZ = static_cast<const SkColorSpace_XYZ*>(src);
|
||||
const SkColorSpace_XYZ* dstXYZ = static_cast<const SkColorSpace_XYZ*>(dst);
|
||||
|
||||
if (srcXYZ->gammaNamed() != dstXYZ->gammaNamed()) {
|
||||
// Profiles are mandatory for A2B0 color spaces, so these must be XYZ
|
||||
if (src->gammaNamed() != dst->gammaNamed()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
switch (srcXYZ->gammaNamed()) {
|
||||
switch (src->gammaNamed()) {
|
||||
case kSRGB_SkGammaNamed:
|
||||
case k2Dot2Curve_SkGammaNamed:
|
||||
case kLinear_SkGammaNamed:
|
||||
if (srcXYZ->toXYZD50Hash() == dstXYZ->toXYZD50Hash()) {
|
||||
SkASSERT(*srcXYZ->toXYZD50() == *dstXYZ->toXYZD50() && "Hash collision");
|
||||
if (src->toXYZD50Hash() == dst->toXYZD50Hash()) {
|
||||
SkASSERT(*src->toXYZD50() == *dst->toXYZD50() && "Hash collision");
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -27,7 +27,7 @@
|
||||
// here by the nature of the design.
|
||||
class SkColorSpace_A2B : public SkColorSpace_Base {
|
||||
public:
|
||||
const SkMatrix44* toXYZD50() const override {
|
||||
const SkMatrix44* onToXYZD50() const override {
|
||||
// the matrix specified in A2B0 profiles is not necessarily
|
||||
// a to-XYZ matrix, as to-Lab is supported as well so returning
|
||||
// that could be misleading. Additionally, B-curves are applied
|
||||
@ -36,18 +36,19 @@ public:
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
uint32_t toXYZD50Hash() const override {
|
||||
// See toXYZD50()'s comment.
|
||||
uint32_t onToXYZD50Hash() const override {
|
||||
// See onToXYZD50()'s comment.
|
||||
return 0;
|
||||
}
|
||||
|
||||
const SkMatrix44* fromXYZD50() const override {
|
||||
// See toXYZD50()'s comment. Also, A2B0 profiles are not supported
|
||||
const SkMatrix44* onFromXYZD50() const override {
|
||||
// See onToXYZD50()'s comment. Also, A2B0 profiles are not supported
|
||||
// as destination color spaces, so an inverse matrix is never wanted.
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// There is no single gamma curve in an A2B0 profile
|
||||
SkGammaNamed onGammaNamed() const override { return kNonStandard_SkGammaNamed; }
|
||||
bool onGammaCloseToSRGB() const override { return false; }
|
||||
bool onGammaIsLinear() const override { return false; }
|
||||
bool onIsNumericalTransferFn(SkColorSpaceTransferFn* coeffs) const override { return false; }
|
||||
|
@ -14,13 +14,6 @@
|
||||
#include "SkOnce.h"
|
||||
#include "SkTemplates.h"
|
||||
|
||||
enum SkGammaNamed : uint8_t {
|
||||
kLinear_SkGammaNamed,
|
||||
kSRGB_SkGammaNamed,
|
||||
k2Dot2Curve_SkGammaNamed,
|
||||
kNonStandard_SkGammaNamed,
|
||||
};
|
||||
|
||||
struct SkGammas : SkRefCnt {
|
||||
|
||||
// There are four possible representations for gamma curves. kNone_Type is used
|
||||
@ -139,57 +132,6 @@ struct SkGammas : SkRefCnt {
|
||||
class SkColorSpace_Base : public SkColorSpace {
|
||||
public:
|
||||
|
||||
/**
|
||||
* Describes color space gamut as a transformation to XYZ D50.
|
||||
* Returns nullptr if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
virtual const SkMatrix44* toXYZD50() const = 0;
|
||||
|
||||
/**
|
||||
* Returns a hash of the gamut transofmration to XYZ D50. Allows for fast equality checking
|
||||
* of gamuts, at the (very small) risk of collision.
|
||||
* Returns 0 if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
virtual uint32_t toXYZD50Hash() const = 0;
|
||||
|
||||
/**
|
||||
* Describes color space gamut as a transformation from XYZ D50
|
||||
* Returns nullptr if color gamut cannot be described in terms of XYZ D50.
|
||||
*/
|
||||
virtual const SkMatrix44* fromXYZD50() const = 0;
|
||||
|
||||
virtual bool onGammaCloseToSRGB() const = 0;
|
||||
|
||||
virtual bool onGammaIsLinear() const = 0;
|
||||
|
||||
virtual bool onIsNumericalTransferFn(SkColorSpaceTransferFn* coeffs) const = 0;
|
||||
|
||||
virtual bool onIsCMYK() const { return false; }
|
||||
|
||||
/**
|
||||
* Returns a color space with the same gamut as this one, but with a linear gamma.
|
||||
* For color spaces whose gamut can not be described in terms of XYZ D50, returns
|
||||
* linear sRGB.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeLinearGamma() const = 0;
|
||||
|
||||
/**
|
||||
* Returns a color space with the same gamut as this one, with with the sRGB transfer
|
||||
* function. For color spaces whose gamut can not be described in terms of XYZ D50, returns
|
||||
* sRGB.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeSRGBGamma() const = 0;
|
||||
|
||||
/**
|
||||
* Returns a color space with the same transfer function as this one, but with the primary
|
||||
* colors rotated. For any XYZ space, this produces a new color space that maps RGB to GBR
|
||||
* (when applied to a source), and maps RGB to BRG (when applied to a destination). For other
|
||||
* types of color spaces, returns nullptr.
|
||||
*
|
||||
* This is used for testing, to construct color spaces that have severe and testable behavior.
|
||||
*/
|
||||
virtual sk_sp<SkColorSpace> makeColorSpin() const { return nullptr; }
|
||||
|
||||
enum class Type : uint8_t {
|
||||
kXYZ,
|
||||
kA2B
|
||||
|
@ -37,7 +37,7 @@ SkColorSpace_XYZ::SkColorSpace_XYZ(SkGammaNamed gammaNamed, sk_sp<SkGammas> gamm
|
||||
}
|
||||
}
|
||||
|
||||
const SkMatrix44* SkColorSpace_XYZ::fromXYZD50() const {
|
||||
const SkMatrix44* SkColorSpace_XYZ::onFromXYZD50() const {
|
||||
fFromXYZOnce([this] {
|
||||
if (!fToXYZD50.invert(&fFromXYZD50)) {
|
||||
// If a client gives us a dst gamut with a transform that we can't invert, we will
|
||||
|
@ -14,10 +14,10 @@
|
||||
|
||||
class SkColorSpace_XYZ : public SkColorSpace_Base {
|
||||
public:
|
||||
const SkMatrix44* toXYZD50() const override { return &fToXYZD50; }
|
||||
uint32_t toXYZD50Hash() const override { return fToXYZD50Hash; }
|
||||
const SkMatrix44* onToXYZD50() const override { return &fToXYZD50; }
|
||||
uint32_t onToXYZD50Hash() const override { return fToXYZD50Hash; }
|
||||
|
||||
const SkMatrix44* fromXYZD50() const override;
|
||||
const SkMatrix44* onFromXYZD50() const override;
|
||||
|
||||
bool onGammaCloseToSRGB() const override;
|
||||
|
||||
@ -31,7 +31,7 @@ public:
|
||||
sk_sp<SkColorSpace> makeSRGBGamma() const override;
|
||||
sk_sp<SkColorSpace> makeColorSpin() const override;
|
||||
|
||||
SkGammaNamed gammaNamed() const { return fGammaNamed; }
|
||||
SkGammaNamed onGammaNamed() const override { return fGammaNamed; }
|
||||
|
||||
const SkGammas* gammas() const { return fGammas.get(); }
|
||||
|
||||
|
@ -163,7 +163,7 @@ static SkPM4f* convert_colors(const SkColor src[], int count, SkColorSpace* devi
|
||||
}
|
||||
} else {
|
||||
auto srcCS = SkColorSpace::MakeSRGB();
|
||||
auto dstCS = as_CSB(deviceCS)->makeLinearGamma();
|
||||
auto dstCS = deviceCS->makeLinearGamma();
|
||||
SkColorSpaceXform::Apply(dstCS.get(), SkColorSpaceXform::kRGBA_F32_ColorFormat, dst,
|
||||
srcCS.get(), SkColorSpaceXform::kBGRA_8888_ColorFormat, src,
|
||||
count, SkColorSpaceXform::kPremul_AlphaOp);
|
||||
|
@ -32,17 +32,11 @@ sk_sp<SkICC> SkICC::Make(const void* ptr, size_t len) {
|
||||
}
|
||||
|
||||
bool SkICC::toXYZD50(SkMatrix44* toXYZD50) const {
|
||||
const SkMatrix44* m = as_CSB(fColorSpace)->toXYZD50();
|
||||
if (!m) {
|
||||
return false;
|
||||
}
|
||||
|
||||
*toXYZD50 = *m;
|
||||
return true;
|
||||
return fColorSpace->toXYZD50(toXYZD50);
|
||||
}
|
||||
|
||||
bool SkICC::isNumericalTransferFn(SkColorSpaceTransferFn* coeffs) const {
|
||||
return as_CSB(fColorSpace)->onIsNumericalTransferFn(coeffs);
|
||||
return fColorSpace->isNumericalTransferFn(coeffs);
|
||||
}
|
||||
|
||||
static const int kDefaultTableSize = 512; // Arbitrary
|
||||
|
@ -109,15 +109,15 @@ static inline bool append_gamut_transform_noclamp(SkRasterPipeline* p,
|
||||
return false;
|
||||
}
|
||||
|
||||
const SkMatrix44 *fromSrc = as_CSB(src)-> toXYZD50(),
|
||||
*toDst = as_CSB(dst)->fromXYZD50();
|
||||
const SkMatrix44 *fromSrc = src-> toXYZD50(),
|
||||
*toDst = dst->fromXYZD50();
|
||||
if (!fromSrc || !toDst) {
|
||||
SkDEBUGFAIL("We can't handle non-XYZ color spaces in append_gamut_transform().");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Slightly more sophisticated version of if (src == dst)
|
||||
if (as_CSB(src)->toXYZD50Hash() == as_CSB(dst)->toXYZD50Hash()) {
|
||||
if (src->toXYZD50Hash() == dst->toXYZD50Hash()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -119,20 +119,20 @@ sk_sp<GrColorSpaceXform> GrColorSpaceXform::Make(const SkColorSpace* src,
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
const SkMatrix44* toXYZD50 = as_CSB(src)->toXYZD50();
|
||||
const SkMatrix44* fromXYZD50 = as_CSB(dst)->fromXYZD50();
|
||||
const SkMatrix44* toXYZD50 = src->toXYZD50();
|
||||
const SkMatrix44* fromXYZD50 = dst->fromXYZD50();
|
||||
if (!toXYZD50 || !fromXYZD50) {
|
||||
// Unsupported colour spaces -- cannot specify gamut as a matrix
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Determine if a gamut xform is needed
|
||||
uint32_t srcHash = as_CSB(src)->toXYZD50Hash();
|
||||
uint32_t dstHash = as_CSB(dst)->toXYZD50Hash();
|
||||
uint32_t srcHash = src->toXYZD50Hash();
|
||||
uint32_t dstHash = dst->toXYZD50Hash();
|
||||
if (srcHash != dstHash) {
|
||||
flags |= kApplyGamutXform_Flag;
|
||||
} else {
|
||||
SkASSERT(*toXYZD50 == *as_CSB(dst)->toXYZD50() && "Hash collision");
|
||||
SkASSERT(*toXYZD50 == *dst->toXYZD50() && "Hash collision");
|
||||
}
|
||||
|
||||
if (0 == flags) {
|
||||
|
@ -390,7 +390,7 @@ SkImageInfo SkImage_Lazy::buildCacheInfo(CachedFormat format) const {
|
||||
return fInfo.makeColorSpace(nullptr);
|
||||
case kLinearF16_CachedFormat:
|
||||
return fInfo.makeColorType(kRGBA_F16_SkColorType)
|
||||
.makeColorSpace(as_CSB(fInfo.colorSpace())->makeLinearGamma());
|
||||
.makeColorSpace(fInfo.colorSpace()->makeLinearGamma());
|
||||
case kSRGB8888_CachedFormat:
|
||||
// If the transfer function is nearly (but not exactly) sRGB, we don't want the codec
|
||||
// to bother trans-coding. It would be slow, and do more harm than good visually,
|
||||
@ -399,7 +399,7 @@ SkImageInfo SkImage_Lazy::buildCacheInfo(CachedFormat format) const {
|
||||
return fInfo.makeColorType(kRGBA_8888_SkColorType);
|
||||
} else {
|
||||
return fInfo.makeColorType(kRGBA_8888_SkColorType)
|
||||
.makeColorSpace(as_CSB(fInfo.colorSpace())->makeSRGBGamma());
|
||||
.makeColorSpace(fInfo.colorSpace()->makeSRGBGamma());
|
||||
}
|
||||
case kSBGR8888_CachedFormat:
|
||||
// See note above about not-quite-sRGB transfer functions.
|
||||
@ -407,7 +407,7 @@ SkImageInfo SkImage_Lazy::buildCacheInfo(CachedFormat format) const {
|
||||
return fInfo.makeColorType(kBGRA_8888_SkColorType);
|
||||
} else {
|
||||
return fInfo.makeColorType(kBGRA_8888_SkColorType)
|
||||
.makeColorSpace(as_CSB(fInfo.colorSpace())->makeSRGBGamma());
|
||||
.makeColorSpace(fInfo.colorSpace()->makeSRGBGamma());
|
||||
}
|
||||
default:
|
||||
SkDEBUGFAIL("Invalid cached format");
|
||||
|
@ -361,7 +361,7 @@ static inline sk_sp<SkData> icc_from_color_space(const SkImageInfo& info) {
|
||||
|
||||
sk_sp<SkColorSpace> owned;
|
||||
if (kRGBA_F16_SkColorType == info.colorType()) {
|
||||
owned = as_CSB(cs)->makeSRGBGamma();
|
||||
owned = cs->makeSRGBGamma();
|
||||
cs = owned.get();
|
||||
}
|
||||
|
||||
|
@ -1385,8 +1385,7 @@ GrGradientEffect::RandomGradientParams::RandomGradientParams(SkRandom* random) {
|
||||
if (fUseColors4f) {
|
||||
fColorSpace = GrTest::TestColorSpace(random);
|
||||
if (fColorSpace) {
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(fColorSpace)->type());
|
||||
fColorSpace = static_cast<SkColorSpace_XYZ*>(fColorSpace.get())->makeLinearGamma();
|
||||
fColorSpace = fColorSpace->makeLinearGamma();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -253,7 +253,7 @@ static void skcolor_to_linear(SkRGBAf dst[], const SkColor src[], int count, SkC
|
||||
bool doPremul) {
|
||||
if (cs) {
|
||||
auto srcCS = SkColorSpace::MakeSRGB();
|
||||
auto dstCS = as_CSB(cs)->makeLinearGamma();
|
||||
auto dstCS = cs->makeLinearGamma();
|
||||
auto op = doPremul ? SkColorSpaceXform::kPremul_AlphaOp
|
||||
: SkColorSpaceXform::kPreserve_AlphaOp;
|
||||
SkColorSpaceXform::Apply(dstCS.get(), SkColorSpaceXform::kRGBA_F32_ColorFormat, dst,
|
||||
@ -271,7 +271,7 @@ static void skcolor_to_linear(SkRGBAf dst[], const SkColor src[], int count, SkC
|
||||
|
||||
static void linear_to_skcolor(SkColor dst[], const SkRGBAf src[], int count, SkColorSpace* cs) {
|
||||
if (cs) {
|
||||
auto srcCS = as_CSB(cs)->makeLinearGamma();
|
||||
auto srcCS = cs->makeLinearGamma();
|
||||
auto dstCS = SkColorSpace::MakeSRGB();
|
||||
SkColorSpaceXform::Apply(dstCS.get(), SkColorSpaceXform::kBGRA_8888_ColorFormat, dst,
|
||||
srcCS.get(), SkColorSpaceXform::kRGBA_F32_ColorFormat, src,
|
||||
|
@ -1143,9 +1143,7 @@ static void test_conversion_possible(skiatest::Reporter* r, const char* path,
|
||||
|| SkCodec::kInvalidConversion == result);
|
||||
}
|
||||
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(infoF16.colorSpace())->type());
|
||||
SkColorSpace_XYZ* csXYZ = static_cast<SkColorSpace_XYZ*>(infoF16.colorSpace());
|
||||
infoF16 = infoF16.makeColorSpace(csXYZ->makeLinearGamma());
|
||||
infoF16 = infoF16.makeColorSpace(infoF16.colorSpace()->makeLinearGamma());
|
||||
result = codec->getPixels(infoF16, bm.getPixels(), bm.rowBytes());
|
||||
REPORTER_ASSERT(r, SkCodec::kSuccess == result);
|
||||
result = codec->startScanlineDecode(infoF16);
|
||||
|
@ -24,11 +24,9 @@ static void test_space(skiatest::Reporter* r, SkColorSpace* space,
|
||||
const SkGammaNamed expectedGamma) {
|
||||
|
||||
REPORTER_ASSERT(r, nullptr != space);
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(space)->type());
|
||||
SkColorSpace_XYZ* csXYZ = static_cast<SkColorSpace_XYZ*>(space);
|
||||
REPORTER_ASSERT(r, expectedGamma == csXYZ->gammaNamed());
|
||||
REPORTER_ASSERT(r, expectedGamma == space->gammaNamed());
|
||||
|
||||
const SkMatrix44& mat = *csXYZ->toXYZD50();
|
||||
const SkMatrix44& mat = *space->toXYZD50();
|
||||
const float src[] = {
|
||||
1, 0, 0, 1,
|
||||
0, 1, 0, 1,
|
||||
@ -211,9 +209,7 @@ DEF_TEST(ColorSpace_Named, r) {
|
||||
auto cs = SkColorSpace_Base::MakeNamed(rec.fNamed);
|
||||
REPORTER_ASSERT(r, cs);
|
||||
if (cs) {
|
||||
SkASSERT(SkColorSpace_Base::Type::kXYZ == as_CSB(cs)->type());
|
||||
SkColorSpace_XYZ* csXYZ = static_cast<SkColorSpace_XYZ*>(cs.get());
|
||||
REPORTER_ASSERT(r, rec.fExpectedGamma == csXYZ->gammaNamed());
|
||||
REPORTER_ASSERT(r, rec.fExpectedGamma == cs->gammaNamed());
|
||||
}
|
||||
}
|
||||
|
||||
@ -477,8 +473,8 @@ DEF_TEST(ColorSpace_MatrixHash, r) {
|
||||
srgbMat.set3x3RowMajorf(gSRGB_toXYZD50);
|
||||
sk_sp<SkColorSpace> strange = SkColorSpace::MakeRGB(fn, srgbMat);
|
||||
|
||||
REPORTER_ASSERT(r, *as_CSB(srgb)->toXYZD50() == *as_CSB(strange)->toXYZD50());
|
||||
REPORTER_ASSERT(r, as_CSB(srgb)->toXYZD50Hash() == as_CSB(strange)->toXYZD50Hash());
|
||||
REPORTER_ASSERT(r, *srgb->toXYZD50() == *strange->toXYZD50());
|
||||
REPORTER_ASSERT(r, srgb->toXYZD50Hash() == strange->toXYZD50Hash());
|
||||
}
|
||||
|
||||
DEF_TEST(ColorSpace_IsSRGB, r) {
|
||||
|
@ -595,11 +595,11 @@ DEF_TEST(ReadPixels_ValidConversion, reporter) {
|
||||
for (SkAlphaType srcAT: kAlphaTypes) {
|
||||
for (sk_sp<SkColorSpace> srcCS : kColorSpaces) {
|
||||
if (kRGBA_F16_SkColorType == dstCT && dstCS) {
|
||||
dstCS = as_CSB(dstCS)->makeLinearGamma();
|
||||
dstCS = dstCS->makeLinearGamma();
|
||||
}
|
||||
|
||||
if (kRGBA_F16_SkColorType == srcCT && srcCS) {
|
||||
srcCS = as_CSB(srcCS)->makeLinearGamma();
|
||||
srcCS = srcCS->makeLinearGamma();
|
||||
}
|
||||
|
||||
test_conversion(reporter,
|
||||
|
@ -812,7 +812,7 @@ static void test_surface_creation_and_snapshot_with_color_space(
|
||||
|
||||
auto srgbColorSpace = SkColorSpace::MakeSRGB();
|
||||
auto adobeColorSpace = SkColorSpace_Base::MakeNamed(SkColorSpace_Base::kAdobeRGB_Named);
|
||||
const SkMatrix44* srgbMatrix = as_CSB(srgbColorSpace)->toXYZD50();
|
||||
const SkMatrix44* srgbMatrix = srgbColorSpace->toXYZD50();
|
||||
SkASSERT(srgbMatrix);
|
||||
SkColorSpaceTransferFn oddGamma;
|
||||
oddGamma.fA = 1.0f;
|
||||
|
@ -158,10 +158,9 @@ DEF_TEST(ParseConfigs_DefaultConfigs, reporter) {
|
||||
REPORTER_ASSERT(reporter, configs[24]->asConfigGpu()->getColorType() == kRGBA_F16_SkColorType);
|
||||
REPORTER_ASSERT(reporter, configs[24]->asConfigGpu()->getColorSpace());
|
||||
REPORTER_ASSERT(reporter, configs[24]->asConfigGpu()->getColorSpace()->gammaIsLinear());
|
||||
const SkMatrix44* srgbXYZ = as_CSB(srgbColorSpace)->toXYZD50();
|
||||
const SkMatrix44* srgbXYZ = srgbColorSpace->toXYZD50();
|
||||
SkASSERT(srgbXYZ);
|
||||
const SkMatrix44* config25XYZ =
|
||||
as_CSB(configs[24]->asConfigGpu()->getColorSpace())->toXYZD50();
|
||||
const SkMatrix44* config25XYZ = configs[24]->asConfigGpu()->getColorSpace()->toXYZD50();
|
||||
SkASSERT(config25XYZ);
|
||||
REPORTER_ASSERT(reporter, *config25XYZ == *srgbXYZ);
|
||||
REPORTER_ASSERT(reporter, configs[25]->asConfigGpu()->getColorType() == kRGBA_8888_SkColorType);
|
||||
@ -169,15 +168,14 @@ DEF_TEST(ParseConfigs_DefaultConfigs, reporter) {
|
||||
REPORTER_ASSERT(reporter, configs[32]->asConfigGpu()->getColorType() == kRGBA_F16_SkColorType);
|
||||
REPORTER_ASSERT(reporter, configs[32]->asConfigGpu()->getColorSpace());
|
||||
REPORTER_ASSERT(reporter, configs[32]->asConfigGpu()->getColorSpace()->gammaIsLinear());
|
||||
const SkMatrix44* config41XYZ =
|
||||
as_CSB(configs[32]->asConfigGpu()->getColorSpace())->toXYZD50();
|
||||
const SkMatrix44* config41XYZ = configs[32]->asConfigGpu()->getColorSpace()->toXYZD50();
|
||||
SkASSERT(config41XYZ);
|
||||
REPORTER_ASSERT(reporter, *config41XYZ != *srgbXYZ);
|
||||
REPORTER_ASSERT(reporter, configs[33]->asConfigGpu()->getColorType() == kRGBA_F16_SkColorType);
|
||||
REPORTER_ASSERT(reporter, configs[33]->asConfigGpu()->getColorSpace());
|
||||
REPORTER_ASSERT(reporter, configs[33]->asConfigGpu()->getColorSpace()->gammaIsLinear());
|
||||
REPORTER_ASSERT(reporter, *as_CSB(configs[33]->asConfigGpu()->getColorSpace())->toXYZD50() !=
|
||||
*as_CSB(srgbColorSpace)->toXYZD50());
|
||||
REPORTER_ASSERT(reporter, *configs[33]->asConfigGpu()->getColorSpace()->toXYZD50() !=
|
||||
*srgbColorSpace->toXYZD50());
|
||||
REPORTER_ASSERT(reporter, configs[34]->asConfigGpu()->getContextType() ==
|
||||
GrContextFactory::kGL_ContextType);
|
||||
REPORTER_ASSERT(reporter, SkToBool(configs[34]->asConfigGpu()->getContextOverrides() &
|
||||
|
@ -531,7 +531,7 @@ int main(int argc, char** argv) {
|
||||
// Draw the sRGB gamut if requested.
|
||||
if (FLAGS_sRGB_gamut) {
|
||||
sk_sp<SkColorSpace> sRGBSpace = SkColorSpace::MakeSRGB();
|
||||
const SkMatrix44* mat = as_CSB(sRGBSpace)->toXYZD50();
|
||||
const SkMatrix44* mat = sRGBSpace->toXYZD50();
|
||||
SkASSERT(mat);
|
||||
draw_gamut(gamutCanvas.canvas(), *mat, "sRGB", 0xFFFF9394, false);
|
||||
}
|
||||
@ -540,11 +540,11 @@ int main(int argc, char** argv) {
|
||||
if (FLAGS_adobeRGB) {
|
||||
sk_sp<SkColorSpace> adobeRGBSpace = SkColorSpace::MakeRGB(
|
||||
SkColorSpace::kSRGB_RenderTargetGamma, SkColorSpace::kAdobeRGB_Gamut);
|
||||
const SkMatrix44* mat = as_CSB(adobeRGBSpace)->toXYZD50();
|
||||
const SkMatrix44* mat = adobeRGBSpace->toXYZD50();
|
||||
SkASSERT(mat);
|
||||
draw_gamut(gamutCanvas.canvas(), *mat, "Adobe RGB", 0xFF31a9e1, false);
|
||||
}
|
||||
const SkMatrix44* mat = as_CSB(colorSpace)->toXYZD50();
|
||||
const SkMatrix44* mat = colorSpace->toXYZD50();
|
||||
SkASSERT(mat);
|
||||
auto xyz = static_cast<SkColorSpace_XYZ*>(colorSpace.get());
|
||||
draw_gamut(gamutCanvas.canvas(), *mat, input, 0xFF000000, true);
|
||||
@ -556,7 +556,7 @@ int main(int argc, char** argv) {
|
||||
if (FLAGS_sRGB_gamma) {
|
||||
draw_transfer_fn(gammaCanvas.canvas(), kSRGB_SkGammaNamed, nullptr, 0xFFFF9394);
|
||||
}
|
||||
draw_transfer_fn(gammaCanvas.canvas(), xyz->gammaNamed(), xyz->gammas(), 0xFF000000);
|
||||
draw_transfer_fn(gammaCanvas.canvas(), colorSpace->gammaNamed(), xyz->gammas(), 0xFF000000);
|
||||
if (!gammaCanvas.save(&outputFilenames, createOutputFilename("gamma", 0))) {
|
||||
return -1;
|
||||
}
|
||||
|
@ -15,7 +15,7 @@
|
||||
* Create a color space that swaps the red, green, and blue channels.
|
||||
*/
|
||||
static sk_sp<SkColorSpace> gbr_color_space() {
|
||||
return as_CSB(SkColorSpace::MakeSRGB())->makeColorSpin();
|
||||
return SkColorSpace::MakeSRGB()->makeColorSpin();
|
||||
}
|
||||
|
||||
/**
|
||||
|
Loading…
Reference in New Issue
Block a user