2 * Copyright 2013 Google Inc.
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
8 #include "SkLumaColorFilter.h"
10 #include "SkColorPriv.h"
14 #include "GrContext.h"
15 #include "GrInvariantOutput.h"
16 #include "glsl/GrGLSLFragmentProcessor.h"
17 #include "glsl/GrGLSLFragmentShaderBuilder.h"
18 #include "glsl/GrGLSLProgramBuilder.h"
21 void SkLumaColorFilter::filterSpan(const SkPMColor src[], int count,
22 SkPMColor dst[]) const {
23 for (int i = 0; i < count; ++i) {
27 * While LuminanceToAlpha is defined to operate on un-premultiplied
28 * inputs, due to the final alpha scaling it can be computed based on
29 * premultipled components:
31 * LumA = (k1 * r / a + k2 * g / a + k3 * b / a) * a
32 * LumA = (k1 * r + k2 * g + k3 * b)
34 unsigned luma = SkComputeLuminance(SkGetPackedR32(c),
37 dst[i] = SkPackARGB32(luma, 0, 0, 0);
41 SkColorFilter* SkLumaColorFilter::Create() { return new SkLumaColorFilter; }
43 SkLumaColorFilter::SkLumaColorFilter() : INHERITED() {}
45 SkFlattenable* SkLumaColorFilter::CreateProc(SkReadBuffer&) { return new SkLumaColorFilter; }
47 void SkLumaColorFilter::flatten(SkWriteBuffer&) const {}
49 #ifndef SK_IGNORE_TO_STRING
50 void SkLumaColorFilter::toString(SkString* str) const {
51 str->append("SkLumaColorFilter ");
56 class LumaColorFilterEffect : public GrFragmentProcessor {
58 static const GrFragmentProcessor* Create() {
59 return new LumaColorFilterEffect;
62 const char* name() const override { return "Luminance-to-Alpha"; }
64 class GLSLProcessor : public GrGLSLFragmentProcessor {
66 GLSLProcessor(const GrProcessor&) {}
68 static void GenKey(const GrProcessor&, const GrGLSLCaps&, GrProcessorKeyBuilder* b) {}
70 virtual void emitCode(EmitArgs& args) override {
71 if (nullptr == args.fInputColor) {
72 args.fInputColor = "vec4(1)";
75 GrGLSLFragmentBuilder* fragBuilder = args.fFragBuilder;
76 fragBuilder->codeAppendf("\tfloat luma = dot(vec3(%f, %f, %f), %s.rgb);\n",
77 SK_ITU_BT709_LUM_COEFF_R,
78 SK_ITU_BT709_LUM_COEFF_G,
79 SK_ITU_BT709_LUM_COEFF_B,
81 fragBuilder->codeAppendf("\t%s = vec4(0, 0, 0, luma);\n",
87 typedef GrGLSLFragmentProcessor INHERITED;
91 LumaColorFilterEffect() {
92 this->initClassID<LumaColorFilterEffect>();
95 GrGLSLFragmentProcessor* onCreateGLSLInstance() const override {
96 return new GLSLProcessor(*this);
99 virtual void onGetGLSLProcessorKey(const GrGLSLCaps& caps,
100 GrProcessorKeyBuilder* b) const override {
101 GLSLProcessor::GenKey(*this, caps, b);
104 bool onIsEqual(const GrFragmentProcessor&) const override { return true; }
106 void onComputeInvariantOutput(GrInvariantOutput* inout) const override {
107 // The output is always black. The alpha value for the color passed in is arbitrary.
108 inout->setToOther(kRGB_GrColorComponentFlags, GrColorPackRGBA(0, 0, 0, 0),
109 GrInvariantOutput::kWill_ReadInput);
113 const GrFragmentProcessor* SkLumaColorFilter::asFragmentProcessor(GrContext*) const {
115 return LumaColorFilterEffect::Create();