GrRenderTargetContext.h revision 649a3411f99a8aea3c46e4ef1f495f61b9801164
1/*
2 * Copyright 2015 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 GrRenderTargetContext_DEFINED
9#define GrRenderTargetContext_DEFINED
10
11#include "GrColor.h"
12#include "GrContext.h"
13#include "GrPaint.h"
14#include "GrSurfaceContext.h"
15#include "GrXferProcessor.h"
16#include "SkRefCnt.h"
17#include "SkSurfaceProps.h"
18#include "../private/GrInstancedPipelineInfo.h"
19#include "../private/GrRenderTargetProxy.h"
20
21class GrClip;
22class GrDrawingManager;
23class GrDrawOp;
24class GrFixedClip;
25class GrPipelineBuilder;
26class GrMeshDrawOp;
27class GrRenderTarget;
28class GrRenderTargetContextPriv;
29class GrRenderTargetOpList;
30class GrStyle;
31class GrSurface;
32class GrTextureProxy;
33struct GrUserStencilSettings;
34class SkDrawFilter;
35struct SkIPoint;
36struct SkIRect;
37class SkLatticeIter;
38class SkMatrix;
39class SkPaint;
40class SkPath;
41struct SkPoint;
42struct SkRect;
43class SkRegion;
44class SkRRect;
45struct SkRSXform;
46class SkTextBlob;
47class SkVertices;
48
49/**
50 * A helper object to orchestrate commands (draws, etc...) for GrSurfaces that are GrRenderTargets.
51 */
52class SK_API GrRenderTargetContext : public GrSurfaceContext {
53public:
54    ~GrRenderTargetContext() override;
55
56    // We use SkPaint rather than GrPaint here for two reasons:
57    //    * The SkPaint carries extra text settings. If these were extracted to a lighter object
58    //      we could use GrPaint except that
59    //    * SkPaint->GrPaint conversion depends upon whether the glyphs are color or grayscale and
60    //      this can vary within a text run.
61    virtual void drawText(const GrClip&, const SkPaint&, const SkMatrix& viewMatrix,
62                          const char text[], size_t byteLength, SkScalar x, SkScalar y,
63                          const SkIRect& clipBounds);
64    virtual void drawPosText(const GrClip&, const SkPaint&, const SkMatrix& viewMatrix,
65                             const char text[], size_t byteLength, const SkScalar pos[],
66                             int scalarsPerPosition, const SkPoint& offset,
67                             const SkIRect& clipBounds);
68    virtual void drawTextBlob(const GrClip&, const SkPaint&,
69                              const SkMatrix& viewMatrix, const SkTextBlob*,
70                              SkScalar x, SkScalar y,
71                              SkDrawFilter*, const SkIRect& clipBounds);
72
73    /**
74     * Provides a perfomance hint that the render target's contents are allowed
75     * to become undefined.
76     */
77    void discard();
78
79    /**
80     * Clear the entire or rect of the render target, ignoring any clips.
81     * @param rect  the rect to clear or the whole thing if rect is NULL.
82     * @param color the color to clear to.
83     * @param canIgnoreRect allows partial clears to be converted to whole
84     *                      clears on platforms for which that is cheap
85     */
86    void clear(const SkIRect* rect, GrColor color, bool canIgnoreRect);
87
88    /**
89     *  Draw everywhere (respecting the clip) with the paint.
90     */
91    void drawPaint(const GrClip&, GrPaint&&, const SkMatrix& viewMatrix);
92
93    /**
94     * Draw the rect using a paint.
95     * @param paint        describes how to color pixels.
96     * @param GrAA         Controls whether rect is antialiased
97     * @param viewMatrix   transformation matrix
98     * @param style        The style to apply. Null means fill. Currently path effects are not
99     *                     allowed.
100     * The rects coords are used to access the paint (through texture matrix)
101     */
102    void drawRect(const GrClip&,
103                  GrPaint&& paint,
104                  GrAA,
105                  const SkMatrix& viewMatrix,
106                  const SkRect&,
107                  const GrStyle* style = nullptr);
108
109    /**
110     * Maps a rectangle of shader coordinates to a rectangle and fills that rectangle.
111     *
112     * @param paint        describes how to color pixels.
113     * @param GrAA         Controls whether rect is antialiased
114     * @param viewMatrix   transformation matrix which applies to rectToDraw
115     * @param rectToDraw   the rectangle to draw
116     * @param localRect    the rectangle of shader coordinates applied to rectToDraw
117     */
118    void fillRectToRect(const GrClip&,
119                        GrPaint&& paint,
120                        GrAA,
121                        const SkMatrix& viewMatrix,
122                        const SkRect& rectToDraw,
123                        const SkRect& localRect);
124
125    /**
126     * Fills a rect with a paint and a localMatrix.
127     */
128    void fillRectWithLocalMatrix(const GrClip& clip,
129                                 GrPaint&& paint,
130                                 GrAA,
131                                 const SkMatrix& viewMatrix,
132                                 const SkRect& rect,
133                                 const SkMatrix& localMatrix);
134
135    /**
136     * Draw a roundrect using a paint.
137     *
138     * @param paint       describes how to color pixels.
139     * @param GrAA        Controls whether rrect is antialiased.
140     * @param viewMatrix  transformation matrix
141     * @param rrect       the roundrect to draw
142     * @param style       style to apply to the rrect. Currently path effects are not allowed.
143     */
144    void drawRRect(const GrClip&,
145                   GrPaint&&,
146                   GrAA,
147                   const SkMatrix& viewMatrix,
148                   const SkRRect& rrect,
149                   const GrStyle& style);
150
151    /**
152     * Draw a roundrect using a paint and a shadow shader. This is separate from drawRRect
153     * because it uses different underlying geometry and GeometryProcessor
154     *
155     * @param paint        describes how to color pixels.
156     * @param viewMatrix   transformation matrix
157     * @param rrect        the roundrect to draw
158     * @param blurRadius   amount of shadow blur to apply (in device space)
159     * @param style        style to apply to the rrect. Currently path effects are not allowed.
160     */
161    void drawShadowRRect(const GrClip&,
162                         GrPaint&&,
163                         const SkMatrix& viewMatrix,
164                         const SkRRect& rrect,
165                         SkScalar blurRadius,
166                         const GrStyle& style);
167
168    /**
169     * Shortcut for filling a SkPath consisting of nested rrects using a paint. The result is
170     * undefined if outer does not contain inner.
171     *
172     * @param paint        describes how to color pixels.
173     * @param GrAA         Controls whether rrects edges are antialiased
174     * @param viewMatrix   transformation matrix
175     * @param outer        the outer roundrect
176     * @param inner        the inner roundrect
177     */
178    void drawDRRect(const GrClip&,
179                    GrPaint&&,
180                    GrAA,
181                    const SkMatrix& viewMatrix,
182                    const SkRRect& outer,
183                    const SkRRect& inner);
184
185    /**
186     * Draws a path.
187     *
188     * @param paint         describes how to color pixels.
189     * @param GrAA          Controls whether the path is antialiased.
190     * @param viewMatrix    transformation matrix
191     * @param path          the path to draw
192     * @param style         style to apply to the path.
193     */
194    void drawPath(const GrClip&,
195                  GrPaint&&,
196                  GrAA,
197                  const SkMatrix& viewMatrix,
198                  const SkPath&,
199                  const GrStyle& style);
200
201    enum class ColorArrayType {
202        kPremulGrColor,
203        kSkColor,
204    };
205    /**
206     * Draws vertices with a paint.
207     *
208     * @param   paint           describes how to color pixels.
209     * @param   viewMatrix      transformation matrix
210     * @param   primitiveType   primitives type to draw.
211     * @param   vertexCount     number of vertices.
212     * @param   positions       array of vertex positions, required.
213     * @param   texCoords       optional array of texture coordinates used
214     *                          to access the paint.
215     * @param   colors          optional array of per-vertex colors, supercedes
216     *                          the paint's color field.
217     * @param   indices         optional array of indices. If NULL vertices
218     *                          are drawn non-indexed.
219     * @param   indexCount      if indices is non-null then this is the
220     *                          number of indices.
221     * @param   ColorArrayType  Determines how the color array should be interpreted.
222     */
223    void drawVertices(const GrClip&,
224                      GrPaint&& paint,
225                      const SkMatrix& viewMatrix,
226                      GrPrimitiveType primitiveType,
227                      int vertexCount,
228                      const SkPoint positions[],
229                      const SkPoint texs[],
230                      const uint32_t colors[],
231                      const uint16_t indices[],
232                      int indexCount,
233                      ColorArrayType = ColorArrayType::kPremulGrColor);
234
235    /**
236     * Draws vertices with a paint.
237     *
238     * @param   paint           describes how to color pixels.
239     * @param   viewMatrix      transformation matrix
240     * @param   veritces        specifies the mesh to draw.
241     * @param   flags           A bitfield of options specified by SkCanvas::VerticesFlags.
242     */
243    void drawVertices(const GrClip&,
244                      GrPaint&& paint,
245                      const SkMatrix& viewMatrix,
246                      sk_sp<SkVertices> vertices,
247                      uint32_t flags);
248
249    /**
250     * Draws textured sprites from an atlas with a paint. This currently does not support AA for the
251     * sprite rectangle edges.
252     *
253     * @param   paint           describes how to color pixels.
254     * @param   viewMatrix      transformation matrix
255     * @param   spriteCount     number of sprites.
256     * @param   xform           array of compressed transformation data, required.
257     * @param   texRect         array of texture rectangles used to access the paint.
258     * @param   colors          optional array of per-sprite colors, supercedes
259     *                          the paint's color field.
260     */
261    void drawAtlas(const GrClip&,
262                   GrPaint&& paint,
263                   const SkMatrix& viewMatrix,
264                   int spriteCount,
265                   const SkRSXform xform[],
266                   const SkRect texRect[],
267                   const SkColor colors[]);
268
269    /**
270     * Draws a region.
271     *
272     * @param paint         describes how to color pixels
273     * @param viewMatrix    transformation matrix
274     * @param aa            should the rects of the region be antialiased.
275     * @param region        the region to be drawn
276     * @param style         style to apply to the region
277     */
278    void drawRegion(const GrClip&,
279                    GrPaint&& paint,
280                    GrAA aa,
281                    const SkMatrix& viewMatrix,
282                    const SkRegion& region,
283                    const GrStyle& style);
284
285    /**
286     * Draws an oval.
287     *
288     * @param paint         describes how to color pixels.
289     * @param GrAA          Controls whether the oval is antialiased.
290     * @param viewMatrix    transformation matrix
291     * @param oval          the bounding rect of the oval.
292     * @param style         style to apply to the oval. Currently path effects are not allowed.
293     */
294    void drawOval(const GrClip&,
295                  GrPaint&& paint,
296                  GrAA,
297                  const SkMatrix& viewMatrix,
298                  const SkRect& oval,
299                  const GrStyle& style);
300    /**
301     * Draws a partial arc of an oval.
302     *
303     * @param paint         describes how to color pixels.
304     * @param GrGrAA        Controls whether the arc is antialiased.
305     * @param viewMatrix    transformation matrix.
306     * @param oval          the bounding rect of the oval.
307     * @param startAngle    starting angle in degrees.
308     * @param sweepAngle    angle to sweep in degrees. Must be in (-360, 360)
309     * @param useCenter     true means that the implied path begins at the oval center, connects as
310     *                      a line to the point indicated by the start contains the arc indicated by
311     *                      the sweep angle. If false the line beginning at the center point is
312     *                      omitted.
313     * @param style         style to apply to the oval.
314     */
315    void drawArc(const GrClip&,
316                 GrPaint&& paint,
317                 GrAA,
318                 const SkMatrix& viewMatrix,
319                 const SkRect& oval,
320                 SkScalar startAngle,
321                 SkScalar sweepAngle,
322                 bool useCenter,
323                 const GrStyle& style);
324
325    /**
326     * Draw the image as a set of rects, specified by |iter|.
327     */
328    void drawImageLattice(const GrClip&,
329                          GrPaint&& paint,
330                          const SkMatrix& viewMatrix,
331                          int imageWidth,
332                          int imageHeight,
333                          std::unique_ptr<SkLatticeIter> iter,
334                          const SkRect& dst);
335
336    /**
337     * After this returns any pending surface IO will be issued to the backend 3D API and
338     * if the surface has MSAA it will be resolved.
339     */
340    void prepareForExternalIO();
341
342    bool isStencilBufferMultisampled() const {
343        return fRenderTargetProxy->isStencilBufferMultisampled();
344    }
345    bool isUnifiedMultisampled() const { return fRenderTargetProxy->isUnifiedMultisampled(); }
346    bool hasMixedSamples() const { return fRenderTargetProxy->isMixedSampled(); }
347
348    const GrCaps* caps() const { return fContext->caps(); }
349    const GrSurfaceDesc& desc() const { return fRenderTargetProxy->desc(); }
350    int width() const { return fRenderTargetProxy->width(); }
351    int height() const { return fRenderTargetProxy->height(); }
352    GrPixelConfig config() const { return fRenderTargetProxy->config(); }
353    int numColorSamples() const { return fRenderTargetProxy->numColorSamples(); }
354    const SkSurfaceProps& surfaceProps() const { return fSurfaceProps; }
355    GrColorSpaceXform* getColorXformFromSRGB() const { return fColorXformFromSRGB.get(); }
356    GrSurfaceOrigin origin() const { return fRenderTargetProxy->origin(); }
357
358    bool wasAbandoned() const;
359
360    GrRenderTarget* instantiate();
361
362    GrRenderTarget* accessRenderTarget() {
363        // TODO: usage of this entry point needs to be reduced and potentially eliminated
364        // since it ends the deferral of the GrRenderTarget's allocation
365        return fRenderTargetProxy->instantiate(fContext->resourceProvider());
366    }
367
368    GrSurfaceProxy* asSurfaceProxy() override { return fRenderTargetProxy.get(); }
369    const GrSurfaceProxy* asSurfaceProxy() const override { return fRenderTargetProxy.get(); }
370    sk_sp<GrSurfaceProxy> asSurfaceProxyRef() override { return fRenderTargetProxy; }
371
372    GrTextureProxy* asTextureProxy() override;
373    sk_sp<GrTextureProxy> asTextureProxyRef() override;
374
375    GrRenderTargetProxy* asRenderTargetProxy() override { return fRenderTargetProxy.get(); }
376    sk_sp<GrRenderTargetProxy> asRenderTargetProxyRef() override { return fRenderTargetProxy; }
377
378    GrRenderTargetContext* asRenderTargetContext() override { return this; }
379
380    sk_sp<GrTexture> asTexture() {
381        if (!this->accessRenderTarget()) {
382            return nullptr;
383        }
384
385        // TODO: usage of this entry point needs to be reduced and potentially eliminated
386        // since it ends the deferral of the GrRenderTarget's allocation
387        // It's usage should migrate to asTextureProxyRef
388        return sk_ref_sp(this->accessRenderTarget()->asTexture());
389    }
390
391    // Provides access to functions that aren't part of the public API.
392    GrRenderTargetContextPriv priv();
393    const GrRenderTargetContextPriv priv() const;
394
395    bool isWrapped_ForTesting() const;
396
397protected:
398    GrRenderTargetContext(GrContext*, GrDrawingManager*, sk_sp<GrRenderTargetProxy>,
399                          sk_sp<SkColorSpace>, const SkSurfaceProps*, GrAuditTrail*,
400                          GrSingleOwner*);
401
402    SkDEBUGCODE(void validate() const;)
403
404private:
405    inline GrAAType decideAAType(GrAA aa, bool allowMixedSamples = false) {
406        if (GrAA::kNo == aa) {
407            return GrAAType::kNone;
408        }
409        if (this->isUnifiedMultisampled()) {
410            return GrAAType::kMSAA;
411        }
412        if (allowMixedSamples && this->isStencilBufferMultisampled()) {
413            return GrAAType::kMixedSamples;
414        }
415        return GrAAType::kCoverage;
416    }
417
418    friend class GrAtlasTextBlob;               // for access to add[Mesh]DrawOp
419    friend class GrStencilAndCoverTextContext;  // for access to add[Mesh]DrawOp
420
421    friend class GrDrawingManager; // for ctor
422    friend class GrRenderTargetContextPriv;
423    friend class GrSWMaskHelper;  // for access to add[Mesh]DrawOp
424
425    // All the path renderers currently make their own ops
426    friend class GrSoftwarePathRenderer;             // for access to add[Mesh]DrawOp
427    friend class GrAAConvexPathRenderer;             // for access to add[Mesh]DrawOp
428    friend class GrDashLinePathRenderer;             // for access to add[Mesh]DrawOp
429    friend class GrAAHairLinePathRenderer;           // for access to add[Mesh]DrawOp
430    friend class GrAALinearizingConvexPathRenderer;  // for access to add[Mesh]DrawOp
431    friend class GrAADistanceFieldPathRenderer;      // for access to add[Mesh]DrawOp
432    friend class GrDefaultPathRenderer;              // for access to add[Mesh]DrawOp
433    friend class GrMSAAPathRenderer;                 // for access to add[Mesh]DrawOp
434    friend class GrStencilAndCoverPathRenderer;      // for access to add[Mesh]DrawOp
435    friend class GrTessellatingPathRenderer;         // for access to add[Mesh]DrawOp
436    // for a unit test
437    friend void test_draw_op(GrContext*, GrRenderTargetContext*,
438                             sk_sp<GrFragmentProcessor>, sk_sp<GrTextureProxy>);
439
440    void internalClear(const GrFixedClip&, const GrColor, bool canIgnoreClip);
441
442    // Only consumes the GrPaint if successful.
443    bool drawFilledDRRect(const GrClip& clip,
444                          GrPaint&& paint,
445                          GrAA,
446                          const SkMatrix& viewMatrix,
447                          const SkRRect& origOuter,
448                          const SkRRect& origInner);
449
450    // Only consumes the GrPaint if successful.
451    bool drawFilledRect(const GrClip& clip,
452                        GrPaint&& paint,
453                        GrAA,
454                        const SkMatrix& viewMatrix,
455                        const SkRect& rect,
456                        const GrUserStencilSettings* ss);
457
458    void drawNonAAFilledRect(const GrClip&,
459                             GrPaint&&,
460                             const SkMatrix& viewMatrix,
461                             const SkRect& rect,
462                             const SkRect* localRect,
463                             const SkMatrix* localMatrix,
464                             const GrUserStencilSettings* ss,
465                             GrAAType hwOrNoneAAType);
466
467    void internalDrawPath(
468            const GrClip&, GrPaint&&, GrAA, const SkMatrix&, const SkPath&, const GrStyle&);
469
470    bool onCopy(GrSurfaceProxy* src, const SkIRect& srcRect, const SkIPoint& dstPoint) override;
471    bool onReadPixels(const SkImageInfo& dstInfo, void* dstBuffer,
472                      size_t dstRowBytes, int x, int y) override;
473    bool onWritePixels(const SkImageInfo& srcInfo, const void* srcBuffer,
474                       size_t srcRowBytes, int x, int y, uint32_t flags) override;
475
476    // These perform processing specific to Gr[Mesh]DrawOp-derived ops before recording them into
477    // the op list. They return the id of the opList to which the op was added, or 0, if it was
478    // dropped (e.g., due to clipping).
479    uint32_t addDrawOp(const GrPipelineBuilder&, const GrClip&, std::unique_ptr<GrDrawOp>);
480    uint32_t addMeshDrawOp(const GrPipelineBuilder&, const GrClip&,
481                           std::unique_ptr<GrMeshDrawOp> op);
482
483    // Makes a copy of the dst if it is necessary for the draw and returns the texture that should
484    // be used by GrXferProcessor to access the destination color. If the texture is nullptr then
485    // a texture copy could not be made.
486    void setupDstTexture(GrRenderTarget*, const GrClip&, const SkRect& opBounds,
487                         GrXferProcessor::DstTexture*);
488
489
490    GrRenderTargetOpList* getOpList();
491
492    sk_sp<GrRenderTargetProxy>        fRenderTargetProxy;
493
494    // In MDB-mode the GrOpList can be closed by some other renderTargetContext that has picked
495    // it up. For this reason, the GrOpList should only ever be accessed via 'getOpList'.
496    GrRenderTargetOpList*             fOpList;
497    GrInstancedPipelineInfo           fInstancedPipelineInfo;
498
499    sk_sp<GrColorSpaceXform>          fColorXformFromSRGB;
500    SkSurfaceProps                    fSurfaceProps;
501
502    typedef GrSurfaceContext INHERITED;
503};
504
505#endif
506