1/*
2 * Copyright 2017 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#ifndef SkDeferredDisplayList_DEFINED
9#define SkDeferredDisplayList_DEFINED
10
11#include "include/core/SkRefCnt.h"
12#include "include/core/SkSurfaceCharacterization.h"
13#include "include/core/SkTypes.h"
14
15class SkDeferredDisplayListPriv;
16
17#if SK_SUPPORT_GPU
18#include "include/private/GrRecordingContext.h"
19#include "include/private/SkTArray.h"
20#include <map>
21class GrRenderTask;
22class GrRenderTargetProxy;
23struct GrCCPerOpsTaskPaths;
24#endif
25
26/*
27 * This class contains pre-processed gpu operations that can be replayed into
28 * an SkSurface via SkSurface::draw(SkDeferredDisplayList*).
29 */
30class SkDeferredDisplayList {
31public:
32 SK_API ~SkDeferredDisplayList();
33
34 SK_API const SkSurfaceCharacterization& characterization() const {
35 return fCharacterization;
36 }
37
38#if SK_SUPPORT_GPU
39 /**
40 * Iterate through the programs required by the DDL.
41 */
42 class SK_API ProgramIterator {
43 public:
44 ProgramIterator(GrContext*, SkDeferredDisplayList*);
45 ~ProgramIterator();
46
47 void compile();
48 bool done() const;
49 void next();
50
51 private:
52 GrContext* fContext;
53 const SkTArray<GrRecordingContext::ProgramData>& fProgramData;
54 int fIndex;
55 };
56#endif
57
58 // Provides access to functions that aren't part of the public API.
59 SkDeferredDisplayListPriv priv();
60 const SkDeferredDisplayListPriv priv() const;
61
62private:
63 friend class GrDrawingManager; // for access to 'fRenderTasks', 'fLazyProxyData', 'fArenas'
64 friend class SkDeferredDisplayListRecorder; // for access to 'fLazyProxyData'
65 friend class SkDeferredDisplayListPriv;
66
67 // This object is the source from which the lazy proxy backing the DDL will pull its backing
68 // texture when the DDL is replayed. It has to be separately ref counted bc the lazy proxy
69 // can outlive the DDL.
70 class LazyProxyData : public SkRefCnt {
71#if SK_SUPPORT_GPU
72 public:
73 // Upon being replayed - this field will be filled in (by the DrawingManager) with the
74 // proxy backing the destination SkSurface. Note that, since there is no good place to
75 // clear it, it can become a dangling pointer.
76 GrRenderTargetProxy* fReplayDest = nullptr;
77#endif
78 };
79
80 SK_API SkDeferredDisplayList(const SkSurfaceCharacterization& characterization,
81 sk_sp<LazyProxyData>);
82
83#if SK_SUPPORT_GPU
84 const SkTArray<GrRecordingContext::ProgramData>& programData() const {
85 return fProgramData;
86 }
87#endif
88
89 const SkSurfaceCharacterization fCharacterization;
90
91#if SK_SUPPORT_GPU
92 // This needs to match the same type in GrCoverageCountingPathRenderer.h
93 using PendingPathsMap = std::map<uint32_t, sk_sp<GrCCPerOpsTaskPaths>>;
94
95 // When programs are stored in 'fProgramData' their memory is actually allocated in
96 // 'fArenas.fRecordTimeAllocator'. In that case that arena must be freed before
97 // 'fPendingPaths' which relies on uniquely holding the atlas proxies used by the
98 // GrCCClipPaths.
99 PendingPathsMap fPendingPaths; // This is the path data from CCPR.
100 // These are ordered such that the destructor cleans op tasks up first (which may refer back
101 // to the arena and memory pool in their destructors).
102 GrRecordingContext::OwnedArenas fArenas;
103 SkTArray<sk_sp<GrRenderTask>> fRenderTasks;
104
105 SkTArray<GrRecordingContext::ProgramData> fProgramData;
106 sk_sp<LazyProxyData> fLazyProxyData;
107#endif
108};
109
110#endif
111