blob: 9fb7b9c60494ee0b08097c591ef5487a4cc2036c [file] [log] [blame]
reed@google.comac10a2d2010-12-22 21:39:39 +00001/*
2 Copyright 2010 Google Inc.
3
4 Licensed under the Apache License, Version 2.0 (the "License");
5 you may not use this file except in compliance with the License.
6 You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10 Unless required by applicable law or agreed to in writing, software
11 distributed under the License is distributed on an "AS IS" BASIS,
12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 See the License for the specific language governing permissions and
14 limitations under the License.
15 */
16
17
18#ifndef GrGpu_DEFINED
19#define GrGpu_DEFINED
20
21#include "GrRect.h"
22#include "GrRefCnt.h"
23#include "GrDrawTarget.h"
24#include "GrGpuVertex.h"
25#include "GrTexture.h"
26#include "GrMemory.h"
27
bsalomon@google.com1c13c962011-02-14 16:51:21 +000028class GrVertexBufferAllocPool;
29class GrIndexBufferAllocPool;
reed@google.comac10a2d2010-12-22 21:39:39 +000030
31class GrGpu : public GrDrawTarget {
32
33public:
34 /**
35 * Possible 3D APIs that may be used by Ganesh.
36 */
37 enum Engine {
38 kOpenGL_Shaders_Engine,
39 kOpenGL_Fixed_Engine,
40 kDirect3D9_Engine
41 };
42
43 /**
44 * Platform specific 3D context.
45 * For
46 * kOpenGL_Shaders_Engine use NULL
47 * kOpenGL_Fixed_Engine use NULL
48 * kDirect3D9_Engine use an IDirect3DDevice9*
49 */
50 typedef void* Platform3DContext;
51
52 /**
53 * Create an instance of GrGpu that matches the specified Engine backend.
54 * If the requested engine is not supported (at compile-time or run-time)
55 * this returns NULL.
56 */
57 static GrGpu* Create(Engine, Platform3DContext context3D);
58
59 /**
reed@google.comac10a2d2010-12-22 21:39:39 +000060 * Used to control the level of antialiasing available for a rendertarget.
61 * Anti-alias quality levels depend on the underlying API/GPU capabilities.
62 */
63 enum AALevels {
64 kNone_AALevel, //<! No antialiasing available.
65 kLow_AALevel, //<! Low quality antialiased rendering. Actual
66 // interpretation is platform-dependent.
67 kMed_AALevel, //<! Medium quality antialiased rendering. Actual
68 // interpretation is platform-dependent.
69 kHigh_AALevel, //<! High quality antialiased rendering. Actual
70 // interpretation is platform-dependent.
71 };
72
73
74 /**
75 * Optional bitfield flags that can be passed to createTexture.
76 */
77 enum TextureFlags {
78 kRenderTarget_TextureFlag = 0x1, //<! Creates a texture that can be
79 // rendered to by calling
80 // GrGpu::setRenderTarget() with
81 // GrTexture::asRenderTarget().
82 kNoPathRendering_TextureFlag = 0x2, //<! If the texture is used as a
83 // rendertarget but paths will not
84 // be rendered to it.
85 kDynamicUpdate_TextureFlag = 0x4 //!< Hint that the CPU may modify
86 // this texture after creation
87 };
88
89 enum {
90 /**
91 * For Index8 pixel config, the colortable must be 256 entries
92 */
93 kColorTableSize = 256 * sizeof(GrColor)
94 };
95 /**
96 * Describes a texture to be created.
97 */
98 struct TextureDesc {
99 uint32_t fFlags; //!< bitfield of TextureFlags
100 GrGpu::AALevels fAALevel;//!< The level of antialiasing available
101 // for a rendertarget texture. Only
102 // flags contains
103 // kRenderTarget_TextureFlag.
104 uint32_t fWidth; //!< Width of the texture
105 uint32_t fHeight; //!< Height of the texture
106 GrTexture::PixelConfig fFormat; //!< Format of source data of the
107 // texture. Not guaraunteed to be the
108 // same as internal format used by
109 // 3D API.
110 };
111
112 /**
113 * Gpu usage statistics.
114 */
115 struct Stats {
116 uint32_t fVertexCnt; //<! Number of vertices drawn
117 uint32_t fIndexCnt; //<! Number of indices drawn
118 uint32_t fDrawCnt; //<! Number of draws
119
120 uint32_t fProgChngCnt;//<! Number of program changes (N/A for fixed)
121
122 /*
123 * Number of times the texture is set in 3D API
124 */
125 uint32_t fTextureChngCnt;
126 /*
127 * Number of times the render target is set in 3D API
128 */
129 uint32_t fRenderTargetChngCnt;
130 /*
131 * Number of textures created (includes textures that are rendertargets).
132 */
133 uint32_t fTextureCreateCnt;
134 /*
135 * Number of rendertargets created.
136 */
137 uint32_t fRenderTargetCreateCnt;
138 };
139
140 ////////////////////////////////////////////////////////////////////////////
141
142 GrGpu();
143 virtual ~GrGpu();
144
145 /**
146 * The GrGpu object normally assumes that no outsider is setting state
147 * within the underlying 3D API's context/device/whatever. This call informs
148 * the GrGpu that the state was modified and it should resend. Shouldn't
149 * be called frequently for good performance.
150 */
151 virtual void resetContext();
152
153 void unimpl(const char[]);
154
155 /**
bsalomon@google.com0748f212011-02-01 22:56:16 +0000156 * Creates a texture object. If desc width or height is not a power of
157 * two but underlying API requires a power of two texture then srcData
158 * will be embedded in a power of two texture. The extra width and height
159 * is filled as though srcData were rendered clamped into the texture.
reed@google.comac10a2d2010-12-22 21:39:39 +0000160 *
161 * @param desc describes the texture to be created.
162 * @param srcData texel data to load texture. Begins with full-size
163 * palette data for paletted textures. Contains width*
164 * height texels. If NULL texture data is uninitialized.
165 *
166 * @return The texture object if successful, otherwise NULL.
167 */
168 virtual GrTexture* createTexture(const TextureDesc& desc,
169 const void* srcData, size_t rowBytes) = 0;
170 /**
171 * Wraps an externally-created rendertarget in a GrRenderTarget.
172 * @param platformRenderTarget handle to the the render target in the
173 * underlying 3D API. Interpretation depends on
174 * GrGpu subclass in use.
175 * @param width width of the render target
176 * @param height height of the render target
177 */
178 virtual GrRenderTarget* createPlatformRenderTarget(
179 intptr_t platformRenderTarget,
180 int width, int height) = 0;
181
182 /**
bsalomon@google.com2e7b43d2011-01-18 20:57:22 +0000183 * Reads the current target object (e.g. FBO or IDirect3DSurface9*) and
184 * viewport state from the underlying 3D API and wraps it in a
185 * GrRenderTarget. The GrRenderTarget will not attempt to delete/destroy the
186 * underlying object in its destructor and it is up to caller to guarantee
187 * that it remains valid while the GrRenderTarget is used.
188 *
189 * @return the newly created GrRenderTarget
190 */
191 virtual GrRenderTarget* createRenderTargetFrom3DApiState() = 0;
192
193 /**
reed@google.comac10a2d2010-12-22 21:39:39 +0000194 * Creates a vertex buffer.
195 *
196 * @param size size in bytes of the vertex buffer
197 * @param dynamic hints whether the data will be frequently changed
198 * by either GrVertexBuffer::lock or
199 * GrVertexBuffer::updateData.
200 *
201 * @return The vertex buffer if successful, otherwise NULL.
202 */
203 virtual GrVertexBuffer* createVertexBuffer(uint32_t size, bool dynamic) = 0;
204
205 /**
206 * Creates an index buffer.
207 *
208 * @param size size in bytes of the index buffer
209 * @param dynamic hints whether the data will be frequently changed
210 * by either GrIndexBuffer::lock or
211 * GrIndexBuffer::updateData.
212 *
213 * @return The index buffer if successful, otherwise NULL.
214 */
215 virtual GrIndexBuffer* createIndexBuffer(uint32_t size, bool dynamic) = 0;
216
217 /**
reed@google.comac10a2d2010-12-22 21:39:39 +0000218 * Erase the entire render target, ignoring any clips/scissors.
219 *
220 * This is issued to the GPU driver immediately.
221 */
222 virtual void eraseColor(GrColor color) = 0;
223
224 /**
225 * Are 8 bit paletted textures supported.
226 *
227 * @return true if 8bit palette textures are supported, false otherwise
228 */
229 bool supports8BitPalette() const { return f8bitPaletteSupport; }
230
231 /**
232 * If single stencil pass winding is supported then one stencil pass
233 * (kWindingStencil1_PathPass) is required to do winding rule path filling
234 * (or inverse winding rule). Otherwise, two passes are required
235 * (kWindingStencil1_PathPass followed by kWindingStencil2_PathPass).
236 *
237 * @return true if only a single stencil pass is needed.
238 */
239 bool supportsSingleStencilPassWinding() const
240 { return fSingleStencilPassForWinding; }
241
242 /**
243 * Checks whether locking vertex and index buffers is supported.
244 *
245 * @return true if locking is supported.
246 */
247 bool supportsBufferLocking() const { return fBufferLockSupport; }
248
249 /**
250 * Gets the minimum width of a render target. If a texture/rt is created
251 * with a width less than this size the GrGpu object will clamp it to this
252 * value.
253 */
254 int minRenderTargetWidth() const { return fMinRenderTargetWidth; }
255
256 /**
257 * Gets the minimum width of a render target. If a texture/rt is created
258 * with a height less than this size the GrGpu object will clamp it to this
259 * value.
260 */
261 int minRenderTargetHeight() const { return fMinRenderTargetHeight; }
262
263 /**
bsalomon@google.com0748f212011-02-01 22:56:16 +0000264 * Returns true if NPOT textures can be created
reed@google.comac10a2d2010-12-22 21:39:39 +0000265 *
bsalomon@google.com0748f212011-02-01 22:56:16 +0000266 * @return true if NPOT textures can be created
reed@google.comac10a2d2010-12-22 21:39:39 +0000267 */
bsalomon@google.com0748f212011-02-01 22:56:16 +0000268 bool npotTextureSupport() const { return fNPOTTextureSupport; }
269
270 /**
271 * Returns true if NPOT textures can be repeat/mirror tiled.
272 *
273 * @return true if NPOT textures can be tiled
274 */
275 bool npotTextureTileSupport() const { return fNPOTTextureTileSupport; }
276
277 /**
278 * Returns true if a NPOT texture can be a rendertarget
279 *
280 * @return the true if NPOT texture/rendertarget can be created.
281 */
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000282 bool npotRenderTargetSupport() const { return fNPOTRenderTargetSupport; }
reed@google.comac10a2d2010-12-22 21:39:39 +0000283
reed@google.com02a7e6c2011-01-28 21:21:49 +0000284 int maxTextureDimension() const { return fMaxTextureDimension; }
285
reed@google.comac10a2d2010-12-22 21:39:39 +0000286 // GrDrawTarget overrides
287 virtual void drawIndexed(PrimitiveType type,
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000288 int startVertex,
289 int startIndex,
290 int vertexCount,
291 int indexCount);
reed@google.comac10a2d2010-12-22 21:39:39 +0000292
293 virtual void drawNonIndexed(PrimitiveType type,
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000294 int startVertex,
295 int vertexCount);
reed@google.comac10a2d2010-12-22 21:39:39 +0000296
297 /**
298 * Determines if blend is effectively disabled.
299 *
300 * @return true if blend can be disabled without changing the rendering
301 * result given the current state including the vertex layout specified
302 * with the vertex source.
303 */
304 bool canDisableBlend() const;
305
306 /**
307 * Returns an index buffer that can be used to render quads.
308 * Indices are 0, 1, 2, 0, 2, 3, etc.
309 * Draw with kTriangles_PrimitiveType
310 */
311 const GrIndexBuffer* quadIndexBuffer() const;
312 /**
313 * Gets the number of quads that can be rendered using quadIndexBuffer.
314 */
315 int maxQuadsInIndexBuffer() const;
316
317 /**
bsalomon@google.com6f7fbc92011-02-01 19:12:40 +0000318 * Returns a vertex buffer with four position-only vertices [(0,0), (1,0), (1,1), (0,1)]
319 */
320 const GrVertexBuffer* unitSquareVertexBuffer() const;
321
322 /**
reed@google.comac10a2d2010-12-22 21:39:39 +0000323 * Ensures that the current render target is actually set in the
324 * underlying 3D API. Used when client wants to use 3D API to directly
325 * render to the RT.
326 */
327 virtual void forceRenderTargetFlush() = 0;
328
329 virtual bool readPixels(int left, int top, int width, int height,
330 GrTexture::PixelConfig, void* buffer) = 0;
331
332
333 const Stats& getStats() const;
334 void resetStats();
335 void printStats() const;
336
337protected:
338 /**
339 * Extensions to GrDrawTarget::StencilPass to implement stencil clipping
340 */
341 enum GpuStencilPass {
342 kSetClip_StencilPass = kDrawTargetCount_StencilPass,
343 /* rendering a hard clip to the stencil
344 buffer. Subsequent draws with other
345 StencilPass values will be clipped
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000346 if kClip_StateBit is set. */
reed@google.comac10a2d2010-12-22 21:39:39 +0000347 kGpuCount_StencilPass
348 };
349
350 /**
351 * Extensions to GrDrawTarget::StateBits to implement stencil clipping
352 */
353 struct ClipState {
354 bool fClipInStencil;
355 bool fClipIsDirty;
356 GrRenderTarget* fStencilClipTarget;
357 } fClipState;
358
359 virtual void clipWillChange(const GrClip& clip);
360 bool setupClipAndFlushState(PrimitiveType type);
361
362 struct BoundsState {
363 bool fScissorEnabled;
364 GrIRect fScissorRect;
365 GrIRect fViewportRect;
366 };
367
368 // defaults to false, subclass can set true to support palleted textures
369 bool f8bitPaletteSupport;
370
bsalomon@google.com0748f212011-02-01 22:56:16 +0000371 // set by subclass
372 bool fNPOTTextureSupport;
373 bool fNPOTTextureTileSupport;
374 bool fNPOTRenderTargetSupport;
reed@google.comac10a2d2010-12-22 21:39:39 +0000375
376 // True if only one stencil pass is required to implement the winding path
377 // fill rule. Subclass responsible for setting this value.
378 bool fSingleStencilPassForWinding;
379
380 // set by subclass to true if index and vertex buffers can be locked, false
381 // otherwise.
382 bool fBufferLockSupport;
383
384 // set by subclass
385 int fMinRenderTargetWidth;
386 int fMinRenderTargetHeight;
reed@google.com02a7e6c2011-01-28 21:21:49 +0000387 int fMaxTextureDimension;
reed@google.comac10a2d2010-12-22 21:39:39 +0000388
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000389 Stats fStats;
390
391 const GrVertexBuffer* fCurrPoolVertexBuffer;
392 int fCurrPoolStartVertex;
393
394 const GrIndexBuffer* fCurrPoolIndexBuffer;
395 int fCurrPoolStartIndex;
396
397 // GrDrawTarget overrides
398 virtual bool acquireGeometryHelper(GrVertexLayout vertexLayout,
399 void** vertices,
400 void** indices);
401 virtual void releaseGeometryHelper();
402
403 virtual void setVertexSourceToArrayHelper(const void* vertexArray,
404 int vertexCount);
405
406 virtual void setIndexSourceToArrayHelper(const void* indexArray,
407 int indexCount);
408 // Helpers for setting up geometry state
409 void finalizeReservedVertices();
410 void finalizeReservedIndices();
411
reed@google.comac10a2d2010-12-22 21:39:39 +0000412 // overridden by API specific GrGpu-derived class to perform the draw call.
413 virtual void drawIndexedHelper(PrimitiveType type,
414 uint32_t startVertex,
415 uint32_t startIndex,
416 uint32_t vertexCount,
417 uint32_t indexCount) = 0;
418
419 virtual void drawNonIndexedHelper(PrimitiveType type,
420 uint32_t vertexCount,
421 uint32_t numVertices) = 0;
422
423 // called to program the vertex data, indexCount will be 0 if drawing non-
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000424 // indexed geometry. The subclass may adjust the startVertex and/or
425 // startIndex since it may have already accounted for these in the setup.
426 virtual void setupGeometry(int* startVertex,
427 int* startIndex,
428 int vertexCount,
429 int indexCount) = 0;
reed@google.comac10a2d2010-12-22 21:39:39 +0000430
431
432 // The GrGpu typically records the clients requested state and then flushes
433 // deltas from previous state at draw time. This function does the
434 // API-specific flush of the state
435 // returns false if current state is unsupported.
436 virtual bool flushGraphicsState(PrimitiveType type) = 0;
437
438 // Sets the scissor rect, or disables if rect is NULL.
439 virtual void flushScissor(const GrIRect* rect) = 0;
440
441 // GrGpu subclass removes the clip from the stencil buffer
442 virtual void eraseStencilClip() = 0;
443
reed@google.comac10a2d2010-12-22 21:39:39 +0000444private:
reed@google.comac10a2d2010-12-22 21:39:39 +0000445
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000446 void prepareVertexPool();
447 void prepareIndexPool();
bsalomon@google.com6f7fbc92011-02-01 19:12:40 +0000448
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000449 GrVertexBufferAllocPool* fVertexPool;
reed@google.comac10a2d2010-12-22 21:39:39 +0000450
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000451 GrIndexBufferAllocPool* fIndexPool;
reed@google.comac10a2d2010-12-22 21:39:39 +0000452
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000453 mutable GrIndexBuffer* fQuadIndexBuffer; // mutable so it can be
454 // created on-demand
reed@google.comac10a2d2010-12-22 21:39:39 +0000455
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000456 mutable GrVertexBuffer* fUnitSquareVertexBuffer; // mutable so it can be
457 // created on-demand
458 typedef GrDrawTarget INHERITED;
reed@google.comac10a2d2010-12-22 21:39:39 +0000459};
460
461#endif