Oolite 1.91.0.7644-241112-7f5034b
Loading...
Searching...
No Matches
OOOpenGLStateManager.m
Go to the documentation of this file.
1/*
2
3OOOpenGLStateManager.m
4
5Implementation of OOSetOpenGLState()/OOVerifyOpenGLState().
6
7
8Oolite
9Copyright (C) 2004-2013 Giles C Williams and contributors
10
11This program is free software; you can redistribute it and/or
12modify it under the terms of the GNU General Public License
13as published by the Free Software Foundation; either version 2
14of the License, or (at your option) any later version.
15
16This program is distributed in the hope that it will be useful,
17but WITHOUT ANY WARRANTY; without even the implied warranty of
18MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19GNU General Public License for more details.
20
21You should have received a copy of the GNU General Public License
22along with this program; if not, write to the Free Software
23Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
24MA 02110-1301, USA.
25
26*/
27
28#import "OOOpenGL.h"
29#import "OOLogging.h"
30#import "OOMaths.h"
31#import "OOMacroOpenGL.h"
34
35/* DESIGN NOTES
36
37 The state manager is heavily based on macro metaprogramming, to avoid copy-
38 and-paste errors. The state it manages is defined in OOOpenGLStates.tbl,
39 which is included each time something needs to be done for each state item
40 (currently six times in total). The exception is the GL blend mode, which
41 is represented by two variables but set with a single glBlendFunc() call;
42 this needs to be managed separately.
43
44 For the meanings of the different ITEM_FOO macro used, see OOOpenGLStates.tbl.
45
46 The states are defined as structs but referred to by index so that the
47 definitions are all in one place. This somewhat reduces the chance of
48 missing one when updating OOOpenGLStates.tbl. The actual definitions are
49 at the bottom of this file.
50*/
51
52
53typedef enum
54{
55 kStateFalse = false,
56 kStateTrue = true,
59
60
61typedef struct
62{
63 const char *name;
64
65 #define ITEM_STATEFLAG(NAME) StateFlag NAME
66 #define ITEM_CLIENTSTATEFLAG(NAME) bool NAME
67 #define ITEM_SPECIAL(NAME, TYPE, _) TYPE NAME
68 #define ITEM_INT(NAME) GLint NAME
69
70 #include "OOOpenGLStates.tbl"
71
72 // These require extra-special handling, because they're set with one function.
73 GLint BLEND_SRC;
74 GLint BLEND_DST;
75
76 #undef ITEM_STATEFLAG
77 #undef ITEM_CLIENTSTATEFLAG
78 #undef ITEM_SPECIAL
79 #undef ITEM_INT
81
82
83static const OOOpenGLState kStandardStates[OPENGL_STATE_INTERNAL_USE_ONLY + 1];
84
86
87
88/* SwitchOpenGLStateInternal(sourceState, targetState)
89
90 Applies the differences between sourceState and targetState. It is assumed
91 that sourceState accurately reflects the current state.
92*/
93static void SwitchOpenGLStateInternal(const OOOpenGLState *sourceState, const OOOpenGLState *targetState) NONNULL_FUNC;
94
95
96/* Accessors
97
98 These functions and macros are used to read and write ITEM_SPECIAL state
99 items. The GetState_ accessors are used only in debug mode, while the
100 SetState_ acccessors are used in either mode.
101*/
102#ifndef NDEBUG
103static inline bool GetState_DEPTH_WRITEMASK(void)
104{
106
107 GLboolean value;
108 OOGL(glGetBooleanv(GL_DEPTH_WRITEMASK, &value));
109 return value;
110}
111#endif
112
113#define SetState_DEPTH_WRITEMASK(VALUE) OOGL(glDepthMask(VALUE))
114
115#define SetState_SHADE_MODEL(VALUE) OOGL(glShadeModel(VALUE))
116
117#ifndef NDEBUG
118static inline GLenum GetState_TEXTURE_ENV_MODE(void)
119{
121
122 GLint value;
123 OOGL(glGetTexEnviv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, &value));
124 return value;
125}
126#endif
127
128#define SetState_TEXTURE_ENV_MODE(VALUE) OOGL(glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, VALUE))
129
130#if OO_MULTITEXTURE
131#ifndef NDEBUG
132static inline GLenum GetState_ACTIVE_TEXTURE(void)
133{
135
136 GLint value;
137 OOGL(glGetIntegerv(GL_ACTIVE_TEXTURE_ARB, &value));
138 return value;
139}
140#endif
141
142#define SetState_ACTIVE_TEXTURE(VALUE) OOGL(glActiveTextureARB(VALUE))
143
144#ifndef NDEBUG
145static inline GLenum GetState_CLIENT_ACTIVE_TEXTURE(void)
146{
148
149 GLint value;
150 OOGL(glGetIntegerv(GL_CLIENT_ACTIVE_TEXTURE_ARB, &value));
151 return value;
152}
153#endif
154
155#define SetState_CLIENT_ACTIVE_TEXTURE(VALUE) OOGL(glClientActiveTextureARB(VALUE))
156
157#else
158static inline GLenum GetState_ACTIVE_TEXTURE(void) {}
159static inline void SetState_ACTIVE_TEXTURE(GLenum value) {}
160static inline GLenum GetState_CLIENT_ACTIVE_TEXTURE(void) {}
161static inline void SetState_CLIENT_ACTIVE_TEXTURE(GLenum value) {}
162#endif
163
164static inline void SetState_CULL_FACE_MODE(GLint value)
165{
167
168 OOGL(glCullFace(value));
169}
170
171#define SetState_FRONT_FACE(VALUE) OOGL(glFrontFace(VALUE))
172
173
174#if OO_GL_STATE_VERIFICATION
175/* Debug mode implementation.
176*/
177
178static NSString * const kOOLogOpenGLVerifyDump = @"rendering.opengl.state";
179
180
181/*
182 VerifyOpenGLStateInternal(caller, nominalCaller, line)
183
184 Tests whether the current OpenGL state matches the last set nominal state.
185 If not, it logs the differences, then reverts to the last set nominal state
186 (using SwitchOpenGLStateInternal()).
187*/
188static void VerifyOpenGLStateInternal(const char *caller, const char *nominalCaller, unsigned line) NONNULL_FUNC;
189
190
191/* GetCurrentOpenGLState(state)
192
193 Retrieves the current OpenGL state.
194*/
196
197
198/* StatesEqual(a, b)
199
200 Test whether two states are identical.
201*/
202static bool StatesEqual(const OOOpenGLState *a, const OOOpenGLState *b) NONNULL_FUNC;
203
204
205#if OO_CHECK_GL_HEAVY
206/* OOGLNoteCurrentFunction(function, line)
207
208 If OO_GL_STATE_VERIFICATION && OO_CHECK_GL_HEAVY, OOGL() calls
209 OOGLNoteCurrentFunction() to help us keep track of where OpenGL calls have
210 been made recently. The penultimate seen function is logged when we come
211 across a state error, which is occasionally actually helpful.
212*/
213
214static const char *sLatestFunction = "<none yet>";
215static unsigned sLatestLine;
216static const char *sPreviousFunction = "<none yet>";
217static unsigned sPreviousLine;
218static bool sGLFunctionTracking = true;
219
220void OOGLNoteCurrentFunction(const char *function, unsigned line)
221{
222 if (sGLFunctionTracking)
223 {
224 if (function != sLatestFunction)
225 {
226 sPreviousFunction = sLatestFunction;
227 sPreviousLine = sLatestLine;
228 sLatestFunction = function;
229 }
230 sLatestLine = line;
231 }
232}
233
234
235/* SetFunctionTracking()
236
237 Enable or disable OOGLNoteCurrentFunction(). It is disabled within the
238 state manager implementation.
239*/
240static inline void SetFunctionTracking(bool value)
241{
242 sGLFunctionTracking = value;
243}
244
245#else
246
247static inline void OOGLNoteCurrentFunction(const char *function, unsigned line) {}
248static inline void SetFunctionTracking(bool value) {}
249
250#endif
251
252
253void OOSetOpenGLState_(OOOpenGLStateID state, const char *function, unsigned line)
254{
255 NSCParameterAssert((unsigned)state < OPENGL_STATE_INTERNAL_USE_ONLY);
256
257 OOGLNoteCurrentFunction(function, line);
258 SetFunctionTracking(false);
259
260 VerifyOpenGLStateInternal("OOSetOpenGLState", function, line);
261
262 if (state != sCurrentStateID)
263 {
265 sCurrentStateID = state;
266 }
267
269}
270
271
272void OOVerifyOpenGLState_(const char *function, unsigned line)
273{
274 OOGLNoteCurrentFunction(function, line);
275 SetFunctionTracking(false);
276
277 VerifyOpenGLStateInternal("OOVerifyOpenGLState", function, line);
278
280}
281
282
284{
285 static const char *name = "<current state>";
286
287 NSCParameterAssert(state != NULL);
289 memset(state, 0, sizeof *state);
290 state->name = name;
291
292 #define ITEM_STATEFLAG(NAME) OOGL(state->NAME = glIsEnabled(GL_##NAME))
293 #define ITEM_CLIENTSTATEFLAG(NAME) OOGL(state->NAME = glIsEnabled(GL_##NAME))
294 #define ITEM_SPECIAL(NAME, _, __) state->NAME = GetState_##NAME()
295 #define ITEM_INT(NAME) OOGL(glGetIntegerv(GL_##NAME, &state->NAME))
296
297 #include "OOOpenGLStates.tbl"
298
299 OOGL(glGetIntegerv(GL_BLEND_SRC, &state->BLEND_SRC));
300 OOGL(glGetIntegerv(GL_BLEND_DST, &state->BLEND_DST));
301
302 #undef ITEM_STATEFLAG
303 #undef ITEM_CLIENTSTATEFLAG
304 #undef ITEM_SPECIAL
305 #undef ITEM_INT
306}
307
308
309static bool StatesEqual(const OOOpenGLState *a, const OOOpenGLState *b)
310{
311 NSCParameterAssert(a != NULL && b != NULL);
312
313 #define ITEM_STATEFLAG(NAME) do { if (a->NAME != b->NAME && a->NAME != kStateMaybe && b->NAME != kStateMaybe) return false; } while (0)
314 #define ITEM_CLIENTSTATEFLAG(NAME) do { if (a->NAME != b->NAME) return false; } while (0)
315 #define ITEM_SPECIAL(NAME, _, __) do { if (a->NAME != b->NAME) return false; } while (0)
316 #define ITEM_INT(NAME) do { if (a->NAME != b->NAME) return false; } while (0)
317
318 #include "OOOpenGLStates.tbl"
319
320 #undef ITEM_STATEFLAG
321 #undef ITEM_CLIENTSTATEFLAG
322 #undef ITEM_SPECIAL
323 #undef ITEM_INT
324
325 return true;
326}
327
328
329static void VerifyOpenGLStateInternal(const char *caller, const char *nominalCaller, unsigned line)
330{
331 OOOpenGLState currentState;
332 GetCurrentOpenGLState(&currentState);
333
334 NSCParameterAssert(sCurrentStateID <= OPENGL_STATE_INTERNAL_USE_ONLY);
335
336 const OOOpenGLState *expectedState = &kStandardStates[sCurrentStateID];
337
338 if (!StatesEqual(&currentState, expectedState))
339 {
341 {
342 OOLog(kOOLogOpenGLVerifyDump, @"Incorrect OpenGL state in %s (line %u)->%s", nominalCaller, line, caller);
343#if OO_CHECK_GL_HEAVY
344 OOLog(kOOLogOpenGLVerifyDump, @"Previous OpenGL-using function: %s (line %u)", sPreviousFunction, sPreviousLine);
345#endif
346 OOLog(kOOLogOpenGLVerifyDump, @"Expected previous state: %s", expectedState->name);
347
348 OOLogIndent();
349
350 #define TEST_ITEM(NAME_, DISP_) \
351 if (currentState.NAME_ != expectedState->NAME_) \
352 { \
353 OOLog(kOOLogOpenGLVerifyDump, @"GL_%@ should be %@ but is %@.", @#NAME_, DISP_(expectedState->NAME_), DISP_(currentState.NAME_)); \
354 }
355
356 #define ITEM_STATEFLAG(NAME) if (expectedState->NAME != kStateMaybe) { TEST_ITEM(NAME, OOGLFlagToString) }
357 #define ITEM_CLIENTSTATEFLAG(NAME) TEST_ITEM(NAME, OOGLFlagToString)
358 #define ITEM_SPECIAL(NAME, _, __) TEST_ITEM(NAME, OOGLFlagToString)
359 #define ITEM_INT(NAME) TEST_ITEM(NAME, OOGLEnumToString)
360
361 #include "OOOpenGLStates.tbl"
362
363 if (currentState.BLEND_SRC != expectedState->BLEND_SRC || currentState.BLEND_DST != expectedState->BLEND_DST)
364 {
365 OOLog(kOOLogOpenGLVerifyDump, @"GL blend mode should be %@, %@ but is %@, %@.", OOGLEnumToString(expectedState->BLEND_SRC), OOGLEnumToString(expectedState->BLEND_DST), OOGLEnumToString(currentState.BLEND_SRC), OOGLEnumToString(currentState.BLEND_DST));
366 }
367
368 #undef ITEM_STATEFLAG
369 #undef ITEM_CLIENTSTATEFLAG
370 #undef ITEM_SPECIAL
371 #undef ITEM_INT
372
373 #undef TEST_ITEM
374
375 OOLogOutdent();
376 }
377
378 SwitchOpenGLStateInternal(&currentState, expectedState);
379 }
380}
381
382#else // OO_GL_STATE_VERIFICATION
383/* Non-debug mode implementation.
384
385 OOSetOpenGLState() performs a switch from the previous nominal state to the
386 new nominal state, without checking that the previous nominal state matches
387 the actual state. OOVerifyOpenGLState is a do-nothing macro.
388*/
389
391{
392 NSCParameterAssert((unsigned)state < OPENGL_STATE_INTERNAL_USE_ONLY);
393
394 if (state != sCurrentStateID)
395 {
397 sCurrentStateID = state;
398 }
399}
400
401#endif // OO_GL_STATE_VERIFICATION
402
403
404static void SwitchOpenGLStateInternal(const OOOpenGLState *sourceState, const OOOpenGLState *targetState)
405{
406 NSCParameterAssert(sourceState != NULL && targetState != NULL);
408
409 #define ITEM_STATEFLAG(NAME) \
410 if (sourceState->NAME != targetState->NAME && sourceState->NAME != kStateMaybe && targetState->NAME != kStateMaybe) \
411 { \
412 if (targetState->NAME) \
413 { \
414 OOGL(glEnable(GL_##NAME)); \
415 } \
416 else \
417 { \
418 OOGL(glDisable(GL_##NAME)); \
419 } \
420 }
421 #define ITEM_CLIENTSTATEFLAG(NAME) \
422 if (sourceState->NAME != targetState->NAME) \
423 { \
424 if (targetState->NAME) \
425 { \
426 OOGL(glEnableClientState(GL_##NAME)); \
427 } \
428 else \
429 { \
430 OOGL(glDisableClientState(GL_##NAME)); \
431 } \
432 }
433 #define ITEM_SPECIAL(NAME, TYPE, _) \
434 if (sourceState->NAME != targetState->NAME) \
435 { \
436 SetState_##NAME(targetState->NAME); \
437 }
438 #define ITEM_INT(NAME) \
439 if (sourceState->NAME != targetState->NAME) \
440 { \
441 SetState_##NAME(targetState->NAME); \
442 }
443
444 #include "OOOpenGLStates.tbl"
445
446 /* some implementations, in non-shader mode, seem to throw out/reset
447 * BlendFunc if Blend is disabled. Therefore, if coming from Blend=false
448 * always reset the blend function even if this should be unnecessary
449 * CIM: 3/1/13 */
450 if (sourceState->BLEND_SRC != targetState->BLEND_SRC || sourceState->BLEND_DST != targetState->BLEND_DST || !sourceState->BLEND)
451 {
452 OOGL(glBlendFunc(targetState->BLEND_SRC, targetState->BLEND_DST));
453 }
454
455 #undef ITEM_STATEFLAG
456 #undef ITEM_CLIENTSTATEFLAG
457 #undef ITEM_SPECIAL
458 #undef ITEM_INT
459}
460
461
463{
464 // State has been reset behind our backs, so to speak; don't verify.
466}
467
468
469// The state definitions.
470static const OOOpenGLState kStandardStates[OPENGL_STATE_INTERNAL_USE_ONLY + 1] =
471{
472 [OPENGL_STATE_INTERNAL_USE_ONLY] =
473 {
474 .name = "<canonical initial state>",
475 .LIGHTING = false,
476 .LIGHT0 = false,
477 .LIGHT1 = false,
478 .LIGHT2 = false,
479 .LIGHT3 = false,
480 .LIGHT4 = false,
481 .LIGHT5 = false,
482 .LIGHT6 = false,
483 .LIGHT7 = false,
484 .TEXTURE_2D = false,
485 .COLOR_MATERIAL = false,
486 .SHADE_MODEL = GL_SMOOTH,
487 .TEXTURE_ENV_MODE = GL_MODULATE,
488 .ACTIVE_TEXTURE = GL_TEXTURE0,
489 .CLIENT_ACTIVE_TEXTURE = GL_TEXTURE0,
490 .BLEND = false,
491 .BLEND_SRC = GL_ONE,
492 .BLEND_DST = GL_ZERO,
493 .FOG = false,
494 .VERTEX_ARRAY = false,
495 .NORMAL_ARRAY = false,
496 .COLOR_ARRAY = false,
497 .INDEX_ARRAY = false,
498 .TEXTURE_COORD_ARRAY = false,
499 .EDGE_FLAG_ARRAY = false,
500 .NORMALIZE = false,
501 .RESCALE_NORMAL = false,
502 .DEPTH_TEST = false,
503 .DEPTH_WRITEMASK = true,
504 .CULL_FACE = false,
505 .CULL_FACE_MODE = GL_BACK,
506 .FRONT_FACE = GL_CCW,
507 },
508 [OPENGL_STATE_OPAQUE] =
509 {
510 .name = "OPENGL_STATE_OPAQUE",
511 .LIGHTING = true,
512 .LIGHT0 = kStateMaybe,
513 /* FIXME: in shader mode, these should not be kStateMaybe, but
514 * false for 0 and true for 1. On the other hand, in shader mode
515 * these settings are supposed to be irrelevant. */
516 .LIGHT1 = kStateMaybe, // FIXME: see above
517 .LIGHT2 = false,
518 .LIGHT3 = false,
519 .LIGHT4 = false,
520 .LIGHT5 = false,
521 .LIGHT6 = false,
522 .LIGHT7 = false,
523 .TEXTURE_2D = true,
524 .COLOR_MATERIAL = false,
525 .SHADE_MODEL = GL_SMOOTH,
526 .TEXTURE_ENV_MODE = GL_MODULATE,
527 .ACTIVE_TEXTURE = GL_TEXTURE0,
528 .CLIENT_ACTIVE_TEXTURE = GL_TEXTURE0,
529 .BLEND = false,
530 .BLEND_SRC = GL_SRC_ALPHA,
531 .BLEND_DST = GL_ONE_MINUS_SRC_ALPHA,
532 .FOG = kStateMaybe,
533 .VERTEX_ARRAY = true,
534 .NORMAL_ARRAY = true,
535 .COLOR_ARRAY = false,
536 .INDEX_ARRAY = false,
537 .TEXTURE_COORD_ARRAY = false,
538 .EDGE_FLAG_ARRAY = false,
539 .NORMALIZE = false,
540 .RESCALE_NORMAL = false,
541 .DEPTH_TEST = true,
542 .DEPTH_WRITEMASK = true,
543 .CULL_FACE = true,
544 .CULL_FACE_MODE = GL_BACK,
545 .FRONT_FACE = GL_CCW,
546 },
547 [OPENGL_STATE_TRANSLUCENT_PASS] =
548 {
549 .name = "OPENGL_STATE_TRANSLUCENT_PASS",
550 .LIGHTING = false,
551 .LIGHT0 = kStateMaybe, // FIXME: see above
552 .LIGHT1 = kStateMaybe, // FIXME: see above
553 .LIGHT2 = false,
554 .LIGHT3 = false,
555 .LIGHT4 = false,
556 .LIGHT5 = false,
557 .LIGHT6 = false,
558 .LIGHT7 = false,
559 .TEXTURE_2D = false,
560 .COLOR_MATERIAL = false,
561 .SHADE_MODEL = GL_SMOOTH,
562 .TEXTURE_ENV_MODE = GL_MODULATE,
563 .ACTIVE_TEXTURE = GL_TEXTURE0,
564 .CLIENT_ACTIVE_TEXTURE = GL_TEXTURE0,
565 .BLEND = false,
566 .BLEND_SRC = GL_SRC_ALPHA,
567 .BLEND_DST = GL_ONE_MINUS_SRC_ALPHA,
568 .FOG = kStateMaybe,
569 .VERTEX_ARRAY = false,
570 .NORMAL_ARRAY = false,
571 .COLOR_ARRAY = false,
572 .INDEX_ARRAY = false,
573 .TEXTURE_COORD_ARRAY = false,
574 .EDGE_FLAG_ARRAY = false,
575 .NORMALIZE = false,
576 .RESCALE_NORMAL = false,
577 .DEPTH_TEST = true,
578 .DEPTH_WRITEMASK = false,
579 .CULL_FACE = true,
580 .CULL_FACE_MODE = GL_BACK,
581 .FRONT_FACE = GL_CCW,
582 },
583 [OPENGL_STATE_ADDITIVE_BLENDING] =
584 {
585 .name = "OPENGL_STATE_ADDITIVE_BLENDING",
586 .LIGHTING = false,
587 .LIGHT0 = kStateMaybe, // FIXME: see above
588 .LIGHT1 = kStateMaybe, // FIXME: see above
589 .LIGHT2 = false,
590 .LIGHT3 = false,
591 .LIGHT4 = false,
592 .LIGHT5 = false,
593 .LIGHT6 = false,
594 .LIGHT7 = false,
595 .TEXTURE_2D = false,
596 .COLOR_MATERIAL = false,
597 .SHADE_MODEL = GL_SMOOTH,
598 .TEXTURE_ENV_MODE = GL_MODULATE, // Should be GL_BLEND?
599 .ACTIVE_TEXTURE = GL_TEXTURE0,
600 .CLIENT_ACTIVE_TEXTURE = GL_TEXTURE0,
601 .BLEND = true,
602 .BLEND_SRC = GL_SRC_ALPHA,
603 .BLEND_DST = GL_ONE,
604 .FOG = kStateMaybe,
605 .VERTEX_ARRAY = true,
606 .NORMAL_ARRAY = false,
607 .COLOR_ARRAY = false,
608 .INDEX_ARRAY = false,
609 .TEXTURE_COORD_ARRAY = false,
610 .EDGE_FLAG_ARRAY = false,
611 .NORMALIZE = false,
612 .RESCALE_NORMAL = false,
613 .DEPTH_TEST = true,
614 .DEPTH_WRITEMASK = false,
615 .CULL_FACE = false,
616 .CULL_FACE_MODE = GL_BACK,
617 .FRONT_FACE = GL_CCW,
618 },
619 [OPENGL_STATE_OVERLAY] =
620 {
621 .name = "OPENGL_STATE_OVERLAY",
622 .LIGHTING = false,
623 .LIGHT0 = kStateMaybe, // FIXME: see above
624 .LIGHT1 = kStateMaybe, // FIXME: see above
625 .LIGHT2 = false,
626 .LIGHT3 = false,
627 .LIGHT4 = false,
628 .LIGHT5 = false,
629 .LIGHT6 = false,
630 .LIGHT7 = false,
631 .TEXTURE_2D = false,
632 .COLOR_MATERIAL = false,
633 .SHADE_MODEL = GL_SMOOTH,
634 .TEXTURE_ENV_MODE = GL_MODULATE,
635 .ACTIVE_TEXTURE = GL_TEXTURE0,
636 .CLIENT_ACTIVE_TEXTURE = GL_TEXTURE0,
637 .BLEND = true,
638 .BLEND_SRC = GL_SRC_ALPHA,
639 .BLEND_DST = GL_ONE_MINUS_SRC_ALPHA,
640 .FOG = false,
641 .VERTEX_ARRAY = false,
642 .NORMAL_ARRAY = false,
643 .COLOR_ARRAY = false,
644 .INDEX_ARRAY = false,
645 .TEXTURE_COORD_ARRAY = false,
646 .EDGE_FLAG_ARRAY = false,
647 .NORMALIZE = false,
648 .RESCALE_NORMAL = false,
649 .DEPTH_TEST = false,
650 .DEPTH_WRITEMASK = false,
651 .CULL_FACE = false, // ??
652 .CULL_FACE_MODE = GL_BACK,
653 .FRONT_FACE = GL_CCW,
654 }
655};
#define NONNULL_FUNC
BOOL OOLogWillDisplayMessagesInClass(NSString *inMessageClass)
Definition OOLogging.m:144
void OOLogOutdent(void)
Definition OOLogging.m:376
#define OOLog(class, format,...)
Definition OOLogging.h:88
void OOLogIndent(void)
Definition OOLogging.m:366
#define OO_ENTER_OPENGL()
static const OOOpenGLState kStandardStates[OPENGL_STATE_INTERNAL_USE_ONLY+1]
static bool GetState_DEPTH_WRITEMASK(void)
static void SetState_CLIENT_ACTIVE_TEXTURE(GLenum value)
static NSString *const kOOLogOpenGLVerifyDump
static GLenum GetState_CLIENT_ACTIVE_TEXTURE(void)
static void SetFunctionTracking(bool value)
void OOResetGLStateVerifier(void)
static void GetCurrentOpenGLState(OOOpenGLState *state) NONNULL_FUNC
static void VerifyOpenGLStateInternal(const char *caller, const char *nominalCaller, unsigned line) NONNULL_FUNC
static GLenum GetState_ACTIVE_TEXTURE(void)
static GLenum GetState_TEXTURE_ENV_MODE(void)
static void SetState_ACTIVE_TEXTURE(GLenum value)
static OOOpenGLStateID sCurrentStateID
static bool StatesEqual(const OOOpenGLState *a, const OOOpenGLState *b) NONNULL_FUNC
static void SetState_CULL_FACE_MODE(GLint value)
static void SwitchOpenGLStateInternal(const OOOpenGLState *sourceState, const OOOpenGLState *targetState) NONNULL_FUNC
void OOVerifyOpenGLState_(const char *function, unsigned line)
void OOSetOpenGLState_(OOOpenGLStateID state, const char *function, unsigned line)
static void OOGLNoteCurrentFunction(const char *function, unsigned line)
@ kStateFalse
@ kStateMaybe
NSString * OOGLEnumToString(GLenum value)
Definition OOOpenGL.m:492
OOOpenGLStateID
Definition OOOpenGL.h:122
@ OPENGL_STATE_INTERNAL_USE_ONLY
Definition OOOpenGL.h:128
#define OOSetOpenGLState(STATE)
Definition OOOpenGL.h:135
#define OOGL(statement)
Definition OOOpenGL.h:251