blob: edd38ecb430d346cf1203679790114cdce0f253a [file] [log] [blame]
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +00001//
2// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
3// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6
7// Renderbuffer.cpp: the gl::Renderbuffer class and its derived classes
8// Colorbuffer, Depthbuffer and Stencilbuffer. Implements GL renderbuffer
9// objects and related functionality. [OpenGL ES 2.0.24] section 4.4.3 page 108.
10
daniel@transgaming.combbf56f72010-04-20 18:52:13 +000011#include "libGLESv2/Renderbuffer.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000012
daniel@transgaming.combbf56f72010-04-20 18:52:13 +000013#include "libGLESv2/main.h"
14#include "libGLESv2/utilities.h"
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000015
16namespace gl
17{
daniel@transgaming.com092bd482010-05-12 03:39:36 +000018unsigned int Renderbuffer::mCurrentSerial = 1;
19
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000020Renderbuffer::Renderbuffer()
21{
22 mWidth = 0;
23 mHeight = 0;
daniel@transgaming.com4901fca2010-04-20 18:52:41 +000024 mFormat = GL_RGBA4; // default format, needs to be one of the expected renderbuffer formats
daniel@transgaming.com092bd482010-05-12 03:39:36 +000025 mSerial = issueSerial();
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000026}
27
28Renderbuffer::~Renderbuffer()
29{
30}
31
32bool Renderbuffer::isColorbuffer()
33{
34 return false;
35}
36
37bool Renderbuffer::isDepthbuffer()
38{
39 return false;
40}
41
42bool Renderbuffer::isStencilbuffer()
43{
44 return false;
45}
46
47IDirect3DSurface9 *Renderbuffer::getRenderTarget()
48{
49 return NULL;
50}
51
52IDirect3DSurface9 *Renderbuffer::getDepthStencil()
53{
54 return NULL;
55}
56
57int Renderbuffer::getWidth()
58{
59 return mWidth;
60}
61
62int Renderbuffer::getHeight()
63{
64 return mHeight;
65}
66
daniel@transgaming.com866f3182010-05-20 19:28:22 +000067void Renderbuffer::setSize(int width, int height)
68{
69 mWidth = width;
70 mHeight = height;
71}
72
73
daniel@transgaming.com4901fca2010-04-20 18:52:41 +000074GLenum Renderbuffer::getFormat()
75{
76 return mFormat;
77}
78
daniel@transgaming.com092bd482010-05-12 03:39:36 +000079unsigned int Renderbuffer::getSerial() const
80{
81 return mSerial;
82}
83
84unsigned int Renderbuffer::issueSerial()
85{
86 return mCurrentSerial++;
87}
88
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000089Colorbuffer::Colorbuffer(IDirect3DSurface9 *renderTarget) : mRenderTarget(renderTarget)
90{
91 if (renderTarget)
92 {
93 renderTarget->AddRef();
94
95 D3DSURFACE_DESC description;
96 renderTarget->GetDesc(&description);
97
daniel@transgaming.com866f3182010-05-20 19:28:22 +000098 setSize(description.Width, description.Height);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +000099 }
daniel@transgaming.com092bd482010-05-12 03:39:36 +0000100
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000101}
102
daniel@transgaming.com70d312a2010-04-20 18:52:38 +0000103Colorbuffer::Colorbuffer(int width, int height, GLenum format)
104{
105 IDirect3DDevice9 *device = getDevice();
106
107 mRenderTarget = NULL;
108 HRESULT result = device->CreateRenderTarget(width, height, es2dx::ConvertRenderbufferFormat(format),
109 D3DMULTISAMPLE_NONE, 0, FALSE, &mRenderTarget, NULL);
110
111 if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
112 {
113 error(GL_OUT_OF_MEMORY);
114
115 return;
116 }
117
118 ASSERT(SUCCEEDED(result));
119
120 if (mRenderTarget)
121 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000122 setSize(width, height);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000123 mFormat = format;
daniel@transgaming.com70d312a2010-04-20 18:52:38 +0000124 }
125 else
126 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000127 setSize(0, 0);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000128 mFormat = GL_RGBA4;
daniel@transgaming.com70d312a2010-04-20 18:52:38 +0000129 }
130}
131
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000132Colorbuffer::~Colorbuffer()
133{
134 if (mRenderTarget)
135 {
136 mRenderTarget->Release();
137 }
138}
139
140bool Colorbuffer::isColorbuffer()
141{
142 return true;
143}
144
145GLuint Colorbuffer::getRedSize()
146{
147 if (mRenderTarget)
148 {
149 D3DSURFACE_DESC description;
150 mRenderTarget->GetDesc(&description);
151
152 return es2dx::GetRedSize(description.Format);
153 }
154
155 return 0;
156}
157
158GLuint Colorbuffer::getGreenSize()
159{
160 if (mRenderTarget)
161 {
162 D3DSURFACE_DESC description;
163 mRenderTarget->GetDesc(&description);
164
165 return es2dx::GetGreenSize(description.Format);
166 }
167
168 return 0;
169}
170
171GLuint Colorbuffer::getBlueSize()
172{
173 if (mRenderTarget)
174 {
175 D3DSURFACE_DESC description;
176 mRenderTarget->GetDesc(&description);
177
178 return es2dx::GetBlueSize(description.Format);
179 }
180
181 return 0;
182}
183
184GLuint Colorbuffer::getAlphaSize()
185{
186 if (mRenderTarget)
187 {
188 D3DSURFACE_DESC description;
189 mRenderTarget->GetDesc(&description);
190
191 return es2dx::GetAlphaSize(description.Format);
192 }
193
194 return 0;
195}
196
197IDirect3DSurface9 *Colorbuffer::getRenderTarget()
198{
199 return mRenderTarget;
200}
201
202Depthbuffer::Depthbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthStencil)
203{
204 if (depthStencil)
205 {
206 depthStencil->AddRef();
207
208 D3DSURFACE_DESC description;
209 depthStencil->GetDesc(&description);
210
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000211 setSize(description.Width, description.Height);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000212 mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
213 // will expect one of the valid renderbuffer formats for use in
214 // glRenderbufferStorage
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000215 }
216}
217
218Depthbuffer::Depthbuffer(int width, int height)
219{
220 IDirect3DDevice9 *device = getDevice();
221
222 mDepthStencil = NULL;
223 HRESULT result = device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, D3DMULTISAMPLE_NONE, 0, FALSE, &mDepthStencil, 0);
224
225 if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
226 {
227 error(GL_OUT_OF_MEMORY);
228
229 return;
230 }
231
232 ASSERT(SUCCEEDED(result));
233
234 if (mDepthStencil)
235 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000236 setSize(width, height);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000237 mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
238 // will expect one of the valid renderbuffer formats for use in
239 // glRenderbufferStorage
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000240 }
241 else
242 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000243 setSize(0, 0);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000244 mFormat = GL_RGBA4; //default format
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000245 }
246}
247
248Depthbuffer::~Depthbuffer()
249{
250 if (mDepthStencil)
251 {
252 mDepthStencil->Release();
253 }
254}
255
256bool Depthbuffer::isDepthbuffer()
257{
258 return true;
259}
260
261GLuint Depthbuffer::getDepthSize()
262{
263 if (mDepthStencil)
264 {
265 D3DSURFACE_DESC description;
266 mDepthStencil->GetDesc(&description);
267
daniel@transgaming.com7a2c2802010-03-16 06:23:33 +0000268 return es2dx::GetDepthSize(description.Format);
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000269 }
270
271 return 0;
272}
273
274IDirect3DSurface9 *Depthbuffer::getDepthStencil()
275{
276 return mDepthStencil;
277}
278
279Stencilbuffer::Stencilbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthStencil)
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +0000280{
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000281 if (depthStencil)
282 {
283 depthStencil->AddRef();
284
285 D3DSURFACE_DESC description;
286 depthStencil->GetDesc(&description);
287
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000288 setSize(description.Width, description.Height);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000289 mFormat = GL_STENCIL_INDEX8; // If the renderbuffer parameters are queried, the calling function
290 // will expect one of the valid renderbuffer formats for use in
291 // glRenderbufferStorage
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000292 }
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +0000293}
294
295Stencilbuffer::Stencilbuffer(int width, int height)
296{
297 IDirect3DDevice9 *device = getDevice();
298
299 mDepthStencil = NULL;
300 HRESULT result = device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, D3DMULTISAMPLE_NONE, 0, FALSE, &mDepthStencil, 0);
301
302 if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
303 {
304 error(GL_OUT_OF_MEMORY);
305
306 return;
307 }
308
309 ASSERT(SUCCEEDED(result));
310
311 if (mDepthStencil)
312 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000313 setSize(width, height);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000314 mFormat = GL_STENCIL_INDEX8; // If the renderbuffer parameters are queried, the calling function
315 // will expect one of the valid renderbuffer formats for use in
316 // glRenderbufferStorage
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +0000317 }
318 else
319 {
daniel@transgaming.com866f3182010-05-20 19:28:22 +0000320 setSize(0, 0);
daniel@transgaming.com4901fca2010-04-20 18:52:41 +0000321 mFormat = GL_RGBA4; //default format
daniel@transgaming.com4a9d65c2010-03-08 21:30:56 +0000322 }
323}
daniel@transgaming.com4f39fd92010-03-08 20:26:45 +0000324
325Stencilbuffer::~Stencilbuffer()
326{
327 if (mDepthStencil)
328 {
329 mDepthStencil->Release();
330 }
331}
332
333GLuint Stencilbuffer::getStencilSize()
334{
335 if (mDepthStencil)
336 {
337 D3DSURFACE_DESC description;
338 mDepthStencil->GetDesc(&description);
339
340 return es2dx::GetStencilSize(description.Format);
341 }
342
343 return 0;
344}
345
346bool Stencilbuffer::isStencilbuffer()
347{
348 return true;
349}
350
351IDirect3DSurface9 *Stencilbuffer::getDepthStencil()
352{
353 return mDepthStencil;
354}
355}