Line data Source code
1 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /* This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this
4 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : #ifndef SCOPEDGLHELPERS_H_
7 : #define SCOPEDGLHELPERS_H_
8 :
9 : #include "GLDefs.h"
10 : #include "mozilla/UniquePtr.h"
11 :
12 : namespace mozilla {
13 : namespace gl {
14 :
15 : class GLContext;
16 :
17 : #ifdef DEBUG
18 : bool IsContextCurrent(GLContext* gl);
19 : #endif
20 :
21 : //RAII via CRTP!
22 : template <class Derived>
23 : struct ScopedGLWrapper
24 : {
25 : private:
26 : bool mIsUnwrapped;
27 :
28 : protected:
29 : GLContext* const mGL;
30 :
31 0 : explicit ScopedGLWrapper(GLContext* gl)
32 : : mIsUnwrapped(false)
33 0 : , mGL(gl)
34 : {
35 : MOZ_ASSERT(&ScopedGLWrapper<Derived>::Unwrap == &Derived::Unwrap);
36 0 : MOZ_ASSERT(&Derived::UnwrapImpl);
37 0 : MOZ_ASSERT(IsContextCurrent(mGL));
38 0 : }
39 :
40 0 : virtual ~ScopedGLWrapper() {
41 0 : if (!mIsUnwrapped)
42 0 : Unwrap();
43 0 : }
44 :
45 : public:
46 0 : void Unwrap() {
47 0 : MOZ_ASSERT(!mIsUnwrapped);
48 0 : MOZ_ASSERT(IsContextCurrent(mGL));
49 :
50 0 : Derived* derived = static_cast<Derived*>(this);
51 0 : derived->UnwrapImpl();
52 :
53 0 : mIsUnwrapped = true;
54 0 : }
55 : };
56 :
57 : // Wraps glEnable/Disable.
58 0 : struct ScopedGLState
59 : : public ScopedGLWrapper<ScopedGLState>
60 : {
61 : friend struct ScopedGLWrapper<ScopedGLState>;
62 :
63 : protected:
64 : const GLenum mCapability;
65 : bool mOldState;
66 :
67 : public:
68 : // Use |newState = true| to enable, |false| to disable.
69 : ScopedGLState(GLContext* aGL, GLenum aCapability, bool aNewState);
70 : // variant that doesn't change state; simply records existing state to be
71 : // restored by the destructor
72 : ScopedGLState(GLContext* aGL, GLenum aCapability);
73 :
74 : protected:
75 : void UnwrapImpl();
76 : };
77 :
78 : // Saves and restores with GetUserBoundFB and BindUserFB.
79 0 : struct ScopedBindFramebuffer
80 : : public ScopedGLWrapper<ScopedBindFramebuffer>
81 : {
82 : friend struct ScopedGLWrapper<ScopedBindFramebuffer>;
83 :
84 : protected:
85 : GLuint mOldReadFB;
86 : GLuint mOldDrawFB;
87 :
88 : private:
89 : void Init();
90 :
91 : public:
92 : explicit ScopedBindFramebuffer(GLContext* aGL);
93 : ScopedBindFramebuffer(GLContext* aGL, GLuint aNewFB);
94 :
95 : protected:
96 : void UnwrapImpl();
97 : };
98 :
99 0 : struct ScopedBindTextureUnit
100 : : public ScopedGLWrapper<ScopedBindTextureUnit>
101 : {
102 : friend struct ScopedGLWrapper<ScopedBindTextureUnit>;
103 :
104 : protected:
105 : GLenum mOldTexUnit;
106 :
107 : public:
108 : ScopedBindTextureUnit(GLContext* aGL, GLenum aTexUnit);
109 :
110 : protected:
111 : void UnwrapImpl();
112 : };
113 :
114 :
115 0 : struct ScopedTexture
116 : : public ScopedGLWrapper<ScopedTexture>
117 : {
118 : friend struct ScopedGLWrapper<ScopedTexture>;
119 :
120 : protected:
121 : GLuint mTexture;
122 :
123 : public:
124 : explicit ScopedTexture(GLContext* aGL);
125 0 : GLuint Texture() { return mTexture; }
126 :
127 : protected:
128 : void UnwrapImpl();
129 : };
130 :
131 :
132 0 : struct ScopedFramebuffer
133 : : public ScopedGLWrapper<ScopedFramebuffer>
134 : {
135 : friend struct ScopedGLWrapper<ScopedFramebuffer>;
136 :
137 : protected:
138 : GLuint mFB;
139 :
140 : public:
141 : explicit ScopedFramebuffer(GLContext* aGL);
142 0 : GLuint FB() { return mFB; }
143 :
144 : protected:
145 : void UnwrapImpl();
146 : };
147 :
148 :
149 0 : struct ScopedRenderbuffer
150 : : public ScopedGLWrapper<ScopedRenderbuffer>
151 : {
152 : friend struct ScopedGLWrapper<ScopedRenderbuffer>;
153 :
154 : protected:
155 : GLuint mRB;
156 :
157 : public:
158 : explicit ScopedRenderbuffer(GLContext* aGL);
159 : GLuint RB() { return mRB; }
160 :
161 : protected:
162 : void UnwrapImpl();
163 : };
164 :
165 :
166 0 : struct ScopedBindTexture
167 : : public ScopedGLWrapper<ScopedBindTexture>
168 : {
169 : friend struct ScopedGLWrapper<ScopedBindTexture>;
170 :
171 : protected:
172 : const GLenum mTarget;
173 : const GLuint mOldTex;
174 :
175 : public:
176 : ScopedBindTexture(GLContext* aGL, GLuint aNewTex,
177 : GLenum aTarget = LOCAL_GL_TEXTURE_2D);
178 :
179 : protected:
180 : void UnwrapImpl();
181 : };
182 :
183 :
184 0 : struct ScopedBindRenderbuffer
185 : : public ScopedGLWrapper<ScopedBindRenderbuffer>
186 : {
187 : friend struct ScopedGLWrapper<ScopedBindRenderbuffer>;
188 :
189 : protected:
190 : GLuint mOldRB;
191 :
192 : private:
193 : void Init();
194 :
195 : public:
196 : explicit ScopedBindRenderbuffer(GLContext* aGL);
197 :
198 : ScopedBindRenderbuffer(GLContext* aGL, GLuint aNewRB);
199 :
200 : protected:
201 : void UnwrapImpl();
202 : };
203 :
204 :
205 0 : struct ScopedFramebufferForTexture
206 : : public ScopedGLWrapper<ScopedFramebufferForTexture>
207 : {
208 : friend struct ScopedGLWrapper<ScopedFramebufferForTexture>;
209 :
210 : protected:
211 : bool mComplete; // True if the framebuffer we create is complete.
212 : GLuint mFB;
213 :
214 : public:
215 : ScopedFramebufferForTexture(GLContext* aGL, GLuint aTexture,
216 : GLenum aTarget = LOCAL_GL_TEXTURE_2D);
217 :
218 0 : bool IsComplete() const {
219 0 : return mComplete;
220 : }
221 :
222 0 : GLuint FB() const {
223 0 : MOZ_ASSERT(IsComplete());
224 0 : return mFB;
225 : }
226 :
227 : protected:
228 : void UnwrapImpl();
229 : };
230 :
231 0 : struct ScopedFramebufferForRenderbuffer
232 : : public ScopedGLWrapper<ScopedFramebufferForRenderbuffer>
233 : {
234 : friend struct ScopedGLWrapper<ScopedFramebufferForRenderbuffer>;
235 :
236 : protected:
237 : bool mComplete; // True if the framebuffer we create is complete.
238 : GLuint mFB;
239 :
240 : public:
241 : ScopedFramebufferForRenderbuffer(GLContext* aGL, GLuint aRB);
242 :
243 : bool IsComplete() const {
244 : return mComplete;
245 : }
246 :
247 0 : GLuint FB() const {
248 0 : return mFB;
249 : }
250 :
251 : protected:
252 : void UnwrapImpl();
253 : };
254 :
255 0 : struct ScopedViewportRect
256 : : public ScopedGLWrapper<ScopedViewportRect>
257 : {
258 : friend struct ScopedGLWrapper<ScopedViewportRect>;
259 :
260 : protected:
261 : GLint mSavedViewportRect[4];
262 :
263 : public:
264 : ScopedViewportRect(GLContext* aGL, GLint x, GLint y, GLsizei width, GLsizei height);
265 :
266 : protected:
267 : void UnwrapImpl();
268 : };
269 :
270 0 : struct ScopedScissorRect
271 : : public ScopedGLWrapper<ScopedScissorRect>
272 : {
273 : friend struct ScopedGLWrapper<ScopedScissorRect>;
274 :
275 : protected:
276 : GLint mSavedScissorRect[4];
277 :
278 : public:
279 : ScopedScissorRect(GLContext* aGL, GLint x, GLint y, GLsizei width, GLsizei height);
280 : explicit ScopedScissorRect(GLContext* aGL);
281 :
282 : protected:
283 : void UnwrapImpl();
284 : };
285 :
286 0 : struct ScopedVertexAttribPointer
287 : : public ScopedGLWrapper<ScopedVertexAttribPointer>
288 : {
289 : friend struct ScopedGLWrapper<ScopedVertexAttribPointer>;
290 :
291 : protected:
292 : GLuint mAttribIndex;
293 : GLint mAttribEnabled;
294 : GLint mAttribSize;
295 : GLint mAttribStride;
296 : GLint mAttribType;
297 : GLint mAttribNormalized;
298 : GLint mAttribBufferBinding;
299 : void* mAttribPointer;
300 : GLuint mBoundBuffer;
301 :
302 : public:
303 : ScopedVertexAttribPointer(GLContext* aGL, GLuint index, GLint size, GLenum type, realGLboolean normalized,
304 : GLsizei stride, GLuint buffer, const GLvoid* pointer);
305 : explicit ScopedVertexAttribPointer(GLContext* aGL, GLuint index);
306 :
307 : protected:
308 : void WrapImpl(GLuint index);
309 : void UnwrapImpl();
310 : };
311 :
312 : struct ScopedGLDrawState
313 : {
314 : explicit ScopedGLDrawState(GLContext* gl);
315 : ~ScopedGLDrawState();
316 :
317 : GLuint boundProgram;
318 : GLuint boundBuffer;
319 :
320 : ScopedGLState blend;
321 : ScopedGLState cullFace;
322 : ScopedGLState depthTest;
323 : ScopedGLState dither;
324 : ScopedGLState polyOffsFill;
325 : ScopedGLState sampleAToC;
326 : ScopedGLState sampleCover;
327 : ScopedGLState scissor;
328 : ScopedGLState stencil;
329 :
330 : GLuint maxAttrib;
331 : UniquePtr<GLint[]> attrib_enabled;
332 : GLint attrib0_size;
333 : GLint attrib0_stride;
334 : GLint attrib0_type;
335 : GLint attrib0_normalized;
336 : GLint attrib0_bufferBinding;
337 : void* attrib0_pointer;
338 :
339 : realGLboolean colorMask[4];
340 : GLint viewport[4];
341 : GLint scissorBox[4];
342 : GLContext* const mGL;
343 : };
344 :
345 0 : struct ScopedPackState
346 : : public ScopedGLWrapper<ScopedPackState>
347 : {
348 : friend struct ScopedGLWrapper<ScopedPackState>;
349 :
350 : protected:
351 : GLint mAlignment;
352 :
353 : GLuint mPixelBuffer;
354 : GLint mRowLength;
355 : GLint mSkipPixels;
356 : GLint mSkipRows;
357 :
358 : public:
359 : explicit ScopedPackState(GLContext* gl);
360 :
361 : protected:
362 : void UnwrapImpl();
363 : };
364 :
365 0 : struct ResetUnpackState
366 : : public ScopedGLWrapper<ResetUnpackState>
367 : {
368 : friend struct ScopedGLWrapper<ResetUnpackState>;
369 :
370 : protected:
371 : GLuint mAlignment;
372 :
373 : GLuint mPBO;
374 : GLuint mRowLength;
375 : GLuint mImageHeight;
376 : GLuint mSkipPixels;
377 : GLuint mSkipRows;
378 : GLuint mSkipImages;
379 :
380 : public:
381 : explicit ResetUnpackState(GLContext* gl);
382 :
383 : protected:
384 : void UnwrapImpl();
385 : };
386 :
387 0 : struct ScopedBindPBO final
388 : : public ScopedGLWrapper<ScopedBindPBO>
389 : {
390 : friend struct ScopedGLWrapper<ScopedBindPBO>;
391 :
392 : protected:
393 : const GLenum mTarget;
394 : const GLuint mPBO;
395 :
396 : public:
397 : ScopedBindPBO(GLContext* gl, GLenum target);
398 :
399 : protected:
400 : void UnwrapImpl();
401 : };
402 :
403 : } /* namespace gl */
404 : } /* namespace mozilla */
405 :
406 : #endif /* SCOPEDGLHELPERS_H_ */
|