DrawManager: Fix Incorrect Resource Binding Hair/Curves

In the DrawManager a dummy texture was attached to the a, au, c, ac
binding points. In the shader those binding points are actual texture
buffers.

The reason for the dummy texture was to work around some OpenGL driver
bugs. In Vulkan (and expected also in Metal) it is not allowed to attach
a texture as a texel buffer. Fixing this would require copying buffers into a
buffer during binding.

This patch will remove the binding of the textures and use the vbos
instead. Also it fixes an issue where a platform does support compute
shaders, but don't support transform feedback. This is currently the
case for the Vulkan backend.

Pull Request: https://projects.blender.org/blender/blender/pulls/108139
This commit is contained in:
Jeroen Bakker
2023-05-22 12:59:09 +02:00
parent 1ab265f535
commit 2164515fab
2 changed files with 12 additions and 20 deletions

View File

@@ -61,7 +61,6 @@ static int g_tf_target_width;
static int g_tf_target_height;
static GPUVertBuf *g_dummy_vbo = nullptr;
static GPUTexture *g_dummy_texture = nullptr;
static DRWPass *g_tf_pass; /* XXX can be a problem with multiple DRWManager in the future */
using CurvesInfosBuf = blender::draw::UniformBuffer<CurvesInfos>;
@@ -121,8 +120,6 @@ void DRW_curves_init(DRWData *drw_data)
GPU_vertbuf_attr_fill(g_dummy_vbo, dummy_id, vert);
/* Create vbo immediately to bind to texture buffer. */
GPU_vertbuf_use(g_dummy_vbo);
g_dummy_texture = GPU_texture_create_from_vertbuf("hair_dummy_attr", g_dummy_vbo);
}
}
@@ -318,12 +315,12 @@ DRWShadingGroup *DRW_shgroup_curves_create_sub(Object *object,
DRWShadingGroup *shgrp = DRW_shgroup_create_sub(shgrp_parent);
/* Fix issue with certain driver not drawing anything if there is no texture bound to
/* Fix issue with certain driver not drawing anything if there is nothing bound to
* "ac", "au", "u" or "c". */
DRW_shgroup_uniform_texture(shgrp, "u", g_dummy_texture);
DRW_shgroup_uniform_texture(shgrp, "au", g_dummy_texture);
DRW_shgroup_uniform_texture(shgrp, "c", g_dummy_texture);
DRW_shgroup_uniform_texture(shgrp, "ac", g_dummy_texture);
DRW_shgroup_buffer_texture(shgrp, "u", g_dummy_vbo);
DRW_shgroup_buffer_texture(shgrp, "au", g_dummy_vbo);
DRW_shgroup_buffer_texture(shgrp, "c", g_dummy_vbo);
DRW_shgroup_buffer_texture(shgrp, "ac", g_dummy_vbo);
/* TODO: Generalize radius implementation for curves data type. */
float hair_rad_shape = 0.0f;
@@ -415,7 +412,7 @@ void DRW_curves_update()
/* Update legacy hair too, to avoid verbosity in callers. */
DRW_hair_update();
if (!GPU_transform_feedback_support()) {
if (drw_curves_shader_type_get() == PART_REFINE_SHADER_TRANSFORM_FEEDBACK_WORKAROUND) {
/**
* Workaround to transform feedback not working on mac.
* On some system it crashes (see #58489) and on some other it renders garbage (see #60171).
@@ -538,5 +535,4 @@ void DRW_curves_free()
DRW_hair_free();
GPU_VERTBUF_DISCARD_SAFE(g_dummy_vbo);
DRW_TEXTURE_FREE_SAFE(g_dummy_texture);
}

View File

@@ -64,7 +64,6 @@ static int g_tf_target_width;
static int g_tf_target_height;
static GPUVertBuf *g_dummy_vbo = nullptr;
static GPUTexture *g_dummy_texture = nullptr;
static DRWPass *g_tf_pass; /* XXX can be a problem with multiple #DRWManager in the future */
static blender::draw::UniformBuffer<CurvesInfos> *g_dummy_curves_info = nullptr;
@@ -96,8 +95,6 @@ void DRW_hair_init(void)
/* Create VBO immediately to bind to texture buffer. */
GPU_vertbuf_use(g_dummy_vbo);
g_dummy_texture = GPU_texture_create_from_vertbuf("hair_dummy_attr", g_dummy_vbo);
g_dummy_curves_info = MEM_new<blender::draw::UniformBuffer<CurvesInfos>>(
"g_dummy_curves_info");
memset(g_dummy_curves_info->is_point_attribute,
@@ -266,15 +263,15 @@ DRWShadingGroup *DRW_shgroup_hair_create_sub(Object *object,
}
}
/* Fix issue with certain driver not drawing anything if there is no texture bound to
/* Fix issue with certain driver not drawing anything if there is nothing bound to
* "ac", "au", "u" or "c". */
if (hair_cache->num_uv_layers == 0) {
DRW_shgroup_uniform_texture(shgrp, "u", g_dummy_texture);
DRW_shgroup_uniform_texture(shgrp, "au", g_dummy_texture);
DRW_shgroup_buffer_texture(shgrp, "u", g_dummy_vbo);
DRW_shgroup_buffer_texture(shgrp, "au", g_dummy_vbo);
}
if (hair_cache->num_col_layers == 0) {
DRW_shgroup_uniform_texture(shgrp, "c", g_dummy_texture);
DRW_shgroup_uniform_texture(shgrp, "ac", g_dummy_texture);
DRW_shgroup_buffer_texture(shgrp, "c", g_dummy_vbo);
DRW_shgroup_buffer_texture(shgrp, "ac", g_dummy_vbo);
}
DRW_hair_duplimat_get(object, psys, md, dupli_mat);
@@ -314,7 +311,7 @@ DRWShadingGroup *DRW_shgroup_hair_create_sub(Object *object,
void DRW_hair_update()
{
if (!GPU_transform_feedback_support()) {
if (drw_hair_shader_type_get() == PART_REFINE_SHADER_TRANSFORM_FEEDBACK_WORKAROUND) {
/**
* Workaround to transform feedback not working on mac.
* On some system it crashes (see #58489) and on some other it renders garbage (see #60171).
@@ -433,6 +430,5 @@ void DRW_hair_update()
void DRW_hair_free(void)
{
GPU_VERTBUF_DISCARD_SAFE(g_dummy_vbo);
DRW_TEXTURE_FREE_SAFE(g_dummy_texture);
MEM_delete(g_dummy_curves_info);
}