GrRenderTargetProxy.cpp revision 96be9df1300b2281641b038ef11064157f6e0b41
1/*
2 * Copyright 2016 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "GrRenderTargetProxy.h"
9
10#include "GrCaps.h"
11#include "GrGpuResourcePriv.h"
12#include "GrRenderTargetOpList.h"
13#include "GrRenderTargetPriv.h"
14#include "GrResourceProvider.h"
15#include "GrTextureRenderTargetProxy.h"
16#include "SkMathPriv.h"
17
18// Deferred version
19// TODO: we can probably munge the 'desc' in both the wrapped and deferred
20// cases to make the sampleConfig/numSamples stuff more rational.
21GrRenderTargetProxy::GrRenderTargetProxy(const GrCaps& caps, const GrSurfaceDesc& desc,
22                                         SkBackingFit fit, SkBudgeted budgeted, uint32_t flags)
23        : INHERITED(desc, fit, budgeted, flags)
24        , fSampleCnt(desc.fSampleCnt)
25        , fRenderTargetFlags(GrRenderTargetFlags::kNone) {
26    // Since we know the newly created render target will be internal, we are able to precompute
27    // what the flags will ultimately end up being.
28    if (caps.usesMixedSamples() && fSampleCnt > 0) {
29        fRenderTargetFlags |= GrRenderTargetFlags::kMixedSampled;
30    }
31    if (caps.maxWindowRectangles() > 0) {
32        fRenderTargetFlags |= GrRenderTargetFlags::kWindowRectsSupport;
33    }
34}
35
36// Wrapped version
37GrRenderTargetProxy::GrRenderTargetProxy(sk_sp<GrSurface> surf)
38    : INHERITED(std::move(surf), SkBackingFit::kExact)
39    , fSampleCnt(fTarget->asRenderTarget()->numStencilSamples())
40    , fRenderTargetFlags(fTarget->asRenderTarget()->renderTargetPriv().flags()) {
41}
42
43int GrRenderTargetProxy::maxWindowRectangles(const GrCaps& caps) const {
44    return (fRenderTargetFlags & GrRenderTargetFlags::kWindowRectsSupport)
45                   ? caps.maxWindowRectangles()
46                   : 0;
47}
48
49bool GrRenderTargetProxy::instantiate(GrResourceProvider* resourceProvider) {
50    static constexpr GrSurfaceFlags kFlags = kRenderTarget_GrSurfaceFlag;
51
52    if (!this->instantiateImpl(resourceProvider, fSampleCnt, kFlags,
53                               /* isMipped = */ false,
54                               SkDestinationSurfaceColorMode::kLegacy)) {
55        return false;
56    }
57    SkASSERT(fTarget->asRenderTarget());
58    // Check that our a priori computation matched the ultimate reality
59    SkASSERT(fRenderTargetFlags == fTarget->asRenderTarget()->renderTargetPriv().flags());
60
61    return true;
62}
63
64sk_sp<GrSurface> GrRenderTargetProxy::createSurface(GrResourceProvider* resourceProvider) const {
65    static constexpr GrSurfaceFlags kFlags = kRenderTarget_GrSurfaceFlag;
66
67    sk_sp<GrSurface> surface = this->createSurfaceImpl(resourceProvider, fSampleCnt, kFlags,
68                                                       /* isMipped = */ false,
69                                                       SkDestinationSurfaceColorMode::kLegacy);
70    if (!surface) {
71        return nullptr;
72    }
73    SkASSERT(surface->asRenderTarget());
74    // Check that our a priori computation matched the ultimate reality
75    SkASSERT(fRenderTargetFlags == surface->asRenderTarget()->renderTargetPriv().flags());
76
77    return surface;
78}
79
80int GrRenderTargetProxy::worstCaseWidth() const {
81    if (fTarget) {
82        return fTarget->width();
83    }
84
85    if (SkBackingFit::kExact == fFit) {
86        return fWidth;
87    }
88    return SkTMax(GrResourceProvider::kMinScratchTextureSize, GrNextPow2(fWidth));
89}
90
91int GrRenderTargetProxy::worstCaseHeight() const {
92    if (fTarget) {
93        return fTarget->height();
94    }
95
96    if (SkBackingFit::kExact == fFit) {
97        return fHeight;
98    }
99    return SkTMax(GrResourceProvider::kMinScratchTextureSize, GrNextPow2(fHeight));
100}
101
102size_t GrRenderTargetProxy::onUninstantiatedGpuMemorySize() const {
103    int colorSamplesPerPixel = this->numColorSamples() + 1;
104    // TODO: do we have enough information to improve this worst case estimate?
105    return GrSurface::ComputeSize(fConfig, fWidth, fHeight, colorSamplesPerPixel, false,
106                                  SkBackingFit::kApprox == fFit);
107}
108
109bool GrRenderTargetProxy::refsWrappedObjects() const {
110    if (!fTarget) {
111        return false;
112    }
113
114    return fTarget->resourcePriv().refsWrappedObjects();
115}
116