blob: fa6bd26577a066f938d93b82b258e65e2e356964 [file] [log] [blame]
robertphillips76948d42016-05-04 12:47:41 -07001/*
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
csmartdaltonf9635992016-08-10 11:09:07 -070010#include "GrCaps.h"
robertphillips76948d42016-05-04 12:47:41 -070011#include "GrDrawTarget.h"
12#include "GrGpuResourcePriv.h"
robertphillips76948d42016-05-04 12:47:41 -070013
csmartdaltonf9635992016-08-10 11:09:07 -070014// Deferred version
15// TODO: we can probably munge the 'desc' in both the wrapped and deferred
16// cases to make the sampleConfig/numSamples stuff more rational.
17GrRenderTargetProxy::GrRenderTargetProxy(const GrCaps& caps, const GrSurfaceDesc& desc,
18 SkBackingFit fit, SkBudgeted budgeted)
19 : INHERITED(desc, fit, budgeted)
20 , fTarget(nullptr)
21 , fFlags(GrRenderTargetPriv::Flags::kNone)
22 , fLastDrawTarget(nullptr) {
23 // Since we know the newly created render target will be internal, we are able to precompute
24 // what the flags will ultimately end up being.
25 if (caps.usesMixedSamples() && fDesc.fSampleCnt > 0) {
26 fFlags |= GrRenderTargetPriv::Flags::kMixedSampled;
27 }
28 if (caps.maxWindowRectangles() > 0) {
29 fFlags |= GrRenderTargetPriv::Flags::kWindowRectsSupport;
30 }
31}
32
33// Wrapped version
34GrRenderTargetProxy::GrRenderTargetProxy(const GrCaps& caps, sk_sp<GrRenderTarget> rt)
robertphillips8abb3702016-08-31 14:04:06 -070035 : INHERITED(rt->desc(), SkBackingFit::kExact,
36 rt->resourcePriv().isBudgeted(), rt->uniqueID())
robertphillips76948d42016-05-04 12:47:41 -070037 , fTarget(std::move(rt))
csmartdaltonf9635992016-08-10 11:09:07 -070038 , fFlags(fTarget->renderTargetPriv().flags())
robertphillips76948d42016-05-04 12:47:41 -070039 , fLastDrawTarget(nullptr) {
40}
41
42GrRenderTargetProxy::~GrRenderTargetProxy() {
43 if (fLastDrawTarget) {
44 fLastDrawTarget->clearRT();
45 }
46 SkSafeUnref(fLastDrawTarget);
47}
48
49GrRenderTarget* GrRenderTargetProxy::instantiate(GrTextureProvider* texProvider) {
50 if (fTarget) {
51 return fTarget.get();
52 }
53
54 // TODO: it would be nice to not have to copy the desc here
55 GrSurfaceDesc desc = fDesc;
56 desc.fFlags |= GrSurfaceFlags::kRenderTarget_GrSurfaceFlag;
57
58 sk_sp<GrTexture> tex;
59 if (SkBackingFit::kApprox == fFit) {
60 tex.reset(texProvider->createApproxTexture(desc));
61 } else {
62 tex.reset(texProvider->createTexture(desc, fBudgeted));
63 }
64 if (!tex || !tex->asRenderTarget()) {
65 return nullptr;
66 }
67
68 fTarget = sk_ref_sp(tex->asRenderTarget());
69
70 // Check that our a priori computation matched the ultimate reality
csmartdaltonf9635992016-08-10 11:09:07 -070071 SkASSERT(fFlags == fTarget->renderTargetPriv().flags());
robertphillips76948d42016-05-04 12:47:41 -070072
73 return fTarget.get();
74}
75
76void GrRenderTargetProxy::setLastDrawTarget(GrDrawTarget* dt) {
77 if (fLastDrawTarget) {
78 // The non-MDB world never closes so we can't check this condition
79#ifdef ENABLE_MDB
80 SkASSERT(fLastDrawTarget->isClosed());
81#endif
82 fLastDrawTarget->clearRT();
83 }
84
85 SkRefCnt_SafeAssign(fLastDrawTarget, dt);
86}
87
88sk_sp<GrRenderTargetProxy> GrRenderTargetProxy::Make(const GrCaps& caps,
89 const GrSurfaceDesc& desc,
90 SkBackingFit fit,
91 SkBudgeted budgeted) {
92 return sk_sp<GrRenderTargetProxy>(new GrRenderTargetProxy(caps, desc, fit, budgeted));
93}
94
csmartdaltonf9635992016-08-10 11:09:07 -070095sk_sp<GrRenderTargetProxy> GrRenderTargetProxy::Make(const GrCaps& caps, sk_sp<GrRenderTarget> rt) {
96 return sk_sp<GrRenderTargetProxy>(new GrRenderTargetProxy(caps, rt));
robertphillips76948d42016-05-04 12:47:41 -070097}
98