2 * Copyright 2012 Google Inc.
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
8 #ifndef GrClipMaskManager_DEFINED
9 #define GrClipMaskManager_DEFINED
11 #include "GrClipMaskCache.h"
12 #include "GrContext.h"
13 #include "GrDrawState.h"
14 #include "GrReducedClip.h"
15 #include "GrStencil.h"
16 #include "GrTexture.h"
18 #include "SkClipStack.h"
27 class GrPathRendererChain;
32 * The clip mask creator handles the generation of the clip mask. If anti
33 * aliasing is requested it will (in the future) generate a single channel
34 * (8bit) mask. If no anti aliasing is requested it will generate a 1-bit
35 * mask in the stencil buffer. In the non anti-aliasing case, if the clip
36 * mask can be represented as a rectangle then scissoring is used. In all
37 * cases scissoring is used to bound the range of the clip mask.
39 class GrClipMaskManager : SkNoncopyable {
42 : fCurrClipMaskType(kNone_ClipMaskType)
44 , fClipMode(kIgnoreClip_StencilClipMode) {
47 // The state of the scissor is controlled by the clip manager, no one else should set
48 // Scissor state. This should really be on Gpu itself. We should revist this when GPU
49 // and drawtarget are separate
51 ScissorState() : fEnabled(false) {}
52 void set(const SkIRect& rect) { fRect = rect; fEnabled = true; }
58 * Creates a clip mask if necessary as a stencil buffer or alpha texture
59 * and sets the GrGpu's scissor and stencil state. If the return is false
60 * then the draw can be skipped. The AutoRestoreEffects is initialized by
61 * the manager when it must install additional effects to implement the
62 * clip. devBounds is optional but can help optimize clipping.
64 bool setupClipping(const GrClipData* clipDataIn,
65 const SkRect* devBounds,
66 GrDrawState::AutoRestoreEffects*,
67 GrDrawState::AutoRestoreStencil*,
71 * Purge resources to free up memory. TODO: This class shouldn't hold any long lived refs
72 * which will allow ResourceCache2 to automatically purge anything this class has created.
74 void purgeResources();
76 bool isClipInStencil() const {
77 return kStencil_ClipMaskType == fCurrClipMaskType;
79 bool isClipInAlpha() const {
80 return kAlpha_ClipMaskType == fCurrClipMaskType;
83 GrContext* getContext() {
84 return fAACache.getContext();
87 void setClipTarget(GrClipTarget*);
89 void adjustPathStencilParams(GrStencilSettings*);
93 * Informs the helper function adjustStencilParams() about how the stencil
94 * buffer clip is being used.
96 enum StencilClipMode {
97 // Draw to the clip bit of the stencil buffer
98 kModifyClip_StencilClipMode,
99 // Clip against the existing representation of the clip in the high bit
100 // of the stencil buffer.
101 kRespectClip_StencilClipMode,
102 // Neither writing to nor clipping against the clip bit.
103 kIgnoreClip_StencilClipMode,
106 // Attempts to install a series of coverage effects to implement the clip. Return indicates
107 // whether the element list was successfully converted to effects.
108 bool installClipEffects(const GrReducedClip::ElementList&,
109 GrDrawState::AutoRestoreEffects*,
110 const SkVector& clipOffset,
111 const SkRect* devBounds);
113 // Draws the clip into the stencil buffer
114 bool createStencilClipMask(int32_t elementsGenID,
115 GrReducedClip::InitialState initialState,
116 const GrReducedClip::ElementList& elements,
117 const SkIRect& clipSpaceIBounds,
118 const SkIPoint& clipSpaceToStencilOffset);
119 // Creates an alpha mask of the clip. The mask is a rasterization of elements through the
120 // rect specified by clipSpaceIBounds.
121 GrTexture* createAlphaClipMask(int32_t elementsGenID,
122 GrReducedClip::InitialState initialState,
123 const GrReducedClip::ElementList& elements,
124 const SkIRect& clipSpaceIBounds);
125 // Similar to createAlphaClipMask but it rasterizes in SW and uploads to the result texture.
126 GrTexture* createSoftwareClipMask(int32_t elementsGenID,
127 GrReducedClip::InitialState initialState,
128 const GrReducedClip::ElementList& elements,
129 const SkIRect& clipSpaceIBounds);
131 // Returns the cached mask texture if it matches the elementsGenID and the clipSpaceIBounds.
132 // Returns NULL if not found.
133 GrTexture* getCachedMaskTexture(int32_t elementsGenID, const SkIRect& clipSpaceIBounds);
136 // Handles allocation (if needed) of a clip alpha-mask texture for both the sw-upload
137 // or gpu-rendered cases.
138 GrTexture* allocMaskTexture(int32_t elementsGenID,
139 const SkIRect& clipSpaceIBounds,
142 bool useSWOnlyPath(const GrReducedClip::ElementList& elements);
144 // Draws a clip element into the target alpha mask. The caller should have already setup the
145 // desired blend operation. Optionally if the caller already selected a path renderer it can
146 // be passed. Otherwise the function will select one if the element is a path.
147 bool drawElement(GrTexture* target, const SkClipStack::Element*, GrPathRenderer* = NULL);
149 // Determines whether it is possible to draw the element to both the stencil buffer and the
150 // alpha mask simultaneously. If so and the element is a path a compatible path renderer is
152 bool canStencilAndDrawElement(GrTexture* target, const SkClipStack::Element*, GrPathRenderer**);
154 void mergeMask(GrTexture* dstMask,
157 const SkIRect& dstBound,
158 const SkIRect& srcBound);
160 GrTexture* createTempMask(int width, int height);
162 void setupCache(const SkClipStack& clip,
163 const SkIRect& bounds);
166 * Called prior to return control back the GrGpu in setupClipping. It
167 * updates the GrGpu with stencil settings that account stencil-based
170 void setDrawStateStencil(GrDrawState::AutoRestoreStencil* asr);
173 * Adjusts the stencil settings to account for interaction with stencil
176 void adjustStencilParams(GrStencilSettings* settings,
177 StencilClipMode mode,
181 * We may represent the clip as a mask in the stencil buffer or as an alpha
182 * texture. It may be neither because the scissor rect suffices or we
183 * haven't yet examined the clip.
187 kStencil_ClipMaskType,
191 GrClipMaskCache fAACache; // cache for the AA path
192 GrClipTarget* fClipTarget;
193 StencilClipMode fClipMode;
195 typedef SkNoncopyable INHERITED;
198 #endif // GrClipMaskManager_DEFINED