GrContext.h revision dafde9e2c1f048328a53f426927a142bc7d2adb8
1
2/*
3 * Copyright 2010 Google Inc.
4 *
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
7 */
8
9
10#ifndef GrContext_DEFINED
11#define GrContext_DEFINED
12
13#include "GrClip.h"
14#include "GrPaint.h"
15// not strictly needed but requires WK change in LayerTextureUpdaterCanvas to
16// remove.
17#include "GrRenderTarget.h"
18
19class GrDrawTarget;
20class GrFontCache;
21class GrGpu;
22struct GrGpuStats;
23class GrIndexBuffer;
24class GrIndexBufferAllocPool;
25class GrInOrderDrawBuffer;
26class GrPathRenderer;
27class GrPathRendererChain;
28class GrResourceEntry;
29class GrResourceCache;
30class GrStencilBuffer;
31class GrVertexBuffer;
32class GrVertexBufferAllocPool;
33
34class GR_API GrContext : public GrRefCnt {
35public:
36    /**
37     * Creates a GrContext from within a 3D context.
38     */
39    static GrContext* Create(GrEngine engine,
40                             GrPlatform3DContext context3D);
41
42    virtual ~GrContext();
43
44    /**
45     * The GrContext normally assumes that no outsider is setting state
46     * within the underlying 3D API's context/device/whatever. This call informs
47     * the context that the state was modified and it should resend. Shouldn't
48     * be called frequently for good performance.
49     */
50    void resetContext();
51
52    /**
53     * Abandons all gpu resources, assumes 3D API state is unknown. Call this
54     * if you have lost the associated GPU context, and thus internal texture,
55     * buffer, etc. references/IDs are now invalid. Should be called even when
56     * GrContext is no longer going to be used for two reasons:
57     *  1) ~GrContext will not try to free the objects in the 3D API.
58     *  2) If you've created GrResources that outlive the GrContext they will
59     *     be marked as invalid (GrResource::isValid()) and won't attempt to
60     *     free their underlying resource in the 3D API.
61     * Content drawn since the last GrContext::flush() may be lost.
62     */
63    void contextLost();
64
65    /**
66     * Similar to contextLost, but makes no attempt to reset state.
67     * Use this method when GrContext destruction is pending, but
68     * the graphics context is destroyed first.
69     */
70    void contextDestroyed();
71
72    /**
73     * Frees gpu created by the context. Can be called to reduce GPU memory
74     * pressure.
75     */
76    void freeGpuResources();
77
78    ///////////////////////////////////////////////////////////////////////////
79    // Textures
80
81    /**
82     * Token that refers to an entry in the texture cache. Returned by
83     * functions that lock textures. Passed to unlockTexture.
84     */
85    class TextureCacheEntry {
86    public:
87        TextureCacheEntry() : fEntry(NULL) {}
88        TextureCacheEntry(const TextureCacheEntry& e) : fEntry(e.fEntry) {}
89        TextureCacheEntry& operator= (const TextureCacheEntry& e) {
90            fEntry = e.fEntry;
91            return *this;
92        }
93        GrTexture* texture() const;
94        void reset() { fEntry = NULL; }
95    private:
96        explicit TextureCacheEntry(GrResourceEntry* entry) { fEntry = entry; }
97        void set(GrResourceEntry* entry) { fEntry = entry; }
98        GrResourceEntry* cacheEntry() { return fEntry; }
99        GrResourceEntry* fEntry;
100        friend class GrContext;
101    };
102
103    /**
104     * Key generated by client. Should be a unique key on the texture data.
105     * Does not need to consider that width and height of the texture. Two
106     * textures with the same TextureKey but different bounds will not collide.
107     */
108    typedef uint64_t TextureKey;
109
110    /**
111     *  Create a new entry, based on the specified key and texture, and return
112     *  its "locked" entry. Must call be balanced with an unlockTexture() call.
113     *
114     *  @param key      A client-generated key that identifies the contents
115     *                  of the texture. Respecified to findAndLockTexture
116     *                  for subsequent uses of the texture.
117     *  @param sampler  The sampler state used to draw a texture may be used
118     *                  to determine how to store the pixel data in the texture
119     *                  cache. (e.g. different versions may exist for different
120     *                  wrap modes on GPUs with limited or no NPOT texture
121     *                  support). Only the wrap and filter fields are used. NULL
122     *                  implies clamp wrap modes and nearest filtering.
123     * @param desc      Description of the texture properties.
124     * @param srcData   Pointer to the pixel values.
125     * @param rowBytes  The number of bytes between rows of the texture. Zero
126     *                  implies tightly packed rows.
127     */
128    TextureCacheEntry createAndLockTexture(TextureKey key,
129                                           const GrSamplerState* sampler,
130                                           const GrTextureDesc& desc,
131                                           void* srcData, size_t rowBytes);
132
133    /**
134     *  Search for an entry based on key and dimensions. If found, "lock" it and
135     *  return it. The entry's texture() function will return NULL if not found.
136     *  Must be balanced with an unlockTexture() call.
137     *
138     *  @param key      A client-generated key that identifies the contents
139     *                  of the texture.
140     *  @param width    The width of the texture in pixels as specifed in
141     *                  the GrTextureDesc originally passed to
142     *                  createAndLockTexture
143     *  @param width    The height of the texture in pixels as specifed in
144     *                  the GrTextureDesc originally passed to
145     *                  createAndLockTexture
146     *  @param sampler  The sampler state used to draw a texture may be used
147     *                  to determine the cache entry used. (e.g. different
148     *                  versions may exist for different wrap modes on GPUs with
149     *                  limited or no NPOT texture support). Only the wrap and
150     *                  filter fields are used. NULL implies clamp wrap modes
151     *                  and nearest filtering.
152     */
153    TextureCacheEntry findAndLockTexture(TextureKey key,
154                                         int width,
155                                         int height,
156                                         const GrSamplerState* sampler);
157    /**
158     * Determines whether a texture is in the cache. If the texture is found it
159     * will not be locked or returned. This call does not affect the priority of
160     * the texture for deletion.
161     */
162    bool isTextureInCache(TextureKey key,
163                          int width,
164                          int height,
165                          const GrSamplerState*) const;
166
167    /**
168     * Enum that determines how closely a returned scratch texture must match
169     * a provided GrTextureDesc.
170     */
171    enum ScratchTexMatch {
172        /**
173         * Finds a texture that exactly matches the descriptor.
174         */
175        kExact_ScratchTexMatch,
176        /**
177         * Finds a texture that approximately matches the descriptor. Will be
178         * at least as large in width and height as desc specifies. If desc
179         * specifies that texture is a render target then result will be a
180         * render target. If desc specifies a render target and doesn't set the
181         * no stencil flag then result will have a stencil. Format and aa level
182         * will always match.
183         */
184        kApprox_ScratchTexMatch
185    };
186
187    /**
188     * Returns a texture matching the desc. It's contents are unknown. Subsequent
189     * requests with the same descriptor are not guaranteed to return the same
190     * texture. The same texture is guaranteed not be returned again until it is
191     * unlocked. Must call be balanced with an unlockTexture() call.
192     *
193     * Textures created by createAndLockTexture() hide the complications of
194     * tiling non-power-of-two textures on APIs that don't support this (e.g.
195     * unextended GLES2). Tiling a npot texture created by lockScratchTexture on
196     * such an API will create gaps in the tiling pattern. This includes clamp
197     * mode. (This may be addressed in a future update.)
198     */
199    TextureCacheEntry lockScratchTexture(const GrTextureDesc& desc, ScratchTexMatch match);
200
201    /**
202     *  When done with an entry, call unlockTexture(entry) on it, which returns
203     *  it to the cache, where it may be purged.
204     */
205    void unlockTexture(TextureCacheEntry entry);
206
207    /**
208     * Creates a texture that is outside the cache. Does not count against
209     * cache's budget.
210     */
211    GrTexture* createUncachedTexture(const GrTextureDesc&,
212                                     void* srcData,
213                                     size_t rowBytes);
214
215    /**
216     *  Returns true if the specified use of an indexed texture is supported.
217     */
218    bool supportsIndex8PixelConfig(const GrSamplerState*,
219                                   int width,
220                                   int height) const;
221
222    /**
223     *  Return the current texture cache limits.
224     *
225     *  @param maxTextures If non-null, returns maximum number of textures that
226     *                     can be held in the cache.
227     *  @param maxTextureBytes If non-null, returns maximum number of bytes of
228     *                         texture memory that can be held in the cache.
229     */
230    void getTextureCacheLimits(int* maxTextures, size_t* maxTextureBytes) const;
231
232    /**
233     *  Specify the texture cache limits. If the current cache exceeds either
234     *  of these, it will be purged (LRU) to keep the cache within these limits.
235     *
236     *  @param maxTextures The maximum number of textures that can be held in
237     *                     the cache.
238     *  @param maxTextureBytes The maximum number of bytes of texture memory
239     *                         that can be held in the cache.
240     */
241    void setTextureCacheLimits(int maxTextures, size_t maxTextureBytes);
242
243    /**
244     *  Return the max width or height of a texture supported by the current gpu
245     */
246    int getMaxTextureSize() const;
247
248    /**
249     * Return the max width or height of a render target supported by the
250     * current gpu
251     */
252    int getMaxRenderTargetSize() const;
253
254    ///////////////////////////////////////////////////////////////////////////
255    // Render targets
256
257    /**
258     * Sets the render target.
259     * @param target    the render target to set. (should not be NULL.)
260     */
261    void setRenderTarget(GrRenderTarget* target);
262
263    /**
264     * Gets the current render target.
265     * @return the currently bound render target. Should never be NULL.
266     */
267    const GrRenderTarget* getRenderTarget() const;
268    GrRenderTarget* getRenderTarget();
269
270    ///////////////////////////////////////////////////////////////////////////
271    // Platform Surfaces
272
273    /**
274     * Wraps an existing texture with a GrTexture object.
275     *
276     * OpenGL: if the object is a texture Gr may change its GL texture params
277     *         when it is drawn.
278     *
279     * @param  desc     description of the object to create.
280     *
281     * @return GrTexture object or NULL on failure.
282     */
283    GrTexture* createPlatformTexture(const GrPlatformTextureDesc& desc);
284
285    /**
286     * Wraps an existing render target with a GrRenderTarget object. It is
287     * similar to createPlatformTexture but can be used to draw into surfaces
288     * that are not also textures (e.g. FBO 0 in OpenGL, or an MSAA buffer that
289     * the client will resolve to a texture).
290     *
291     * @param  desc     description of the object to create.
292     *
293     * @return GrTexture object or NULL on failure.
294     */
295     GrRenderTarget* createPlatformRenderTarget(
296                                    const GrPlatformRenderTargetDesc& desc);
297
298    /**
299     * This interface is depracted and will be removed in a future revision.
300     * Callers should use createPlatformTexture or createPlatformRenderTarget
301     * instead.
302     *
303     * Wraps an existing 3D API surface in a GrObject. desc.fFlags determines
304     * the type of object returned. If kIsTexture is set the returned object
305     * will be a GrTexture*. Otherwise, it will be a GrRenderTarget*. If both
306     * are set the render target object is accessible by
307     * GrTexture::asRenderTarget().
308     *
309     * GL: if the object is a texture Gr may change its GL texture parameters
310     *     when it is drawn.
311     *
312     * @param   desc    description of the object to create.
313     * @return either a GrTexture* or GrRenderTarget* depending on desc. NULL
314     *         on failure.
315     */
316    GrResource* createPlatformSurface(const GrPlatformSurfaceDesc& desc);
317
318    ///////////////////////////////////////////////////////////////////////////
319    // Matrix state
320
321    /**
322     * Gets the current transformation matrix.
323     * @return the current matrix.
324     */
325    const GrMatrix& getMatrix() const;
326
327    /**
328     * Sets the transformation matrix.
329     * @param m the matrix to set.
330     */
331    void setMatrix(const GrMatrix& m);
332
333    /**
334     * Concats the current matrix. The passed matrix is applied before the
335     * current matrix.
336     * @param m the matrix to concat.
337     */
338    void concatMatrix(const GrMatrix& m) const;
339
340
341    ///////////////////////////////////////////////////////////////////////////
342    // Clip state
343    /**
344     * Gets the current clip.
345     * @return the current clip.
346     */
347    const GrClip& getClip() const;
348
349    /**
350     * Sets the clip.
351     * @param clip  the clip to set.
352     */
353    void setClip(const GrClip& clip);
354
355    /**
356     * Convenience method for setting the clip to a rect.
357     * @param rect  the rect to set as the new clip.
358     */
359    void setClip(const GrIRect& rect);
360
361    ///////////////////////////////////////////////////////////////////////////
362    // Draws
363
364    /**
365     * Clear the entire or rect of the render target, ignoring any clips.
366     * @param rect  the rect to clear or the whole thing if rect is NULL.
367     * @param color the color to clear to.
368     */
369    void clear(const GrIRect* rect, GrColor color);
370
371    /**
372     *  Draw everywhere (respecting the clip) with the paint.
373     */
374    void drawPaint(const GrPaint& paint);
375
376    /**
377     *  Draw the rect using a paint.
378     *  @param paint        describes how to color pixels.
379     *  @param strokeWidth  If strokeWidth < 0, then the rect is filled, else
380     *                      the rect is mitered stroked based on strokeWidth. If
381     *                      strokeWidth == 0, then the stroke is always a single
382     *                      pixel thick.
383     *  @param matrix       Optional matrix applied to the rect. Applied before
384     *                      context's matrix or the paint's matrix.
385     *  The rects coords are used to access the paint (through texture matrix)
386     */
387    void drawRect(const GrPaint& paint,
388                  const GrRect&,
389                  GrScalar strokeWidth = -1,
390                  const GrMatrix* matrix = NULL);
391
392    /**
393     * Maps a rect of paint coordinates onto the a rect of destination
394     * coordinates. Each rect can optionally be transformed. The srcRect
395     * is stretched over the dstRect. The dstRect is transformed by the
396     * context's matrix and the srcRect is transformed by the paint's matrix.
397     * Additional optional matrices can be provided by parameters.
398     *
399     * @param paint     describes how to color pixels.
400     * @param dstRect   the destination rect to draw.
401     * @param srcRect   rect of paint coordinates to be mapped onto dstRect
402     * @param dstMatrix Optional matrix to transform dstRect. Applied before
403     *                  context's matrix.
404     * @param srcMatrix Optional matrix to transform srcRect Applied before
405     *                  paint's matrix.
406     */
407    void drawRectToRect(const GrPaint& paint,
408                        const GrRect& dstRect,
409                        const GrRect& srcRect,
410                        const GrMatrix* dstMatrix = NULL,
411                        const GrMatrix* srcMatrix = NULL);
412
413    /**
414     * Draws a path.
415     *
416     * @param paint         describes how to color pixels.
417     * @param path          the path to draw
418     * @param fill          the path filling rule to use.
419     * @param translate     optional additional translation applied to the
420     *                      path.
421     */
422    void drawPath(const GrPaint& paint, const GrPath& path, GrPathFill fill,
423                  const GrPoint* translate = NULL);
424
425    /**
426     * Draws vertices with a paint.
427     *
428     * @param   paint           describes how to color pixels.
429     * @param   primitiveType   primitives type to draw.
430     * @param   vertexCount     number of vertices.
431     * @param   positions       array of vertex positions, required.
432     * @param   texCoords       optional array of texture coordinates used
433     *                          to access the paint.
434     * @param   colors          optional array of per-vertex colors, supercedes
435     *                          the paint's color field.
436     * @param   indices         optional array of indices. If NULL vertices
437     *                          are drawn non-indexed.
438     * @param   indexCount      if indices is non-null then this is the
439     *                          number of indices.
440     */
441    void drawVertices(const GrPaint& paint,
442                      GrPrimitiveType primitiveType,
443                      int vertexCount,
444                      const GrPoint positions[],
445                      const GrPoint texs[],
446                      const GrColor colors[],
447                      const uint16_t indices[],
448                      int indexCount);
449
450    ///////////////////////////////////////////////////////////////////////////
451    // Misc.
452
453    /**
454     * Flags that affect flush() behavior.
455     */
456    enum FlushBits {
457        /**
458         * A client may want Gr to bind a GrRenderTarget in the 3D API so that
459         * it can be rendered to directly. However, Gr lazily sets state. Simply
460         * calling setRenderTarget() followed by flush() without flags may not
461         * bind the render target. This flag forces the context to bind the last
462         * set render target in the 3D API.
463         */
464        kForceCurrentRenderTarget_FlushBit   = 0x1,
465        /**
466         * A client may reach a point where it has partially rendered a frame
467         * through a GrContext that it knows the user will never see. This flag
468         * causes the flush to skip submission of deferred content to the 3D API
469         * during the flush.
470         */
471        kDiscard_FlushBit                    = 0x2,
472    };
473
474    /**
475     * Call to ensure all drawing to the context has been issued to the
476     * underlying 3D API.
477     * @param flagsBitfield     flags that control the flushing behavior. See
478     *                          FlushBits.
479     */
480    void flush(int flagsBitfield = 0);
481
482    /**
483     * Reads a rectangle of pixels from a render target.
484     * @param target        the render target to read from. NULL means the
485     *                      current render target.
486     * @param left          left edge of the rectangle to read (inclusive)
487     * @param top           top edge of the rectangle to read (inclusive)
488     * @param width         width of rectangle to read in pixels.
489     * @param height        height of rectangle to read in pixels.
490     * @param config        the pixel config of the destination buffer
491     * @param buffer        memory to read the rectangle into.
492     * @param rowBytes      number of bytes bewtween consecutive rows. Zero
493     *                      means rows are tightly packed.
494     *
495     * @return true if the read succeeded, false if not. The read can fail
496     *              because of an unsupported pixel config or because no render
497     *              target is currently set.
498     */
499    bool readRenderTargetPixels(GrRenderTarget* target,
500                                int left, int top, int width, int height,
501                                GrPixelConfig config, void* buffer,
502                                size_t rowBytes) {
503        return this->internalReadRenderTargetPixels(target, left, top,
504                                                    width, height,
505                                                    config, buffer,
506                                                    rowBytes, 0);
507    }
508
509    /**
510     * Copy the src pixels [buffer, rowbytes, pixelconfig] into a render target
511     * at the specified rectangle.
512     * @param target        the render target to write into. NULL means the
513     *                      current render target.
514     * @param left          left edge of the rectangle to write (inclusive)
515     * @param top           top edge of the rectangle to write (inclusive)
516     * @param width         width of rectangle to write in pixels.
517     * @param height        height of rectangle to write in pixels.
518     * @param config        the pixel config of the source buffer
519     * @param buffer        memory to read the rectangle from.
520     * @param rowBytes      number of bytes bewtween consecutive rows. Zero
521     *                      means rows are tightly packed.
522     */
523    void writeRenderTargetPixels(GrRenderTarget* target,
524                                 int left, int top, int width, int height,
525                                 GrPixelConfig config, const void* buffer,
526                                 size_t rowBytes) {
527        this->internalWriteRenderTargetPixels(target, left, top, width, height,
528                                              config, buffer, rowBytes, 0);
529    }
530
531    /**
532     * Reads a rectangle of pixels from a texture.
533     * @param texture       the texture to read from.
534     * @param left          left edge of the rectangle to read (inclusive)
535     * @param top           top edge of the rectangle to read (inclusive)
536     * @param width         width of rectangle to read in pixels.
537     * @param height        height of rectangle to read in pixels.
538     * @param config        the pixel config of the destination buffer
539     * @param buffer        memory to read the rectangle into.
540     * @param rowBytes      number of bytes bewtween consecutive rows. Zero
541     *                      means rows are tightly packed.
542     *
543     * @return true if the read succeeded, false if not. The read can fail
544     *              because of an unsupported pixel config.
545     */
546    bool readTexturePixels(GrTexture* texture,
547                           int left, int top, int width, int height,
548                           GrPixelConfig config, void* buffer,
549                           size_t rowBytes) {
550        return this->internalReadTexturePixels(texture, left, top,
551                                               width, height,
552                                               config, buffer, rowBytes, 0);
553    }
554
555    /**
556     * Writes a rectangle of pixels to a texture.
557     * @param texture       the render target to read from.
558     * @param left          left edge of the rectangle to write (inclusive)
559     * @param top           top edge of the rectangle to write (inclusive)
560     * @param width         width of rectangle to write in pixels.
561     * @param height        height of rectangle to write in pixels.
562     * @param config        the pixel config of the source buffer
563     * @param buffer        memory to read pixels from
564     * @param rowBytes      number of bytes bewtween consecutive rows. Zero
565     *                      means rows are tightly packed.
566     */
567    void writeTexturePixels(GrTexture* texture,
568                            int left, int top, int width, int height,
569                            GrPixelConfig config, const void* buffer,
570                            size_t rowBytes) {
571        this->internalWriteTexturePixels(texture, left, top, width, height,
572                                         config, buffer, rowBytes, 0);
573    }
574    /**
575     * Copies all texels from one texture to another.
576     * @param src           the texture to copy from.
577     * @param dst           the render target to copy to.
578     */
579    void copyTexture(GrTexture* src, GrRenderTarget* dst);
580    /**
581     * Applies a 1D convolution kernel in the X direction to a rectangle of
582     * pixels from a given texture.
583     * @param texture         the texture to read from
584     * @param rect            the destination rectangle
585     * @param kernel          the convolution kernel (kernelWidth elements)
586     * @param kernelWidth     the width of the convolution kernel
587     */
588    void convolveInX(GrTexture* texture,
589                     const SkRect& rect,
590                     const float* kernel,
591                     int kernelWidth);
592    /**
593     * Applies a 1D convolution kernel in the Y direction to a rectangle of
594     * pixels from a given texture.
595     * direction.
596     * @param texture         the texture to read from
597     * @param rect            the destination rectangle
598     * @param kernel          the convolution kernel (kernelWidth elements)
599     * @param kernelWidth     the width of the convolution kernel
600     */
601    void convolveInY(GrTexture* texture,
602                     const SkRect& rect,
603                     const float* kernel,
604                     int kernelWidth);
605    ///////////////////////////////////////////////////////////////////////////
606    // Helpers
607
608    class AutoRenderTarget : ::GrNoncopyable {
609    public:
610        AutoRenderTarget(GrContext* context, GrRenderTarget* target) {
611            fContext = NULL;
612            fPrevTarget = context->getRenderTarget();
613            if (fPrevTarget != target) {
614                context->setRenderTarget(target);
615                fContext = context;
616            }
617        }
618        ~AutoRenderTarget() {
619            if (fContext) {
620                fContext->setRenderTarget(fPrevTarget);
621            }
622        }
623    private:
624        GrContext*      fContext;
625        GrRenderTarget* fPrevTarget;
626    };
627
628
629    ///////////////////////////////////////////////////////////////////////////
630    // Functions intended for internal use only.
631    GrGpu* getGpu() { return fGpu; }
632    const GrGpu* getGpu() const { return fGpu; }
633    GrFontCache* getFontCache() { return fFontCache; }
634    GrDrawTarget* getTextTarget(const GrPaint& paint);
635    void flushText();
636    const GrIndexBuffer* getQuadIndexBuffer() const;
637    void resetStats();
638    const GrGpuStats& getStats() const;
639    void printStats() const;
640    /**
641     * Stencil buffers add themselves to the cache using
642     * addAndLockStencilBuffer. When a SB's RT-attachment count
643     * reaches zero the SB unlocks itself using unlockStencilBuffer and is
644     * eligible for purging. findStencilBuffer is called to check the cache for
645     * a SB that matching an RT's criteria. If a match is found that has been
646     * unlocked (its attachment count has reached 0) then it will be relocked.
647     */
648    GrResourceEntry* addAndLockStencilBuffer(GrStencilBuffer* sb);
649    void unlockStencilBuffer(GrResourceEntry* sbEntry);
650    GrStencilBuffer* findStencilBuffer(int width, int height, int sampleCnt);
651
652private:
653    // used to keep track of when we need to flush the draw buffer
654    enum DrawCategory {
655        kBuffered_DrawCategory,      // last draw was inserted in draw buffer
656        kUnbuffered_DrawCategory,    // last draw was not inserted in the draw buffer
657        kText_DrawCategory           // text context was last to draw
658    };
659    DrawCategory fLastDrawCategory;
660
661    GrGpu*              fGpu;
662    GrResourceCache*    fTextureCache;
663    GrFontCache*        fFontCache;
664
665    GrPathRendererChain*        fPathRendererChain;
666
667    GrVertexBufferAllocPool*    fDrawBufferVBAllocPool;
668    GrIndexBufferAllocPool*     fDrawBufferIBAllocPool;
669    GrInOrderDrawBuffer*        fDrawBuffer;
670
671    GrIndexBuffer*              fAAFillRectIndexBuffer;
672    GrIndexBuffer*              fAAStrokeRectIndexBuffer;
673    int                         fMaxOffscreenAASize;
674
675    GrContext(GrGpu* gpu);
676
677    void fillAARect(GrDrawTarget* target,
678                    const GrRect& devRect,
679                    bool useVertexCoverage);
680
681    void strokeAARect(GrDrawTarget* target,
682                      const GrRect& devRect,
683                      const GrVec& devStrokeSize,
684                      bool useVertexCoverage);
685
686    inline int aaFillRectIndexCount() const;
687    GrIndexBuffer* aaFillRectIndexBuffer();
688
689    inline int aaStrokeRectIndexCount() const;
690    GrIndexBuffer* aaStrokeRectIndexBuffer();
691
692    void setupDrawBuffer();
693
694    void flushDrawBuffer();
695
696    void setPaint(const GrPaint& paint, GrDrawTarget* target);
697
698    GrDrawTarget* prepareToDraw(const GrPaint& paint, DrawCategory drawType);
699
700    GrPathRenderer* getPathRenderer(const GrPath& path,
701                                    GrPathFill fill,
702                                    bool antiAlias);
703
704    struct OffscreenRecord;
705
706    // determines whether offscreen AA should be applied
707    bool doOffscreenAA(GrDrawTarget* target,
708                       bool isHairLines) const;
709
710    // attempts to setup offscreen AA. All paint state must be transferred to
711    // target by the time this is called.
712    bool prepareForOffscreenAA(GrDrawTarget* target,
713                               bool requireStencil,
714                               const GrIRect& boundRect,
715                               GrPathRenderer* pr,
716                               OffscreenRecord* record);
717
718    // sets up target to draw coverage to the supersampled render target
719    void setupOffscreenAAPass1(GrDrawTarget* target,
720                               const GrIRect& boundRect,
721                               int tileX, int tileY,
722                               OffscreenRecord* record);
723
724    // sets up target to sample coverage of supersampled render target back
725    // to the main render target using stage kOffscreenStage.
726    void doOffscreenAAPass2(GrDrawTarget* target,
727                            const GrPaint& paint,
728                            const GrIRect& boundRect,
729                            int tileX, int tileY,
730                            OffscreenRecord* record);
731
732    // restored the draw target state and releases offscreen target to cache
733    void cleanupOffscreenAA(GrDrawTarget* target,
734                            GrPathRenderer* pr,
735                            OffscreenRecord* record);
736
737    void convolve(GrTexture* texture,
738                  const SkRect& rect,
739                  float imageIncrement[2],
740                  const float* kernel,
741                  int kernelWidth);
742
743    /**
744     * Flags to the internal read/write pixels funcs
745     */
746    enum PixelOpsFlags {
747        kDontFlush_PixelOpsFlag = 0x1,
748    };
749
750    bool internalReadRenderTargetPixels(GrRenderTarget* target,
751                                        int left, int top,
752                                        int width, int height,
753                                        GrPixelConfig config, void* buffer,
754                                        size_t rowBytes, uint32_t flags);
755
756    void internalWriteRenderTargetPixels(GrRenderTarget* target,
757                                        int left, int top,
758                                        int width, int height,
759                                        GrPixelConfig, const void* buffer,
760                                        size_t rowBytes, uint32_t flags);
761
762    bool internalReadTexturePixels(GrTexture* texture,
763                                   int left, int top,
764                                   int width, int height,
765                                   GrPixelConfig config, void* buffer,
766                                   size_t rowBytes, uint32_t flags);
767
768    void internalWriteTexturePixels(GrTexture* texture,
769                                    int left, int top,
770                                    int width, int height,
771                                    GrPixelConfig config, const void* buffer,
772                                    size_t rowBytes, uint32_t flags);
773    // needed for access to internalWriteTexturePixels. TODO: make GrContext
774    // be a facade for an internal class. Then functions that are public on the
775    // internal class would have only be callable in src/gpu. The facade would
776    // only have to functions necessary for clients.
777    friend class GrAtlas;
778
779    // computes vertex layout bits based on the paint. If paint expresses
780    // a texture for a stage, the stage coords will be bound to postitions
781    // unless hasTexCoords[s]==true in which case stage s's input coords
782    // are bound to tex coord index s. hasTexCoords == NULL is a shortcut
783    // for an array where all the values are false.
784    static int PaintStageVertexLayoutBits(
785                                    const GrPaint& paint,
786                                    const bool hasTexCoords[GrPaint::kTotalStages]);
787
788};
789
790/**
791 *  Save/restore the view-matrix in the context.
792 */
793class GrAutoMatrix : GrNoncopyable {
794public:
795    GrAutoMatrix() : fContext(NULL) {}
796    GrAutoMatrix(GrContext* ctx) : fContext(ctx) {
797        fMatrix = ctx->getMatrix();
798    }
799    GrAutoMatrix(GrContext* ctx, const GrMatrix& matrix) : fContext(ctx) {
800        fMatrix = ctx->getMatrix();
801        ctx->setMatrix(matrix);
802    }
803    void set(GrContext* ctx) {
804        if (NULL != fContext) {
805            fContext->setMatrix(fMatrix);
806        }
807        fMatrix = ctx->getMatrix();
808        fContext = ctx;
809    }
810    void set(GrContext* ctx, const GrMatrix& matrix) {
811        if (NULL != fContext) {
812            fContext->setMatrix(fMatrix);
813        }
814        fMatrix = ctx->getMatrix();
815        ctx->setMatrix(matrix);
816        fContext = ctx;
817    }
818    ~GrAutoMatrix() {
819        if (NULL != fContext) {
820            fContext->setMatrix(fMatrix);
821        }
822    }
823
824private:
825    GrContext*  fContext;
826    GrMatrix    fMatrix;
827};
828
829/**
830 * Gets and locks a scratch texture from a descriptor using
831 * either exact or approximate criteria. Unlocks texture in
832 * the destructor.
833 */
834class GrAutoScratchTexture : ::GrNoncopyable {
835public:
836    GrAutoScratchTexture()
837        : fContext(NULL) {
838    }
839
840    GrAutoScratchTexture(GrContext* context,
841                         const GrTextureDesc& desc,
842                         GrContext::ScratchTexMatch match =
843                            GrContext::kApprox_ScratchTexMatch)
844      : fContext(NULL) {
845      this->set(context, desc, match);
846    }
847
848    ~GrAutoScratchTexture() {
849        if (NULL != fContext) {
850            fContext->unlockTexture(fEntry);
851        }
852    }
853
854    GrTexture* set(GrContext* context,
855                   const GrTextureDesc& desc,
856                   GrContext::ScratchTexMatch match =
857                        GrContext::kApprox_ScratchTexMatch) {
858        if (NULL != fContext) {
859            fContext->unlockTexture(fEntry);
860        }
861        fContext = context;
862        if (NULL != fContext) {
863            fEntry = fContext->lockScratchTexture(desc, match);
864            GrTexture* ret = fEntry.texture();
865            if (NULL == ret) {
866                fContext = NULL;
867            }
868            return ret;
869        } else {
870            return NULL;
871        }
872    }
873
874    GrTexture* texture() { return fEntry.texture(); }
875private:
876    GrContext*                    fContext;
877    GrContext::TextureCacheEntry  fEntry;
878};
879
880#endif
881
882