Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCampbell Barton <ideasman42@gmail.com>2020-03-11 06:52:57 +0300
committerCampbell Barton <ideasman42@gmail.com>2020-03-11 06:52:57 +0300
commit4184f890fdbef7409af27f1e9a13b01161001ef2 (patch)
tree2958d2c1579c5055ff8aa708774150ef8d20a90f /source/blender/gpu
parentf9cca128869fc07da46c095ac7dce16467121092 (diff)
GPU: minor changes to support standalone GHOST builds
- Move gpuPush/Pop from GPU_draw.h into GPU_state.h as this is for pushing/popping state. - Add 'GPU_STANDALONE' define, to bypass use of user-preferences for theme colors and pixelsize, as well as pbvh init/free functions. Needed to get GHOST tests working again.
Diffstat (limited to 'source/blender/gpu')
-rw-r--r--source/blender/gpu/GPU_draw.h12
-rw-r--r--source/blender/gpu/GPU_state.h12
-rw-r--r--source/blender/gpu/intern/gpu_draw.c185
-rw-r--r--source/blender/gpu/intern/gpu_extensions.c4
-rw-r--r--source/blender/gpu/intern/gpu_immediate.c8
-rw-r--r--source/blender/gpu/intern/gpu_init_exit.c4
-rw-r--r--source/blender/gpu/intern/gpu_select_pick.c1
-rw-r--r--source/blender/gpu/intern/gpu_select_sample_query.c7
-rw-r--r--source/blender/gpu/intern/gpu_state.c185
9 files changed, 222 insertions, 196 deletions
diff --git a/source/blender/gpu/GPU_draw.h b/source/blender/gpu/GPU_draw.h
index 5ed27d9a648..f521fa3c702 100644
--- a/source/blender/gpu/GPU_draw.h
+++ b/source/blender/gpu/GPU_draw.h
@@ -95,18 +95,6 @@ void GPU_create_smoke_velocity(struct FluidModifierData *mmd);
/* Delayed free of OpenGL buffers by main thread */
void GPU_free_unused_buffers(struct Main *bmain);
-/* utilities */
-typedef enum eGPUAttrMask {
- GPU_DEPTH_BUFFER_BIT = (1 << 0),
- GPU_ENABLE_BIT = (1 << 1),
- GPU_SCISSOR_BIT = (1 << 2),
- GPU_VIEWPORT_BIT = (1 << 3),
- GPU_BLEND_BIT = (1 << 4),
-} eGPUAttrMask;
-
-void gpuPushAttr(eGPUAttrMask mask);
-void gpuPopAttr(void);
-
#ifdef __cplusplus
}
#endif
diff --git a/source/blender/gpu/GPU_state.h b/source/blender/gpu/GPU_state.h
index 894ef22e963..9ce91d31d69 100644
--- a/source/blender/gpu/GPU_state.h
+++ b/source/blender/gpu/GPU_state.h
@@ -65,6 +65,18 @@ void GPU_finish(void);
void GPU_logic_op_invert_set(bool enable);
+/* Attribute push & pop. */
+typedef enum eGPUAttrMask {
+ GPU_DEPTH_BUFFER_BIT = (1 << 0),
+ GPU_ENABLE_BIT = (1 << 1),
+ GPU_SCISSOR_BIT = (1 << 2),
+ GPU_VIEWPORT_BIT = (1 << 3),
+ GPU_BLEND_BIT = (1 << 4),
+} eGPUAttrMask;
+
+void gpuPushAttr(eGPUAttrMask mask);
+void gpuPopAttr(void);
+
#ifdef __cplusplus
}
#endif
diff --git a/source/blender/gpu/intern/gpu_draw.c b/source/blender/gpu/intern/gpu_draw.c
index d674f8600c2..33bc3ced5b2 100644
--- a/source/blender/gpu/intern/gpu_draw.c
+++ b/source/blender/gpu/intern/gpu_draw.c
@@ -861,6 +861,7 @@ static void gpu_texture_update_from_ibuf(
* available. It is also required when requesting the GPUTexture for a render result. */
GPUTexture *GPU_texture_from_blender(Image *ima, ImageUser *iuser, ImBuf *ibuf, int textarget)
{
+#ifndef GPU_STANDALONE
if (ima == NULL) {
return NULL;
}
@@ -919,10 +920,13 @@ GPUTexture *GPU_texture_from_blender(Image *ima, ImageUser *iuser, ImBuf *ibuf,
GPU_texture_orig_size_set(*tex, ibuf_intern->x, ibuf_intern->y);
return *tex;
+#endif
+ return NULL;
}
GPUTexture *GPU_texture_from_movieclip(MovieClip *clip, MovieClipUser *cuser, int textarget)
{
+#ifndef GPU_STANDALONE
if (clip == NULL) {
return NULL;
}
@@ -945,6 +949,9 @@ GPUTexture *GPU_texture_from_movieclip(MovieClip *clip, MovieClipUser *cuser, in
*tex = GPU_texture_from_bindcode(textarget, bindcode);
return *tex;
+#else
+ return NULL;
+#endif
}
void GPU_free_texture_movieclip(struct MovieClip *clip)
@@ -1270,6 +1277,7 @@ void GPU_create_gl_tex_compressed(unsigned int *bind, int textarget, Image *ima,
* re-uploaded to OpenGL */
void GPU_paint_set_mipmap(Main *bmain, bool mipmap)
{
+#ifndef GPU_STANDALONE
if (!GTS.domipmap) {
return;
}
@@ -1321,10 +1329,12 @@ void GPU_paint_set_mipmap(Main *bmain, bool mipmap)
}
}
}
+#endif /* GPU_STANDALONE */
}
void GPU_paint_update_image(Image *ima, ImageUser *iuser, int x, int y, int w, int h)
{
+#ifndef GPU_STANDALONE
ImBuf *ibuf = BKE_image_acquire_ibuf(ima, iuser, NULL);
ImageTile *tile = BKE_image_get_tile_from_iuser(ima, iuser);
@@ -1346,6 +1356,7 @@ void GPU_paint_update_image(Image *ima, ImageUser *iuser, int x, int y, int w, i
}
BKE_image_release_ibuf(ima, ibuf, NULL);
+#endif
}
static LinkNode *image_free_queue = NULL;
@@ -1526,177 +1537,3 @@ void GPU_state_init(void)
glEnable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
}
}
-
-/** \name Framebuffer color depth, for selection codes
- * \{ */
-
-#define STATE_STACK_DEPTH 16
-
-typedef struct {
- eGPUAttrMask mask;
-
- /* GL_ENABLE_BIT */
- uint is_blend : 1;
- uint is_cull_face : 1;
- uint is_depth_test : 1;
- uint is_dither : 1;
- uint is_lighting : 1;
- uint is_line_smooth : 1;
- uint is_color_logic_op : 1;
- uint is_multisample : 1;
- uint is_polygon_offset_line : 1;
- uint is_polygon_offset_fill : 1;
- uint is_polygon_smooth : 1;
- uint is_sample_alpha_to_coverage : 1;
- uint is_scissor_test : 1;
- uint is_stencil_test : 1;
-
- bool is_clip_plane[6];
-
- /* GL_DEPTH_BUFFER_BIT */
- /* uint is_depth_test : 1; */
- int depth_func;
- double depth_clear_value;
- bool depth_write_mask;
-
- /* GL_SCISSOR_BIT */
- int scissor_box[4];
- /* uint is_scissor_test : 1; */
-
- /* GL_VIEWPORT_BIT */
- int viewport[4];
- double near_far[2];
-} GPUAttrValues;
-
-typedef struct {
- GPUAttrValues attr_stack[STATE_STACK_DEPTH];
- uint top;
-} GPUAttrStack;
-
-static GPUAttrStack state = {
- .top = 0,
-};
-
-#define AttrStack state
-#define Attr state.attr_stack[state.top]
-
-/**
- * Replacement for glPush/PopAttributes
- *
- * We don't need to cover all the options of legacy OpenGL
- * but simply the ones used by Blender.
- */
-void gpuPushAttr(eGPUAttrMask mask)
-{
- Attr.mask = mask;
-
- if ((mask & GPU_DEPTH_BUFFER_BIT) != 0) {
- Attr.is_depth_test = glIsEnabled(GL_DEPTH_TEST);
- glGetIntegerv(GL_DEPTH_FUNC, &Attr.depth_func);
- glGetDoublev(GL_DEPTH_CLEAR_VALUE, &Attr.depth_clear_value);
- glGetBooleanv(GL_DEPTH_WRITEMASK, (GLboolean *)&Attr.depth_write_mask);
- }
-
- if ((mask & GPU_ENABLE_BIT) != 0) {
- Attr.is_blend = glIsEnabled(GL_BLEND);
-
- for (int i = 0; i < 6; i++) {
- Attr.is_clip_plane[i] = glIsEnabled(GL_CLIP_PLANE0 + i);
- }
-
- Attr.is_cull_face = glIsEnabled(GL_CULL_FACE);
- Attr.is_depth_test = glIsEnabled(GL_DEPTH_TEST);
- Attr.is_dither = glIsEnabled(GL_DITHER);
- Attr.is_line_smooth = glIsEnabled(GL_LINE_SMOOTH);
- Attr.is_color_logic_op = glIsEnabled(GL_COLOR_LOGIC_OP);
- Attr.is_multisample = glIsEnabled(GL_MULTISAMPLE);
- Attr.is_polygon_offset_line = glIsEnabled(GL_POLYGON_OFFSET_LINE);
- Attr.is_polygon_offset_fill = glIsEnabled(GL_POLYGON_OFFSET_FILL);
- Attr.is_polygon_smooth = glIsEnabled(GL_POLYGON_SMOOTH);
- Attr.is_sample_alpha_to_coverage = glIsEnabled(GL_SAMPLE_ALPHA_TO_COVERAGE);
- Attr.is_scissor_test = glIsEnabled(GL_SCISSOR_TEST);
- Attr.is_stencil_test = glIsEnabled(GL_STENCIL_TEST);
- }
-
- if ((mask & GPU_SCISSOR_BIT) != 0) {
- Attr.is_scissor_test = glIsEnabled(GL_SCISSOR_TEST);
- glGetIntegerv(GL_SCISSOR_BOX, (GLint *)&Attr.scissor_box);
- }
-
- if ((mask & GPU_VIEWPORT_BIT) != 0) {
- glGetDoublev(GL_DEPTH_RANGE, (GLdouble *)&Attr.near_far);
- glGetIntegerv(GL_VIEWPORT, (GLint *)&Attr.viewport);
- }
-
- if ((mask & GPU_BLEND_BIT) != 0) {
- Attr.is_blend = glIsEnabled(GL_BLEND);
- }
-
- BLI_assert(AttrStack.top < STATE_STACK_DEPTH);
- AttrStack.top++;
-}
-
-static void restore_mask(GLenum cap, const bool value)
-{
- if (value) {
- glEnable(cap);
- }
- else {
- glDisable(cap);
- }
-}
-
-void gpuPopAttr(void)
-{
- BLI_assert(AttrStack.top > 0);
- AttrStack.top--;
-
- GLint mask = Attr.mask;
-
- if ((mask & GPU_DEPTH_BUFFER_BIT) != 0) {
- restore_mask(GL_DEPTH_TEST, Attr.is_depth_test);
- glDepthFunc(Attr.depth_func);
- glClearDepth(Attr.depth_clear_value);
- glDepthMask(Attr.depth_write_mask);
- }
-
- if ((mask & GPU_ENABLE_BIT) != 0) {
- restore_mask(GL_BLEND, Attr.is_blend);
-
- for (int i = 0; i < 6; i++) {
- restore_mask(GL_CLIP_PLANE0 + i, Attr.is_clip_plane[i]);
- }
-
- restore_mask(GL_CULL_FACE, Attr.is_cull_face);
- restore_mask(GL_DEPTH_TEST, Attr.is_depth_test);
- restore_mask(GL_DITHER, Attr.is_dither);
- restore_mask(GL_LINE_SMOOTH, Attr.is_line_smooth);
- restore_mask(GL_COLOR_LOGIC_OP, Attr.is_color_logic_op);
- restore_mask(GL_MULTISAMPLE, Attr.is_multisample);
- restore_mask(GL_POLYGON_OFFSET_LINE, Attr.is_polygon_offset_line);
- restore_mask(GL_POLYGON_OFFSET_FILL, Attr.is_polygon_offset_fill);
- restore_mask(GL_POLYGON_SMOOTH, Attr.is_polygon_smooth);
- restore_mask(GL_SAMPLE_ALPHA_TO_COVERAGE, Attr.is_sample_alpha_to_coverage);
- restore_mask(GL_SCISSOR_TEST, Attr.is_scissor_test);
- restore_mask(GL_STENCIL_TEST, Attr.is_stencil_test);
- }
-
- if ((mask & GPU_VIEWPORT_BIT) != 0) {
- glViewport(Attr.viewport[0], Attr.viewport[1], Attr.viewport[2], Attr.viewport[3]);
- glDepthRange(Attr.near_far[0], Attr.near_far[1]);
- }
-
- if ((mask & GPU_SCISSOR_BIT) != 0) {
- restore_mask(GL_SCISSOR_TEST, Attr.is_scissor_test);
- glScissor(Attr.scissor_box[0], Attr.scissor_box[1], Attr.scissor_box[2], Attr.scissor_box[3]);
- }
-
- if ((mask & GPU_BLEND_BIT) != 0) {
- restore_mask(GL_BLEND, Attr.is_blend);
- }
-}
-
-#undef Attr
-#undef AttrStack
-
-/** \} */
diff --git a/source/blender/gpu/intern/gpu_extensions.c b/source/blender/gpu/intern/gpu_extensions.c
index 4676cc3b244..5a2b74f3407 100644
--- a/source/blender/gpu/intern/gpu_extensions.c
+++ b/source/blender/gpu/intern/gpu_extensions.c
@@ -348,7 +348,11 @@ void gpu_extensions_exit(void)
bool GPU_mem_stats_supported(void)
{
+#ifndef GPU_STANDALONE
return (GLEW_NVX_gpu_memory_info || GLEW_ATI_meminfo) && (G.debug & G_DEBUG_GPU_MEM);
+#else
+ return false;
+#endif
}
void GPU_mem_stats_get(int *totalmem, int *freemem)
diff --git a/source/blender/gpu/intern/gpu_immediate.c b/source/blender/gpu/intern/gpu_immediate.c
index bd3de96d636..671335ca702 100644
--- a/source/blender/gpu/intern/gpu_immediate.c
+++ b/source/blender/gpu/intern/gpu_immediate.c
@@ -23,7 +23,9 @@
* GPU immediate mode work-alike
*/
-#include "UI_resources.h"
+#ifndef GPU_STANDALONE
+# include "UI_resources.h"
+#endif
#include "GPU_attr_binding.h"
#include "GPU_immediate.h"
@@ -910,6 +912,8 @@ void immUniformColor4ubv(const uchar rgba[4])
immUniformColor4ub(rgba[0], rgba[1], rgba[2], rgba[3]);
}
+#ifndef GPU_STANDALONE
+
void immUniformThemeColor(int color_id)
{
float color[4];
@@ -958,3 +962,5 @@ void immThemeColorShadeAlpha(int colorid, int coloffset, int alphaoffset)
UI_GetThemeColorShadeAlpha4ubv(colorid, coloffset, alphaoffset, col);
immUniformColor4ub(col[0], col[1], col[2], col[3]);
}
+
+#endif /* GPU_STANDALONE */
diff --git a/source/blender/gpu/intern/gpu_init_exit.c b/source/blender/gpu/intern/gpu_init_exit.c
index c99b7fc8a67..96dc437e10b 100644
--- a/source/blender/gpu/intern/gpu_init_exit.c
+++ b/source/blender/gpu/intern/gpu_init_exit.c
@@ -64,12 +64,16 @@ void GPU_init(void)
immInit();
}
+#ifndef GPU_STANDALONE
gpu_pbvh_init();
+#endif
}
void GPU_exit(void)
{
+#ifndef GPU_STANDALONE
gpu_pbvh_exit();
+#endif
if (!G.background) {
immDestroy();
diff --git a/source/blender/gpu/intern/gpu_select_pick.c b/source/blender/gpu/intern/gpu_select_pick.c
index 1fb83b628e1..498de13e10f 100644
--- a/source/blender/gpu/intern/gpu_select_pick.c
+++ b/source/blender/gpu/intern/gpu_select_pick.c
@@ -30,6 +30,7 @@
#include "GPU_immediate.h"
#include "GPU_draw.h"
#include "GPU_select.h"
+#include "GPU_state.h"
#include "GPU_glew.h"
#include "MEM_guardedalloc.h"
diff --git a/source/blender/gpu/intern/gpu_select_sample_query.c b/source/blender/gpu/intern/gpu_select_sample_query.c
index 6e8b062cff0..578546f3af9 100644
--- a/source/blender/gpu/intern/gpu_select_sample_query.c
+++ b/source/blender/gpu/intern/gpu_select_sample_query.c
@@ -26,9 +26,8 @@
#include <stdlib.h>
-#include "GPU_immediate.h"
-#include "GPU_draw.h"
#include "GPU_select.h"
+#include "GPU_state.h"
#include "GPU_glew.h"
#include "MEM_guardedalloc.h"
@@ -37,10 +36,6 @@
#include "BLI_utildefines.h"
-#include "PIL_time.h"
-
-#include "BKE_global.h"
-
#include "gpu_select_private.h"
/* Ad hoc number of queries to allocate to skip doing many glGenQueries */
diff --git a/source/blender/gpu/intern/gpu_state.c b/source/blender/gpu/intern/gpu_state.c
index caf97a620ab..9ff518aec1b 100644
--- a/source/blender/gpu/intern/gpu_state.c
+++ b/source/blender/gpu/intern/gpu_state.c
@@ -18,7 +18,12 @@
* \ingroup gpu
*/
-#include "DNA_userdef_types.h"
+#ifndef GPU_STANDALONE
+# include "DNA_userdef_types.h"
+# define PIXELSIZE (U.pixelsize)
+#else
+# define PIXELSIZE (1.0f)
+#endif
#include "BLI_utildefines.h"
@@ -107,7 +112,7 @@ void GPU_line_smooth(bool enable)
void GPU_line_width(float width)
{
float max_size = GPU_max_line_width();
- float final_size = width * U.pixelsize;
+ float final_size = width * PIXELSIZE;
/* Fix opengl errors on certain platform / drivers. */
CLAMP(final_size, 1.0f, max_size);
glLineWidth(final_size);
@@ -115,7 +120,7 @@ void GPU_line_width(float width)
void GPU_point_size(float size)
{
- glPointSize(size * U.pixelsize);
+ glPointSize(size * PIXELSIZE);
}
void GPU_polygon_smooth(bool enable)
@@ -189,3 +194,177 @@ void GPU_logic_op_invert_set(bool enable)
glEnable(GL_DITHER);
}
}
+
+/** \name GPU Push/Pop State
+ * \{ */
+
+#define STATE_STACK_DEPTH 16
+
+typedef struct {
+ eGPUAttrMask mask;
+
+ /* GL_ENABLE_BIT */
+ uint is_blend : 1;
+ uint is_cull_face : 1;
+ uint is_depth_test : 1;
+ uint is_dither : 1;
+ uint is_lighting : 1;
+ uint is_line_smooth : 1;
+ uint is_color_logic_op : 1;
+ uint is_multisample : 1;
+ uint is_polygon_offset_line : 1;
+ uint is_polygon_offset_fill : 1;
+ uint is_polygon_smooth : 1;
+ uint is_sample_alpha_to_coverage : 1;
+ uint is_scissor_test : 1;
+ uint is_stencil_test : 1;
+
+ bool is_clip_plane[6];
+
+ /* GL_DEPTH_BUFFER_BIT */
+ /* uint is_depth_test : 1; */
+ int depth_func;
+ double depth_clear_value;
+ bool depth_write_mask;
+
+ /* GL_SCISSOR_BIT */
+ int scissor_box[4];
+ /* uint is_scissor_test : 1; */
+
+ /* GL_VIEWPORT_BIT */
+ int viewport[4];
+ double near_far[2];
+} GPUAttrValues;
+
+typedef struct {
+ GPUAttrValues attr_stack[STATE_STACK_DEPTH];
+ uint top;
+} GPUAttrStack;
+
+static GPUAttrStack state = {
+ .top = 0,
+};
+
+#define AttrStack state
+#define Attr state.attr_stack[state.top]
+
+/**
+ * Replacement for glPush/PopAttributes
+ *
+ * We don't need to cover all the options of legacy OpenGL
+ * but simply the ones used by Blender.
+ */
+void gpuPushAttr(eGPUAttrMask mask)
+{
+ Attr.mask = mask;
+
+ if ((mask & GPU_DEPTH_BUFFER_BIT) != 0) {
+ Attr.is_depth_test = glIsEnabled(GL_DEPTH_TEST);
+ glGetIntegerv(GL_DEPTH_FUNC, &Attr.depth_func);
+ glGetDoublev(GL_DEPTH_CLEAR_VALUE, &Attr.depth_clear_value);
+ glGetBooleanv(GL_DEPTH_WRITEMASK, (GLboolean *)&Attr.depth_write_mask);
+ }
+
+ if ((mask & GPU_ENABLE_BIT) != 0) {
+ Attr.is_blend = glIsEnabled(GL_BLEND);
+
+ for (int i = 0; i < 6; i++) {
+ Attr.is_clip_plane[i] = glIsEnabled(GL_CLIP_PLANE0 + i);
+ }
+
+ Attr.is_cull_face = glIsEnabled(GL_CULL_FACE);
+ Attr.is_depth_test = glIsEnabled(GL_DEPTH_TEST);
+ Attr.is_dither = glIsEnabled(GL_DITHER);
+ Attr.is_line_smooth = glIsEnabled(GL_LINE_SMOOTH);
+ Attr.is_color_logic_op = glIsEnabled(GL_COLOR_LOGIC_OP);
+ Attr.is_multisample = glIsEnabled(GL_MULTISAMPLE);
+ Attr.is_polygon_offset_line = glIsEnabled(GL_POLYGON_OFFSET_LINE);
+ Attr.is_polygon_offset_fill = glIsEnabled(GL_POLYGON_OFFSET_FILL);
+ Attr.is_polygon_smooth = glIsEnabled(GL_POLYGON_SMOOTH);
+ Attr.is_sample_alpha_to_coverage = glIsEnabled(GL_SAMPLE_ALPHA_TO_COVERAGE);
+ Attr.is_scissor_test = glIsEnabled(GL_SCISSOR_TEST);
+ Attr.is_stencil_test = glIsEnabled(GL_STENCIL_TEST);
+ }
+
+ if ((mask & GPU_SCISSOR_BIT) != 0) {
+ Attr.is_scissor_test = glIsEnabled(GL_SCISSOR_TEST);
+ glGetIntegerv(GL_SCISSOR_BOX, (GLint *)&Attr.scissor_box);
+ }
+
+ if ((mask & GPU_VIEWPORT_BIT) != 0) {
+ glGetDoublev(GL_DEPTH_RANGE, (GLdouble *)&Attr.near_far);
+ glGetIntegerv(GL_VIEWPORT, (GLint *)&Attr.viewport);
+ }
+
+ if ((mask & GPU_BLEND_BIT) != 0) {
+ Attr.is_blend = glIsEnabled(GL_BLEND);
+ }
+
+ BLI_assert(AttrStack.top < STATE_STACK_DEPTH);
+ AttrStack.top++;
+}
+
+static void restore_mask(GLenum cap, const bool value)
+{
+ if (value) {
+ glEnable(cap);
+ }
+ else {
+ glDisable(cap);
+ }
+}
+
+void gpuPopAttr(void)
+{
+ BLI_assert(AttrStack.top > 0);
+ AttrStack.top--;
+
+ GLint mask = Attr.mask;
+
+ if ((mask & GPU_DEPTH_BUFFER_BIT) != 0) {
+ restore_mask(GL_DEPTH_TEST, Attr.is_depth_test);
+ glDepthFunc(Attr.depth_func);
+ glClearDepth(Attr.depth_clear_value);
+ glDepthMask(Attr.depth_write_mask);
+ }
+
+ if ((mask & GPU_ENABLE_BIT) != 0) {
+ restore_mask(GL_BLEND, Attr.is_blend);
+
+ for (int i = 0; i < 6; i++) {
+ restore_mask(GL_CLIP_PLANE0 + i, Attr.is_clip_plane[i]);
+ }
+
+ restore_mask(GL_CULL_FACE, Attr.is_cull_face);
+ restore_mask(GL_DEPTH_TEST, Attr.is_depth_test);
+ restore_mask(GL_DITHER, Attr.is_dither);
+ restore_mask(GL_LINE_SMOOTH, Attr.is_line_smooth);
+ restore_mask(GL_COLOR_LOGIC_OP, Attr.is_color_logic_op);
+ restore_mask(GL_MULTISAMPLE, Attr.is_multisample);
+ restore_mask(GL_POLYGON_OFFSET_LINE, Attr.is_polygon_offset_line);
+ restore_mask(GL_POLYGON_OFFSET_FILL, Attr.is_polygon_offset_fill);
+ restore_mask(GL_POLYGON_SMOOTH, Attr.is_polygon_smooth);
+ restore_mask(GL_SAMPLE_ALPHA_TO_COVERAGE, Attr.is_sample_alpha_to_coverage);
+ restore_mask(GL_SCISSOR_TEST, Attr.is_scissor_test);
+ restore_mask(GL_STENCIL_TEST, Attr.is_stencil_test);
+ }
+
+ if ((mask & GPU_VIEWPORT_BIT) != 0) {
+ glViewport(Attr.viewport[0], Attr.viewport[1], Attr.viewport[2], Attr.viewport[3]);
+ glDepthRange(Attr.near_far[0], Attr.near_far[1]);
+ }
+
+ if ((mask & GPU_SCISSOR_BIT) != 0) {
+ restore_mask(GL_SCISSOR_TEST, Attr.is_scissor_test);
+ glScissor(Attr.scissor_box[0], Attr.scissor_box[1], Attr.scissor_box[2], Attr.scissor_box[3]);
+ }
+
+ if ((mask & GPU_BLEND_BIT) != 0) {
+ restore_mask(GL_BLEND, Attr.is_blend);
+ }
+}
+
+#undef Attr
+#undef AttrStack
+
+/** \} */