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:
Diffstat (limited to 'source/blender/gpu/intern')
-rw-r--r--source/blender/gpu/intern/gpu_batch_private.h8
-rw-r--r--source/blender/gpu/intern/gpu_context_private.h4
-rw-r--r--source/blender/gpu/intern/gpu_draw.c63
-rw-r--r--source/blender/gpu/intern/gpu_framebuffer.c4
-rw-r--r--source/blender/gpu/intern/gpu_immediate.c8
-rw-r--r--source/blender/gpu/intern/gpu_immediate_util.c26
-rw-r--r--source/blender/gpu/intern/gpu_shader_interface.c6
-rw-r--r--source/blender/gpu/intern/gpu_state.c40
-rw-r--r--source/blender/gpu/intern/gpu_texture.c115
-rw-r--r--source/blender/gpu/intern/gpu_viewport.c8
10 files changed, 185 insertions, 97 deletions
diff --git a/source/blender/gpu/intern/gpu_batch_private.h b/source/blender/gpu/intern/gpu_batch_private.h
index 42cfc1e2a5c..58d1810ac7a 100644
--- a/source/blender/gpu/intern/gpu_batch_private.h
+++ b/source/blender/gpu/intern/gpu_batch_private.h
@@ -27,14 +27,14 @@
#ifndef __GPU_BATCH_PRIVATE_H__
#define __GPU_BATCH_PRIVATE_H__
-#ifdef __cplusplus
-extern "C" {
-#endif
-
#include "GPU_batch.h"
#include "GPU_context.h"
#include "GPU_shader_interface.h"
+#ifdef __cplusplus
+extern "C" {
+#endif
+
void gpu_batch_remove_interface_ref(GPUBatch *batch, const GPUShaderInterface *interface);
#ifdef __cplusplus
diff --git a/source/blender/gpu/intern/gpu_context_private.h b/source/blender/gpu/intern/gpu_context_private.h
index c9379e5433f..f64cdf439a1 100644
--- a/source/blender/gpu/intern/gpu_context_private.h
+++ b/source/blender/gpu/intern/gpu_context_private.h
@@ -26,12 +26,12 @@
#ifndef __GPU_CONTEXT_PRIVATE_H__
#define __GPU_CONTEXT_PRIVATE_H__
+#include "GPU_context.h"
+
#ifdef __cplusplus
extern "C" {
#endif
-#include "GPU_context.h"
-
struct GPUFrameBuffer;
GLuint GPU_vao_default(void);
diff --git a/source/blender/gpu/intern/gpu_draw.c b/source/blender/gpu/intern/gpu_draw.c
index 5f3822c794e..7871907a7d4 100644
--- a/source/blender/gpu/intern/gpu_draw.c
+++ b/source/blender/gpu/intern/gpu_draw.c
@@ -1481,66 +1481,3 @@ void GPU_free_images_old(Main *bmain)
ima = ima->id.next;
}
}
-
-static void gpu_disable_multisample(void)
-{
-#ifdef __linux__
- /* changing multisample from the default (enabled) causes problems on some
- * systems (NVIDIA/Linux) when the pixel format doesn't have a multisample buffer */
- bool toggle_ok = true;
-
- if (GPU_type_matches(GPU_DEVICE_NVIDIA, GPU_OS_UNIX, GPU_DRIVER_ANY)) {
- int samples = 0;
- glGetIntegerv(GL_SAMPLES, &samples);
-
- if (samples == 0) {
- toggle_ok = false;
- }
- }
-
- if (toggle_ok) {
- glDisable(GL_MULTISAMPLE);
- }
-#else
- glDisable(GL_MULTISAMPLE);
-#endif
-}
-
-/* Default OpenGL State
- *
- * This is called on startup, for opengl offscreen render.
- * Generally we should always return to this state when
- * temporarily modifying the state for drawing, though that are (undocumented)
- * exceptions that we should try to get rid of. */
-
-void GPU_state_init(void)
-{
- GPU_program_point_size(false);
-
- glEnable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
-
- glDepthFunc(GL_LEQUAL);
-
- glDisable(GL_BLEND);
- glDisable(GL_DEPTH_TEST);
- glDisable(GL_COLOR_LOGIC_OP);
- glDisable(GL_STENCIL_TEST);
-
- glDepthRange(0.0, 1.0);
-
- glFrontFace(GL_CCW);
- glCullFace(GL_BACK);
- glDisable(GL_CULL_FACE);
-
- gpu_disable_multisample();
-
- /* This is a bit dangerous since addons could change this. */
- glEnable(GL_PRIMITIVE_RESTART);
- glPrimitiveRestartIndex((GLuint)0xFFFFFFFF);
-
- /* TODO: Should become default. But needs at least GL 4.3 */
- if (GLEW_ARB_ES3_compatibility) {
- /* Takes predecence over GL_PRIMITIVE_RESTART */
- glEnable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
- }
-}
diff --git a/source/blender/gpu/intern/gpu_framebuffer.c b/source/blender/gpu/intern/gpu_framebuffer.c
index e6092b55fc4..5af9364b92c 100644
--- a/source/blender/gpu/intern/gpu_framebuffer.c
+++ b/source/blender/gpu/intern/gpu_framebuffer.c
@@ -541,10 +541,6 @@ void GPU_framebuffer_bind(GPUFrameBuffer *fb)
}
#endif
- if (fb->multisample) {
- glEnable(GL_MULTISAMPLE);
- }
-
glViewport(0, 0, fb->width, fb->height);
}
diff --git a/source/blender/gpu/intern/gpu_immediate.c b/source/blender/gpu/intern/gpu_immediate.c
index 7bcb0a7a552..d95904c0007 100644
--- a/source/blender/gpu/intern/gpu_immediate.c
+++ b/source/blender/gpu/intern/gpu_immediate.c
@@ -272,6 +272,14 @@ void immBegin(GPUPrimType prim_type, uint vertex_len)
/* printf("mapping %u to %u\n", imm.buffer_offset, imm.buffer_offset + bytes_needed - 1); */
+#if TRUST_NO_ONE
+ {
+ GLint bufsize;
+ glGetBufferParameteriv(GL_ARRAY_BUFFER, GL_BUFFER_SIZE, &bufsize);
+ assert(active_buffer->buffer_offset + bytes_needed <= bufsize);
+ }
+#endif
+
active_buffer->buffer_data = glMapBufferRange(
GL_ARRAY_BUFFER,
active_buffer->buffer_offset,
diff --git a/source/blender/gpu/intern/gpu_immediate_util.c b/source/blender/gpu/intern/gpu_immediate_util.c
index 7266f595447..e834d6afccb 100644
--- a/source/blender/gpu/intern/gpu_immediate_util.c
+++ b/source/blender/gpu/intern/gpu_immediate_util.c
@@ -361,25 +361,35 @@ void imm_draw_box_wire_3d(uint pos, float x1, float y1, float x2, float y2)
/**
* Draw a standard checkerboard to indicate transparent backgrounds.
*/
-void imm_draw_box_checker_2d(float x1, float y1, float x2, float y2)
+void imm_draw_box_checker_2d_ex(float x1,
+ float y1,
+ float x2,
+ float y2,
+ const float color_primary[4],
+ const float color_secondary[4],
+ int checker_size)
{
uint pos = GPU_vertformat_attr_add(immVertexFormat(), "pos", GPU_COMP_F32, 2, GPU_FETCH_FLOAT);
- float checker_primary[4];
- float checker_secondary[4];
- int checker_size = UI_GetThemeValue(TH_TRANSPARENT_CHECKER_SIZE);
immBindBuiltinProgram(GPU_SHADER_2D_CHECKER);
- UI_GetThemeColor4fv(TH_TRANSPARENT_CHECKER_PRIMARY, checker_primary);
- UI_GetThemeColor4fv(TH_TRANSPARENT_CHECKER_SECONDARY, checker_secondary);
- immUniform4fv("color1", checker_primary);
- immUniform4fv("color2", checker_secondary);
+ immUniform4fv("color1", color_primary);
+ immUniform4fv("color2", color_secondary);
immUniform1i("size", checker_size);
immRectf(pos, x1, y1, x2, y2);
immUnbindProgram();
}
+void imm_draw_box_checker_2d(float x1, float y1, float x2, float y2)
+{
+ float checker_primary[4];
+ float checker_secondary[4];
+ UI_GetThemeColor4fv(TH_TRANSPARENT_CHECKER_PRIMARY, checker_primary);
+ UI_GetThemeColor4fv(TH_TRANSPARENT_CHECKER_SECONDARY, checker_secondary);
+ int checker_size = UI_GetThemeValue(TH_TRANSPARENT_CHECKER_SIZE);
+ imm_draw_box_checker_2d_ex(x1, y1, x2, y2, checker_primary, checker_secondary, checker_size);
+}
void imm_draw_cube_fill_3d(uint pos, const float co[3], const float aspect[3])
{
diff --git a/source/blender/gpu/intern/gpu_shader_interface.c b/source/blender/gpu/intern/gpu_shader_interface.c
index 8cd1afad536..3218d12bc0d 100644
--- a/source/blender/gpu/intern/gpu_shader_interface.c
+++ b/source/blender/gpu/intern/gpu_shader_interface.c
@@ -254,8 +254,12 @@ GPUShaderInterface *GPU_shaderinterface_create(int32_t program)
}
/* TODO: reject DOUBLE gl_types */
-
input->location = glGetAttribLocation(program, name);
+ /* Ignore OpenGL names like `gl_BaseInstanceARB`, `gl_InstanceID` and `gl_VertexID`. */
+ if (input->location == -1) {
+ MEM_freeN(input);
+ continue;
+ }
if (input->location != -1) {
shaderface->enabled_attr_mask |= (1 << input->location);
diff --git a/source/blender/gpu/intern/gpu_state.c b/source/blender/gpu/intern/gpu_state.c
index d6f044a79e3..908f5fa5771 100644
--- a/source/blender/gpu/intern/gpu_state.c
+++ b/source/blender/gpu/intern/gpu_state.c
@@ -370,4 +370,44 @@ void gpuPopAttr(void)
#undef Attr
#undef AttrStack
+/* Default OpenGL State
+ *
+ * This is called on startup, for opengl offscreen render.
+ * Generally we should always return to this state when
+ * temporarily modifying the state for drawing, though that are (undocumented)
+ * exceptions that we should try to get rid of. */
+
+void GPU_state_init(void)
+{
+ GPU_program_point_size(false);
+
+ glEnable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
+
+ glDisable(GL_BLEND);
+ glDisable(GL_DEPTH_TEST);
+ glDisable(GL_COLOR_LOGIC_OP);
+ glDisable(GL_STENCIL_TEST);
+ glDisable(GL_DITHER);
+
+ glDepthFunc(GL_LEQUAL);
+ glDepthRange(0.0, 1.0);
+
+ glFrontFace(GL_CCW);
+ glCullFace(GL_BACK);
+ glDisable(GL_CULL_FACE);
+
+ /* Is default but better be explicit. */
+ glEnable(GL_MULTISAMPLE);
+
+ /* This is a bit dangerous since addons could change this. */
+ glEnable(GL_PRIMITIVE_RESTART);
+ glPrimitiveRestartIndex((GLuint)0xFFFFFFFF);
+
+ /* TODO: Should become default. But needs at least GL 4.3 */
+ if (GLEW_ARB_ES3_compatibility) {
+ /* Takes predecence over GL_PRIMITIVE_RESTART */
+ glEnable(GL_PRIMITIVE_RESTART_FIXED_INDEX);
+ }
+}
+
/** \} */
diff --git a/source/blender/gpu/intern/gpu_texture.c b/source/blender/gpu/intern/gpu_texture.c
index fd01ddf8597..38ba8bc612f 100644
--- a/source/blender/gpu/intern/gpu_texture.c
+++ b/source/blender/gpu/intern/gpu_texture.c
@@ -94,6 +94,7 @@ struct GPUTexture {
};
static uint gpu_get_bytesize(eGPUTextureFormat data_type);
+static void gpu_texture_framebuffer_ensure(GPUTexture *tex);
/* ------ Memory Management ------- */
/* Records every texture allocation / free
@@ -1570,25 +1571,117 @@ void *GPU_texture_read(GPUTexture *tex, eGPUDataFormat gpu_data_format, int mipl
void GPU_texture_clear(GPUTexture *tex, eGPUDataFormat gpu_data_format, const void *color)
{
- if (GLEW_ARB_clear_texture) {
- GLenum data_format = gpu_get_gl_dataformat(tex->format, &tex->format_flag);
+ BLI_assert(color != NULL); /* Do not accept NULL as parameter. */
+ gpu_validate_data_format(tex->format, gpu_data_format);
+
+ if (false && GLEW_ARB_clear_texture) {
GLenum data_type = gpu_get_gl_datatype(gpu_data_format);
+ GLenum data_format = gpu_get_gl_dataformat(tex->format, &tex->format_flag);
glClearTexImage(tex->bindcode, 0, data_format, data_type, color);
+
+ if (GPU_texture_stencil(tex) && GPU_texture_depth(tex)) {
+ /* TODO(clem) implement in fallback. */
+ BLI_assert(0);
+ }
+ else if (GPU_texture_depth(tex)) {
+ switch (gpu_data_format) {
+ case GPU_DATA_FLOAT:
+ case GPU_DATA_UNSIGNED_INT:
+ break;
+ default:
+ /* TODO(clem) implement in fallback. */
+ BLI_assert(0);
+ break;
+ }
+ }
+ else {
+ switch (gpu_data_format) {
+ case GPU_DATA_FLOAT:
+ case GPU_DATA_UNSIGNED_INT:
+ case GPU_DATA_UNSIGNED_BYTE:
+ break;
+ default:
+ /* TODO(clem) implement in fallback. */
+ BLI_assert(0);
+ break;
+ }
+ }
}
else {
- size_t buffer_len = gpu_texture_memory_footprint_compute(tex);
- unsigned char *pixels = MEM_mallocN(buffer_len, __func__);
- if (color) {
- const size_t bytesize = (size_t)gpu_get_bytesize(tex->format);
- for (size_t byte = 0; byte < buffer_len; byte += bytesize) {
- memcpy(&pixels[byte], color, bytesize);
+ /* Fallback for older GL. */
+ GPUFrameBuffer *prev_fb = GPU_framebuffer_active_get();
+
+ gpu_texture_framebuffer_ensure(tex);
+ /* This means that this function can only be used in one context for each texture. */
+ BLI_assert(tex->copy_fb_ctx == GPU_context_active_get());
+
+ glBindFramebuffer(GL_FRAMEBUFFER, tex->copy_fb);
+ glViewport(0, 0, tex->w, tex->h);
+
+ /* Watch: Write mask could prevent the clear.
+ * glClearTexImage does not change the state so we don't do it here either. */
+ if (GPU_texture_stencil(tex) && GPU_texture_depth(tex)) {
+ /* TODO(clem) implement. */
+ BLI_assert(0);
+ }
+ else if (GPU_texture_depth(tex)) {
+ float depth;
+ switch (gpu_data_format) {
+ case GPU_DATA_FLOAT: {
+ depth = *(float *)color;
+ break;
+ }
+ case GPU_DATA_UNSIGNED_INT: {
+ depth = *(uint *)color / (float)UINT_MAX;
+ break;
+ }
+ default:
+ BLI_assert(!"Unhandled data format");
+ depth = 0.0f;
+ break;
}
+ glClearDepth(depth);
+ glClear(GL_DEPTH_BUFFER_BIT);
}
else {
- memset(pixels, 0, buffer_len);
+ float r, g, b, a;
+ switch (gpu_data_format) {
+ case GPU_DATA_FLOAT: {
+ float *f_color = (float *)color;
+ r = f_color[0];
+ g = (tex->components > 1) ? f_color[1] : 0.0f;
+ b = (tex->components > 2) ? f_color[2] : 0.0f;
+ a = (tex->components > 3) ? f_color[3] : 0.0f;
+ break;
+ }
+ case GPU_DATA_UNSIGNED_INT: {
+ uint *u_color = (uint *)color;
+ r = u_color[0] / (float)UINT_MAX;
+ g = (tex->components > 1) ? u_color[1] / (float)UINT_MAX : 0.0f;
+ b = (tex->components > 2) ? u_color[2] / (float)UINT_MAX : 0.0f;
+ a = (tex->components > 3) ? u_color[3] / (float)UINT_MAX : 0.0f;
+ break;
+ }
+ case GPU_DATA_UNSIGNED_BYTE: {
+ uchar *ub_color = (uchar *)color;
+ r = ub_color[0] / 255.0f;
+ g = (tex->components > 1) ? ub_color[1] / 255.0f : 0.0f;
+ b = (tex->components > 2) ? ub_color[2] / 255.0f : 0.0f;
+ a = (tex->components > 3) ? ub_color[3] / 255.0f : 0.0f;
+ break;
+ }
+ default:
+ BLI_assert(!"Unhandled data format");
+ r = g = b = a = 0.0f;
+ break;
+ }
+ glClearColor(r, g, b, a);
+ glClear(GL_COLOR_BUFFER_BIT);
+ }
+
+ if (prev_fb) {
+ GPU_framebuffer_bind(prev_fb);
}
- GPU_texture_update(tex, gpu_data_format, pixels);
- MEM_freeN(pixels);
}
}
diff --git a/source/blender/gpu/intern/gpu_viewport.c b/source/blender/gpu/intern/gpu_viewport.c
index 496e8981f2b..f30270b9eed 100644
--- a/source/blender/gpu/intern/gpu_viewport.c
+++ b/source/blender/gpu/intern/gpu_viewport.c
@@ -559,10 +559,10 @@ void GPU_viewport_colorspace_set(GPUViewport *viewport,
{
/**
* HACK(fclem): We copy the settings here to avoid use after free if an update frees the scene
- * and the viewport stays cached (see T75443). But this means the OCIO curvemapping caching
- * (which is based on CurveMap pointer address) cannot operate correctly and it will create
- * a different OCIO processor for each viewport. We try to only realloc the curvemap copy if
- * needed to avoid uneeded cache invalidation.
+ * and the viewport stays cached (see T75443). But this means the OCIO curve-mapping caching
+ * (which is based on #CurveMap pointer address) cannot operate correctly and it will create
+ * a different OCIO processor for each viewport. We try to only reallocate the curve-map copy
+ * if needed to avoid unneeded cache invalidation.
*/
if (view_settings->curve_mapping) {
if (viewport->view_settings.curve_mapping) {