1f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips/*
2130fb3f7aac19e40eddfc8fa85a9b39e7c99a7e8Ethan Nicholas * Copyright 2018 Google Inc.
3f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips *
4f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips * Use of this source code is governed by a BSD-style license that can be
5f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips * found in the LICENSE file.
6f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips */
7f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips
8130fb3f7aac19e40eddfc8fa85a9b39e7c99a7e8Ethan Nicholas/**************************************************************************************************
9130fb3f7aac19e40eddfc8fa85a9b39e7c99a7e8Ethan Nicholas *** This file was autogenerated from GrAlphaThresholdFragmentProcessor.fp; do not modify.
10130fb3f7aac19e40eddfc8fa85a9b39e7c99a7e8Ethan Nicholas **************************************************************************************************/
11f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips#include "GrAlphaThresholdFragmentProcessor.h"
12ceb4d48ef4839aab9d99d0200dcfe403ccd0cdf3Ethan Nicholas#if SK_SUPPORT_GPU
13f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips
14b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholasinline GrFragmentProcessor::OptimizationFlags GrAlphaThresholdFragmentProcessor::optFlags(
15b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        float outerThreshold) {
16b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas    if (outerThreshold >= 1.0) {
17b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        return kPreservesOpaqueInput_OptimizationFlag |
18b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas               kCompatibleWithCoverageAsAlpha_OptimizationFlag;
19b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas    } else {
20b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        return kCompatibleWithCoverageAsAlpha_OptimizationFlag;
219fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    }
22b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas}
23f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips#include "glsl/GrGLSLFragmentProcessor.h"
24f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips#include "glsl/GrGLSLFragmentShaderBuilder.h"
259fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas#include "glsl/GrGLSLProgramBuilder.h"
262d5f9b3d58e07ac8a8df17f4c0321cb65f255e69Ethan Nicholas#include "GrTexture.h"
279fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas#include "SkSLCPP.h"
289fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas#include "SkSLUtil.h"
299fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholasclass GrGLSLAlphaThresholdFragmentProcessor : public GrGLSLFragmentProcessor {
30f7142e71d7c0a7d8406679e207ff766085499d2erobertphillipspublic:
319fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    GrGLSLAlphaThresholdFragmentProcessor() {}
329fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    void emitCode(EmitArgs& args) override {
339fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas        GrGLSLFPFragmentBuilder* fragBuilder = args.fFragBuilder;
34b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        const GrAlphaThresholdFragmentProcessor& _outer =
35b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fFp.cast<GrAlphaThresholdFragmentProcessor>();
36b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        (void)_outer;
37823994624aa5e805e16833ecd3d748fc769a164dEthan Nicholas        auto innerThreshold = _outer.innerThreshold();
38823994624aa5e805e16833ecd3d748fc769a164dEthan Nicholas        (void)innerThreshold;
39823994624aa5e805e16833ecd3d748fc769a164dEthan Nicholas        auto outerThreshold = _outer.outerThreshold();
40823994624aa5e805e16833ecd3d748fc769a164dEthan Nicholas        (void)outerThreshold;
41b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        fInnerThresholdVar = args.fUniformHandler->addUniform(
42f7b8820dc813d1eb0b6b43fe4581dded0da38cafEthan Nicholas                kFragment_GrShaderFlag, kHalf_GrSLType, kDefault_GrSLPrecision, "innerThreshold");
43b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        fOuterThresholdVar = args.fUniformHandler->addUniform(
44f7b8820dc813d1eb0b6b43fe4581dded0da38cafEthan Nicholas                kFragment_GrShaderFlag, kHalf_GrSLType, kDefault_GrSLPrecision, "outerThreshold");
4572a37bed66c90ff2acb930dc4493dc633f265488Brian Osman        SkString sk_TransformedCoords2D_0 = fragBuilder->ensureCoords2D(args.fTransformedCoords[0]);
46b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        fragBuilder->codeAppendf(
47a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                "half4 color = %s;\nhalf4 mask_color = texture(%s, %s).%s;\nif "
48a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                "(float(mask_color.w) < 0.5) {\n    if (color.w > %s) {\n        half scale = %s / "
49a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                "color.w;\n        color.xyz *= scale;\n        color.w = %s;\n    }\n} else if "
50a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                "(color.w < %s) {\n    half scale = float(%s) / max(0.001, float(color.w));\n    "
51a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                "color.xyz *= scale;\n    color.w = %s;\n}\n%s = color;\n",
52a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                args.fInputColor ? args.fInputColor : "half4(1)",
53b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                fragBuilder->getProgramBuilder()->samplerVariable(args.fTexSamplers[0]).c_str(),
54b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                sk_TransformedCoords2D_0.c_str(),
55b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                fragBuilder->getProgramBuilder()->samplerSwizzle(args.fTexSamplers[0]).c_str(),
56b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fOuterThresholdVar),
57b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fOuterThresholdVar),
58b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fOuterThresholdVar),
59b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fInnerThresholdVar),
60b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fInnerThresholdVar),
61b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                args.fUniformHandler->getUniformCStr(fInnerThresholdVar), args.fOutputColor);
626fb592e6afb0061c9c0af15ddf599e2903f508f1Brian Osman    }
63b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas
64f7142e71d7c0a7d8406679e207ff766085499d2erobertphillipsprivate:
65b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas    void onSetData(const GrGLSLProgramDataManager& pdman,
66b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                   const GrFragmentProcessor& _proc) override {
67b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        const GrAlphaThresholdFragmentProcessor& _outer =
68b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                _proc.cast<GrAlphaThresholdFragmentProcessor>();
699fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas        {
70b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas            pdman.set1f(fInnerThresholdVar, _outer.innerThreshold());
71b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas            pdman.set1f(fOuterThresholdVar, _outer.outerThreshold());
729fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas        }
739fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    }
749fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    UniformHandle fInnerThresholdVar;
759fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    UniformHandle fOuterThresholdVar;
76f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips};
779fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan NicholasGrGLSLFragmentProcessor* GrAlphaThresholdFragmentProcessor::onCreateGLSLInstance() const {
789fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    return new GrGLSLAlphaThresholdFragmentProcessor();
79f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips}
80b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholasvoid GrAlphaThresholdFragmentProcessor::onGetGLSLProcessorKey(const GrShaderCaps& caps,
81a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman                                                              GrProcessorKeyBuilder* b) const {}
829fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholasbool GrAlphaThresholdFragmentProcessor::onIsEqual(const GrFragmentProcessor& other) const {
839fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    const GrAlphaThresholdFragmentProcessor& that = other.cast<GrAlphaThresholdFragmentProcessor>();
84b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas    (void)that;
859fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    if (fMask != that.fMask) return false;
869fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    if (fInnerThreshold != that.fInnerThreshold) return false;
879fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    if (fOuterThreshold != that.fOuterThreshold) return false;
889fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    return true;
89f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips}
90f57c0d67611186ba74179b53b421e64b63a579c7Ethan NicholasGrAlphaThresholdFragmentProcessor::GrAlphaThresholdFragmentProcessor(
91f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas        const GrAlphaThresholdFragmentProcessor& src)
92abff956455637b12eab374fd44b99e1338799113Ethan Nicholas        : INHERITED(kGrAlphaThresholdFragmentProcessor_ClassID, src.optimizationFlags())
93f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas        , fMask(src.fMask)
94f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas        , fInnerThreshold(src.fInnerThreshold)
95f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas        , fOuterThreshold(src.fOuterThreshold)
96f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas        , fMaskCoordTransform(src.fMaskCoordTransform) {
97f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas    this->addTextureSampler(&fMask);
98f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas    this->addCoordTransform(&fMaskCoordTransform);
99f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas}
100aff329b8e9b239bca1d93b13a914fbef45ccf7feBrian Salomonstd::unique_ptr<GrFragmentProcessor> GrAlphaThresholdFragmentProcessor::clone() const {
101aff329b8e9b239bca1d93b13a914fbef45ccf7feBrian Salomon    return std::unique_ptr<GrFragmentProcessor>(new GrAlphaThresholdFragmentProcessor(*this));
102f57c0d67611186ba74179b53b421e64b63a579c7Ethan Nicholas}
103f7142e71d7c0a7d8406679e207ff766085499d2erobertphillipsGR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrAlphaThresholdFragmentProcessor);
1046f6961ebad65c582318564b3688e78e5c99f3935Hal Canary#if GR_TEST_UTILS
105aff329b8e9b239bca1d93b13a914fbef45ccf7feBrian Salomonstd::unique_ptr<GrFragmentProcessor> GrAlphaThresholdFragmentProcessor::TestCreate(
106b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas        GrProcessorTestData* testData) {
1079fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    sk_sp<GrTextureProxy> maskProxy = testData->textureProxy(GrProcessorUnitTest::kAlphaTextureIdx);
1085b5f096a038259b8d9084834f877588a0db80250Ethan Nicholas    // Make the inner and outer thresholds be in (0, 1) exclusive and be sorted correctly.
1099fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    float innerThresh = testData->fRandom->nextUScalar1() * .99f + 0.005f;
1109fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    float outerThresh = testData->fRandom->nextUScalar1() * .99f + 0.005f;
111f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips    const int kMaxWidth = 1000;
112f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips    const int kMaxHeight = 1000;
1139fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    uint32_t width = testData->fRandom->nextULessThan(kMaxWidth);
1149fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    uint32_t height = testData->fRandom->nextULessThan(kMaxHeight);
1159fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    uint32_t x = testData->fRandom->nextULessThan(kMaxWidth - width);
1169fb036fb133d0b2eafb95a86a06b7910c0b0039cEthan Nicholas    uint32_t y = testData->fRandom->nextULessThan(kMaxHeight - height);
117f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips    SkIRect bounds = SkIRect::MakeXYWH(x, y, width, height);
118a4aa1332a4c6a70d6c54a3bbc6172d26fc2dce15Brian Osman    return GrAlphaThresholdFragmentProcessor::Make(std::move(maskProxy), innerThresh, outerThresh,
119b7e8c3b52a306357ecd08d00170062137ec641d4Ethan Nicholas                                                   bounds);
120f7142e71d7c0a7d8406679e207ff766085499d2erobertphillips}
1216f6961ebad65c582318564b3688e78e5c99f3935Hal Canary#endif
122ceb4d48ef4839aab9d99d0200dcfe403ccd0cdf3Ethan Nicholas#endif
123