aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core/SkPM4fPriv.h
diff options
context:
space:
mode:
authorGravatar Mike Klein <mtklein@chromium.org>2016-11-14 16:02:41 -0500
committerGravatar Mike Klein <mtklein@chromium.org>2016-11-14 22:05:47 +0000
commit662c2aed38c1917c05883095a8013f51931aafa4 (patch)
tree406b473cd8f3333aa2087e9bc2769145098fe047 /src/core/SkPM4fPriv.h
parent0fdde549825bcf6931aadbc292a91403ea15bb63 (diff)
Fill in gamut-transformation TODOs for software pipeline.
This adds support for paint colors, color shaders, and mode color filters (everything that the software pipeline supports today). BUG=skia: GOLD_TRYBOT_URL= https://gold.skia.org/search?issue=4781 Change-Id: I6e5da6d0dba03fbc82ecaa233ce8c727e7ce17b3 Reviewed-on: https://skia-review.googlesource.com/4781 Reviewed-by: Brian Osman <brianosman@google.com>
Diffstat (limited to 'src/core/SkPM4fPriv.h')
-rw-r--r--src/core/SkPM4fPriv.h51
1 files changed, 50 insertions, 1 deletions
diff --git a/src/core/SkPM4fPriv.h b/src/core/SkPM4fPriv.h
index f70c5c5a53..304a49ffdd 100644
--- a/src/core/SkPM4fPriv.h
+++ b/src/core/SkPM4fPriv.h
@@ -10,7 +10,10 @@
#include "SkColorPriv.h"
#include "SkColorSpace.h"
+#include "SkColorSpace_Base.h"
+#include "SkFixedAlloc.h"
#include "SkPM4f.h"
+#include "SkRasterPipeline.h"
#include "SkSRGB.h"
static inline Sk4f set_alpha(const Sk4f& px, float alpha) {
@@ -72,12 +75,58 @@ static inline float exact_srgb_to_linear(float srgb) {
return linear;
}
+
+// N.B. scratch_matrix_3x4 must live at least as long as p.
+static inline bool append_gamut_transform(SkRasterPipeline* p, float scratch_matrix_3x4[12],
+ SkColorSpace* src, SkColorSpace* dst) {
+ if (src == dst) { return true; }
+ if (!dst) { return true; } // Legacy modes intentionally ignore color gamut.
+ if (!src) { return true; } // A null src color space means linear gamma, dst gamut.
+
+ auto toXYZ = as_CSB(src)-> toXYZD50(),
+ fromXYZ = as_CSB(dst)->fromXYZD50();
+ if (!toXYZ || !fromXYZ) { return false; } // Unsupported color space type.
+
+ if (as_CSB(src)->toXYZD50Hash() == as_CSB(dst)->toXYZD50Hash()) { return true; }
+
+ SkMatrix44 m44(*fromXYZ, *toXYZ);
+
+ // Convert from 4x4 to (column-major) 3x4.
+ auto ptr = scratch_matrix_3x4;
+ *ptr++ = m44.get(0,0); *ptr++ = m44.get(1,0); *ptr++ = m44.get(2,0);
+ *ptr++ = m44.get(0,1); *ptr++ = m44.get(1,1); *ptr++ = m44.get(2,1);
+ *ptr++ = m44.get(0,2); *ptr++ = m44.get(1,2); *ptr++ = m44.get(2,2);
+ *ptr++ = m44.get(0,3); *ptr++ = m44.get(1,3); *ptr++ = m44.get(2,3);
+
+ p->append(SkRasterPipeline::matrix_3x4, scratch_matrix_3x4);
+ // TODO: detect whether we can skip the clamps?
+ p->append(SkRasterPipeline::clamp_0);
+ p->append(SkRasterPipeline::clamp_a);
+ return true;
+}
+
+static inline bool append_gamut_transform(SkRasterPipeline* p, SkFallbackAlloc* scratch,
+ SkColorSpace* src, SkColorSpace* dst) {
+ struct matrix_3x4 { float arr[12]; };
+ return append_gamut_transform(p, scratch->make<matrix_3x4>()->arr, src, dst);
+}
+
static inline SkPM4f SkPM4f_from_SkColor(SkColor color, SkColorSpace* dst) {
SkColor4f color4f;
if (dst) {
// sRGB gamma, sRGB gamut.
color4f = SkColor4f::FromColor(color);
- // TODO: gamut transform if needed
+ void* color4f_ptr = &color4f;
+
+ float scratch_matrix_3x4[12];
+
+ SkRasterPipeline p;
+ p.append(SkRasterPipeline::constant_color, color4f_ptr);
+ append_gamut_transform(&p, scratch_matrix_3x4,
+ SkColorSpace::MakeNamed(SkColorSpace::kSRGB_Named).get(), dst);
+ p.append(SkRasterPipeline::store_f32, &color4f_ptr);
+
+ p.compile()(0,1);
} else {
// Linear gamma, dst gamut.
swizzle_rb(SkNx_cast<float>(Sk4b::Load(&color)) * (1/255.0f)).store(&color4f);