1cb93a386Sopenharmony_ci/*
2cb93a386Sopenharmony_ci * Copyright 2015 Google Inc.
3cb93a386Sopenharmony_ci *
4cb93a386Sopenharmony_ci * Use of this source code is governed by a BSD-style license that can be
5cb93a386Sopenharmony_ci * found in the LICENSE file.
6cb93a386Sopenharmony_ci */
7cb93a386Sopenharmony_ci
8cb93a386Sopenharmony_ci#include "src/gpu/GrPipeline.h"
9cb93a386Sopenharmony_ci
10cb93a386Sopenharmony_ci#include "src/gpu/GrAppliedClip.h"
11cb93a386Sopenharmony_ci#include "src/gpu/GrCaps.h"
12cb93a386Sopenharmony_ci#include "src/gpu/GrXferProcessor.h"
13cb93a386Sopenharmony_ci#include "src/gpu/glsl/GrGLSLProgramDataManager.h"
14cb93a386Sopenharmony_ci#include "src/gpu/glsl/GrGLSLUniformHandler.h"
15cb93a386Sopenharmony_ci
16cb93a386Sopenharmony_ciGrPipeline::GrPipeline(const InitArgs& args,
17cb93a386Sopenharmony_ci                       sk_sp<const GrXferProcessor> xferProcessor,
18cb93a386Sopenharmony_ci                       const GrAppliedHardClip& hardClip)
19cb93a386Sopenharmony_ci        : fDstProxy(args.fDstProxyView)
20cb93a386Sopenharmony_ci        , fWindowRectsState(hardClip.windowRectsState())
21cb93a386Sopenharmony_ci        , fXferProcessor(std::move(xferProcessor))
22cb93a386Sopenharmony_ci        , fWriteSwizzle(args.fWriteSwizzle) {
23cb93a386Sopenharmony_ci    fFlags = (Flags)args.fInputFlags;
24cb93a386Sopenharmony_ci    if (hardClip.hasStencilClip()) {
25cb93a386Sopenharmony_ci        fFlags |= Flags::kHasStencilClip;
26cb93a386Sopenharmony_ci    }
27cb93a386Sopenharmony_ci    if (hardClip.scissorState().enabled()) {
28cb93a386Sopenharmony_ci        fFlags |= Flags::kScissorTestEnabled;
29cb93a386Sopenharmony_ci    }
30cb93a386Sopenharmony_ci    // If we have any special dst sample flags we better also have a dst proxy
31cb93a386Sopenharmony_ci    SkASSERT(this->dstSampleFlags() == GrDstSampleFlags::kNone || this->dstProxyView());
32cb93a386Sopenharmony_ci}
33cb93a386Sopenharmony_ci
34cb93a386Sopenharmony_ciGrPipeline::GrPipeline(const InitArgs& args, GrProcessorSet&& processors,
35cb93a386Sopenharmony_ci                       GrAppliedClip&& appliedClip)
36cb93a386Sopenharmony_ci        : GrPipeline(args, processors.refXferProcessor(), appliedClip.hardClip()) {
37cb93a386Sopenharmony_ci    SkASSERT(processors.isFinalized());
38cb93a386Sopenharmony_ci    // Copy GrFragmentProcessors from GrProcessorSet to Pipeline
39cb93a386Sopenharmony_ci    fNumColorProcessors = processors.hasColorFragmentProcessor() ? 1 : 0;
40cb93a386Sopenharmony_ci    int numTotalProcessors = fNumColorProcessors +
41cb93a386Sopenharmony_ci                             (processors.hasCoverageFragmentProcessor() ? 1 : 0) +
42cb93a386Sopenharmony_ci                             (appliedClip.hasCoverageFragmentProcessor() ? 1 : 0);
43cb93a386Sopenharmony_ci    fFragmentProcessors.reset(numTotalProcessors);
44cb93a386Sopenharmony_ci
45cb93a386Sopenharmony_ci    int currFPIdx = 0;
46cb93a386Sopenharmony_ci    if (processors.hasColorFragmentProcessor()) {
47cb93a386Sopenharmony_ci        fFragmentProcessors[currFPIdx++] = processors.detachColorFragmentProcessor();
48cb93a386Sopenharmony_ci    }
49cb93a386Sopenharmony_ci    if (processors.hasCoverageFragmentProcessor()) {
50cb93a386Sopenharmony_ci        fFragmentProcessors[currFPIdx++] = processors.detachCoverageFragmentProcessor();
51cb93a386Sopenharmony_ci    }
52cb93a386Sopenharmony_ci    if (appliedClip.hasCoverageFragmentProcessor()) {
53cb93a386Sopenharmony_ci        fFragmentProcessors[currFPIdx++] = appliedClip.detachCoverageFragmentProcessor();
54cb93a386Sopenharmony_ci    }
55cb93a386Sopenharmony_ci}
56cb93a386Sopenharmony_ci
57cb93a386Sopenharmony_ciGrXferBarrierType GrPipeline::xferBarrierType(const GrCaps& caps) const {
58cb93a386Sopenharmony_ci    if (this->dstSampleFlags() & GrDstSampleFlags::kRequiresTextureBarrier) {
59cb93a386Sopenharmony_ci        return kTexture_GrXferBarrierType;
60cb93a386Sopenharmony_ci    }
61cb93a386Sopenharmony_ci    return this->getXferProcessor().xferBarrierType(caps);
62cb93a386Sopenharmony_ci}
63cb93a386Sopenharmony_ci
64cb93a386Sopenharmony_ciGrPipeline::GrPipeline(GrScissorTest scissorTest,
65cb93a386Sopenharmony_ci                       sk_sp<const GrXferProcessor> xp,
66cb93a386Sopenharmony_ci                       const GrSwizzle& writeSwizzle,
67cb93a386Sopenharmony_ci                       InputFlags inputFlags)
68cb93a386Sopenharmony_ci        : fWindowRectsState()
69cb93a386Sopenharmony_ci        , fFlags((Flags)inputFlags)
70cb93a386Sopenharmony_ci        , fXferProcessor(std::move(xp))
71cb93a386Sopenharmony_ci        , fWriteSwizzle(writeSwizzle) {
72cb93a386Sopenharmony_ci    if (GrScissorTest::kEnabled == scissorTest) {
73cb93a386Sopenharmony_ci        fFlags |= Flags::kScissorTestEnabled;
74cb93a386Sopenharmony_ci    }
75cb93a386Sopenharmony_ci}
76cb93a386Sopenharmony_ci
77cb93a386Sopenharmony_civoid GrPipeline::genKey(GrProcessorKeyBuilder* b, const GrCaps& caps) const {
78cb93a386Sopenharmony_ci    // kSnapVerticesToPixelCenters is implemented in a shader.
79cb93a386Sopenharmony_ci    InputFlags ignoredFlags = InputFlags::kSnapVerticesToPixelCenters;
80cb93a386Sopenharmony_ci    b->add32((uint32_t)fFlags & ~(uint32_t)ignoredFlags, "flags");
81cb93a386Sopenharmony_ci
82cb93a386Sopenharmony_ci    const GrXferProcessor::BlendInfo& blendInfo = this->getXferProcessor().getBlendInfo();
83cb93a386Sopenharmony_ci
84cb93a386Sopenharmony_ci    static constexpr uint32_t kBlendCoeffSize = 5;
85cb93a386Sopenharmony_ci    static constexpr uint32_t kBlendEquationSize = 5;
86cb93a386Sopenharmony_ci    static_assert(kLast_GrBlendCoeff < (1 << kBlendCoeffSize));
87cb93a386Sopenharmony_ci    static_assert(kLast_GrBlendEquation < (1 << kBlendEquationSize));
88cb93a386Sopenharmony_ci
89cb93a386Sopenharmony_ci    b->addBool(blendInfo.fWriteColor, "writeColor");
90cb93a386Sopenharmony_ci    b->addBits(kBlendCoeffSize, blendInfo.fSrcBlend, "srcBlend");
91cb93a386Sopenharmony_ci    b->addBits(kBlendCoeffSize, blendInfo.fDstBlend, "dstBlend");
92cb93a386Sopenharmony_ci    b->addBits(kBlendEquationSize, blendInfo.fEquation, "equation");
93cb93a386Sopenharmony_ci    b->addBool(this->usesDstInputAttachment(), "inputAttach");
94cb93a386Sopenharmony_ci}
95cb93a386Sopenharmony_ci
96cb93a386Sopenharmony_civoid GrPipeline::visitTextureEffects(
97cb93a386Sopenharmony_ci        const std::function<void(const GrTextureEffect&)>& func) const {
98cb93a386Sopenharmony_ci    for (auto& fp : fFragmentProcessors) {
99cb93a386Sopenharmony_ci        fp->visitTextureEffects(func);
100cb93a386Sopenharmony_ci    }
101cb93a386Sopenharmony_ci}
102cb93a386Sopenharmony_ci
103cb93a386Sopenharmony_civoid GrPipeline::visitProxies(const GrVisitProxyFunc& func) const {
104cb93a386Sopenharmony_ci    // This iteration includes any clip coverage FPs
105cb93a386Sopenharmony_ci    for (auto& fp : fFragmentProcessors) {
106cb93a386Sopenharmony_ci        fp->visitProxies(func);
107cb93a386Sopenharmony_ci    }
108cb93a386Sopenharmony_ci    if (this->usesDstTexture()) {
109cb93a386Sopenharmony_ci        func(this->dstProxyView().proxy(), GrMipmapped::kNo);
110cb93a386Sopenharmony_ci    }
111cb93a386Sopenharmony_ci}
112cb93a386Sopenharmony_ci
113cb93a386Sopenharmony_civoid GrPipeline::setDstTextureUniforms(const GrGLSLProgramDataManager& pdm,
114cb93a386Sopenharmony_ci                                       GrGLSLBuiltinUniformHandles* fBuiltinUniformHandles) const {
115cb93a386Sopenharmony_ci    GrTexture* dstTexture = this->peekDstTexture();
116cb93a386Sopenharmony_ci
117cb93a386Sopenharmony_ci    if (dstTexture) {
118cb93a386Sopenharmony_ci        if (fBuiltinUniformHandles->fDstTextureCoordsUni.isValid()) {
119cb93a386Sopenharmony_ci            pdm.set4f(fBuiltinUniformHandles->fDstTextureCoordsUni,
120cb93a386Sopenharmony_ci                      static_cast<float>(this->dstTextureOffset().fX),
121cb93a386Sopenharmony_ci                      static_cast<float>(this->dstTextureOffset().fY),
122cb93a386Sopenharmony_ci                      1.f / dstTexture->width(),
123cb93a386Sopenharmony_ci                      1.f / dstTexture->height());
124cb93a386Sopenharmony_ci        }
125cb93a386Sopenharmony_ci    } else {
126cb93a386Sopenharmony_ci        SkASSERT(!fBuiltinUniformHandles->fDstTextureCoordsUni.isValid());
127cb93a386Sopenharmony_ci    }
128cb93a386Sopenharmony_ci}
129cb93a386Sopenharmony_ci
130cb93a386Sopenharmony_ci// Advanced Filter
131cb93a386Sopenharmony_cibool GrPipeline::checkAFRecursively() const
132cb93a386Sopenharmony_ci{
133cb93a386Sopenharmony_ci    for (const auto& fp : fFragmentProcessors) {
134cb93a386Sopenharmony_ci        if (fp != nullptr && fp->checkAFRecursively()) {
135cb93a386Sopenharmony_ci            return true;
136cb93a386Sopenharmony_ci        }
137cb93a386Sopenharmony_ci    }
138cb93a386Sopenharmony_ci    return false;
139cb93a386Sopenharmony_ci}
140