diff options
-rw-r--r-- | source/blender/draw/intern/draw_cache_impl_displist.c | 1 | ||||
-rw-r--r-- | source/blender/gpu/GPU_vertex_buffer.h | 15 | ||||
-rw-r--r-- | source/blender/gpu/GPU_vertex_format.h | 55 | ||||
-rw-r--r-- | source/blender/gpu/intern/gpu_attr_binding.c | 3 | ||||
-rw-r--r-- | source/blender/gpu/intern/gpu_batch.c | 3 | ||||
-rw-r--r-- | source/blender/gpu/intern/gpu_vertex_format.c | 90 |
6 files changed, 63 insertions, 104 deletions
diff --git a/source/blender/draw/intern/draw_cache_impl_displist.c b/source/blender/draw/intern/draw_cache_impl_displist.c index 6825b52963b..d1c214c2aa6 100644 --- a/source/blender/draw/intern/draw_cache_impl_displist.c +++ b/source/blender/draw/intern/draw_cache_impl_displist.c @@ -404,7 +404,6 @@ void DRW_displist_vertbuf_create_loop_pos_and_nor_and_uv(ListBase *lb, &format_pos_nor, "pos", GPU_COMP_F32, 3, GPU_FETCH_FLOAT); attr_id.nor = GPU_vertformat_attr_add( &format_pos_nor, "nor", GPU_COMP_I10, 3, GPU_FETCH_INT_TO_FLOAT_UNIT); - GPU_vertformat_triple_load(&format_pos_nor); /* UVs are in [0..1] range. We can compress them. */ attr_id.uv = GPU_vertformat_attr_add( &format_uv, "u", GPU_COMP_I16, 2, GPU_FETCH_INT_TO_FLOAT_UNIT); diff --git a/source/blender/gpu/GPU_vertex_buffer.h b/source/blender/gpu/GPU_vertex_buffer.h index a5a5e3d4296..3e178e193dc 100644 --- a/source/blender/gpu/GPU_vertex_buffer.h +++ b/source/blender/gpu/GPU_vertex_buffer.h @@ -48,12 +48,17 @@ typedef enum { typedef struct GPUVertBuf { GPUVertFormat format; - uint vertex_len; /* number of verts we want to draw */ - uint vertex_alloc; /* number of verts data */ - bool dirty; + /** Number of verts we want to draw. */ + uint vertex_len; + /** Number of verts data. */ + uint vertex_alloc; + /** 0 indicates not yet allocated. */ + uint32_t vbo_id; + /** Usage hint for GL optimisation. */ + uint usage : 2; + /** Data has been touched and need to be reuploaded to GPU. */ + uint dirty : 1; unsigned char *data; /* NULL indicates data in VRAM (unmapped) */ - uint32_t vbo_id; /* 0 indicates not yet allocated */ - GPUUsageType usage; /* usage hint for GL optimisation */ } GPUVertBuf; GPUVertBuf *GPU_vertbuf_create(GPUUsageType); diff --git a/source/blender/gpu/GPU_vertex_format.h b/source/blender/gpu/GPU_vertex_format.h index 7f1934431cf..74fad51f571 100644 --- a/source/blender/gpu/GPU_vertex_format.h +++ b/source/blender/gpu/GPU_vertex_format.h @@ -27,6 +27,7 @@ #define __GPU_VERTEX_FORMAT_H__ #include "GPU_common.h" +#include "BLI_compiler_compat.h" #define GPU_VERT_ATTR_MAX_LEN 16 #define GPU_VERT_ATTR_MAX_NAMES 4 @@ -54,28 +55,35 @@ typedef enum { } GPUVertFetchMode; typedef struct GPUVertAttr { - GPUVertFetchMode fetch_mode; - GPUVertCompType comp_type; + GPUVertFetchMode fetch_mode : 2; + GPUVertCompType comp_type : 3; + /* 1 to 4 or 8 or 12 or 16 */ + uint comp_len : 5; + /* size in bytes, 1 to 64 */ + uint sz : 7; + /* from beginning of vertex, in bytes */ + uint offset : 11; + /* up to GPU_VERT_ATTR_MAX_NAMES */ + uint name_len : 3; uint gl_comp_type; - uint comp_len; /* 1 to 4 or 8 or 12 or 16 */ - uint sz; /* size in bytes, 1 to 64 */ - uint offset; /* from beginning of vertex, in bytes */ - uint name_len; /* up to GPU_VERT_ATTR_MAX_NAMES */ - const char *name[GPU_VERT_ATTR_MAX_NAMES]; + /* -- 8 Bytes -- */ + uchar names[GPU_VERT_ATTR_MAX_NAMES]; } GPUVertAttr; typedef struct GPUVertFormat { /** 0 to 16 (GPU_VERT_ATTR_MAX_LEN). */ - uint attr_len; + uint attr_len : 5; /** Total count of active vertex attribute. */ - uint name_len; - /** Stride in bytes, 1 to 256. */ - uint stride; - uint name_offset; - bool packed; - char names[GPU_VERT_ATTR_NAMES_BUF_LEN]; - /** TODO: variable-size array */ + uint name_len : 5; + /** Stride in bytes, 1 to 1024. */ + uint stride : 11; + /** Has the format been packed. */ + uint packed : 1; + /** Current offset in names[]. */ + uint name_offset : 8; + GPUVertAttr attrs[GPU_VERT_ATTR_MAX_LEN]; + char names[GPU_VERT_ATTR_NAMES_BUF_LEN]; } GPUVertFormat; struct GPUShaderInterface; @@ -88,18 +96,15 @@ void GPU_vertformat_from_interface(GPUVertFormat *format, uint GPU_vertformat_attr_add( GPUVertFormat *, const char *name, GPUVertCompType, uint comp_len, GPUVertFetchMode); void GPU_vertformat_alias_add(GPUVertFormat *, const char *alias); + int GPU_vertformat_attr_id_get(const GPUVertFormat *, const char *name); -/** - * This makes the "virtual" attributes with suffixes "0", "1", "2" - * to access triangle data in the vertex shader. - * - * IMPORTANT: - * - Call this before creating the vertex buffer and after creating all attributes - * - Only first vertex out of 3 has the correct information. - * Use flat output with #GL_FIRST_VERTEX_CONVENTION. - */ -void GPU_vertformat_triple_load(GPUVertFormat *format); +BLI_INLINE const char *GPU_vertformat_attr_name_get(const GPUVertFormat *format, + const GPUVertAttr *attr, + uint n_idx) +{ + return format->names + attr->names[n_idx]; +} /* format conversion */ diff --git a/source/blender/gpu/intern/gpu_attr_binding.c b/source/blender/gpu/intern/gpu_attr_binding.c index e280b77f661..802b15a0c4e 100644 --- a/source/blender/gpu/intern/gpu_attr_binding.c +++ b/source/blender/gpu/intern/gpu_attr_binding.c @@ -70,7 +70,8 @@ void get_attr_locations(const GPUVertFormat *format, for (uint a_idx = 0; a_idx < format->attr_len; ++a_idx) { const GPUVertAttr *a = &format->attrs[a_idx]; for (uint n_idx = 0; n_idx < a->name_len; ++n_idx) { - const GPUShaderInput *input = GPU_shaderinterface_attr(shaderface, a->name[n_idx]); + const char *name = GPU_vertformat_attr_name_get(format, a, n_idx); + const GPUShaderInput *input = GPU_shaderinterface_attr(shaderface, name); #if TRUST_NO_ONE assert(input != NULL); /* TODO: make this a recoverable runtime error? diff --git a/source/blender/gpu/intern/gpu_batch.c b/source/blender/gpu/intern/gpu_batch.c index 010f57bf5f8..45697befe50 100644 --- a/source/blender/gpu/intern/gpu_batch.c +++ b/source/blender/gpu/intern/gpu_batch.c @@ -370,7 +370,8 @@ static void create_bindings(GPUVertBuf *verts, const GLvoid *pointer = (const GLubyte *)0 + a->offset + v_first * stride; for (uint n_idx = 0; n_idx < a->name_len; ++n_idx) { - const GPUShaderInput *input = GPU_shaderinterface_attr(interface, a->name[n_idx]); + const char *name = GPU_vertformat_attr_name_get(format, a, n_idx); + const GPUShaderInput *input = GPU_shaderinterface_attr(interface, name); if (input == NULL) { continue; diff --git a/source/blender/gpu/intern/gpu_vertex_format.c b/source/blender/gpu/intern/gpu_vertex_format.c index 388773afbbc..82ae7dd4021 100644 --- a/source/blender/gpu/intern/gpu_vertex_format.c +++ b/source/blender/gpu/intern/gpu_vertex_format.c @@ -58,12 +58,6 @@ void GPU_vertformat_copy(GPUVertFormat *dest, const GPUVertFormat *src) { /* copy regular struct fields */ memcpy(dest, src, sizeof(GPUVertFormat)); - - for (uint i = 0; i < dest->attr_len; i++) { - for (uint j = 0; j < dest->attrs[i].name_len; j++) { - dest->attrs[i].name[j] = (char *)dest + (src->attrs[i].name[j] - ((char *)src)); - } - } } static GLenum convert_comp_type_to_gl(GPUVertCompType type) @@ -122,32 +116,20 @@ uint vertex_buffer_size(const GPUVertFormat *format, uint vertex_len) return format->stride * vertex_len; } -static const char *copy_attr_name(GPUVertFormat *format, const char *name, const char *suffix) +static const char copy_attr_name(GPUVertFormat *format, const char *name) { /* strncpy does 110% of what we need; let's do exactly 100% */ - char *name_copy = format->names + format->name_offset; - uint available = GPU_VERT_ATTR_NAMES_BUF_LEN - format->name_offset; + uchar name_offset = format->name_offset; + char *name_copy = format->names + name_offset; + uint available = GPU_VERT_ATTR_NAMES_BUF_LEN - name_offset; bool terminated = false; for (uint i = 0; i < available; ++i) { const char c = name[i]; name_copy[i] = c; if (c == '\0') { - if (suffix) { - for (uint j = 0; j < available; ++j) { - const char s = suffix[j]; - name_copy[i + j] = s; - if (s == '\0') { - terminated = true; - format->name_offset += (i + j + 1); - break; - } - } - } - else { - terminated = true; - format->name_offset += (i + 1); - } + terminated = true; + format->name_offset += (i + 1); break; } } @@ -157,7 +139,7 @@ static const char *copy_attr_name(GPUVertFormat *format, const char *name, const #else (void)terminated; #endif - return name_copy; + return name_offset; } uint GPU_vertformat_attr_add(GPUVertFormat *format, @@ -196,7 +178,7 @@ uint GPU_vertformat_attr_add(GPUVertFormat *format, const uint attr_id = format->attr_len++; GPUVertAttr *attr = &format->attrs[attr_id]; - attr->name[attr->name_len++] = copy_attr_name(format, name, NULL); + attr->names[attr->name_len++] = copy_attr_name(format, name); attr->comp_type = comp_type; attr->gl_comp_type = convert_comp_type_to_gl(comp_type); attr->comp_len = (comp_type == GPU_COMP_I10) ? @@ -217,7 +199,7 @@ void GPU_vertformat_alias_add(GPUVertFormat *format, const char *alias) assert(attr->name_len < GPU_VERT_ATTR_MAX_NAMES); #endif format->name_len++; /* multiname support */ - attr->name[attr->name_len++] = copy_attr_name(format, alias, NULL); + attr->names[attr->name_len++] = copy_attr_name(format, alias); } int GPU_vertformat_attr_id_get(const GPUVertFormat *format, const char *name) @@ -225,7 +207,8 @@ int GPU_vertformat_attr_id_get(const GPUVertFormat *format, const char *name) for (int i = 0; i < format->attr_len; i++) { const GPUVertAttr *attr = &format->attrs[i]; for (int j = 0; j < attr->name_len; j++) { - if (STREQ(name, attr->name[j])) { + const char *attr_name = GPU_vertformat_attr_name_get(format, attr, j); + if (STREQ(name, attr_name)) { return i; } } @@ -233,41 +216,6 @@ int GPU_vertformat_attr_id_get(const GPUVertFormat *format, const char *name) return -1; } -void GPU_vertformat_triple_load(GPUVertFormat *format) -{ -#if TRUST_NO_ONE - assert(!format->packed); - assert(format->attr_len * 3 < GPU_VERT_ATTR_MAX_LEN); - assert(format->name_len + format->attr_len * 3 < GPU_VERT_ATTR_MAX_LEN); -#endif - - VertexFormat_pack(format); - - uint old_attr_len = format->attr_len; - for (uint a_idx = 0; a_idx < old_attr_len; ++a_idx) { - GPUVertAttr *attr = &format->attrs[a_idx]; - /* Duplicate attr twice */ - for (int i = 1; i < 3; ++i) { - GPUVertAttr *dst_attr = &format->attrs[format->attr_len]; - memcpy(dst_attr, attr, sizeof(GPUVertAttr)); - /* Increase offset to the next vertex. */ - dst_attr->offset += format->stride * i; - /* Only copy first name for now. */ - dst_attr->name_len = 0; - dst_attr->name[dst_attr->name_len++] = copy_attr_name( - format, attr->name[0], (i == 1) ? "1" : "2"); - format->attr_len++; - } - -#if TRUST_NO_ONE - assert(attr->name_len < GPU_VERT_ATTR_MAX_NAMES); -#endif - /* Add alias to first attr. */ - format->name_len++; - attr->name[attr->name_len++] = copy_attr_name(format, attr->name[0], "0"); - } -} - uint padding(uint offset, uint alignment) { const uint mod = offset % alignment; @@ -364,7 +312,6 @@ static uint calc_input_component_size(const GPUShaderInput *input) static void get_fetch_mode_and_comp_type(int gl_type, GPUVertCompType *r_comp_type, - uint *r_gl_comp_type, GPUVertFetchMode *r_fetch_mode) { switch (gl_type) { @@ -382,7 +329,6 @@ static void get_fetch_mode_and_comp_type(int gl_type, case GL_FLOAT_MAT4x2: case GL_FLOAT_MAT4x3: *r_comp_type = GPU_COMP_F32; - *r_gl_comp_type = GL_FLOAT; *r_fetch_mode = GPU_FETCH_FLOAT; break; case GL_INT: @@ -390,7 +336,6 @@ static void get_fetch_mode_and_comp_type(int gl_type, case GL_INT_VEC3: case GL_INT_VEC4: *r_comp_type = GPU_COMP_I32; - *r_gl_comp_type = GL_INT; *r_fetch_mode = GPU_FETCH_INT; break; case GL_UNSIGNED_INT: @@ -398,7 +343,6 @@ static void get_fetch_mode_and_comp_type(int gl_type, case GL_UNSIGNED_INT_VEC3: case GL_UNSIGNED_INT_VEC4: *r_comp_type = GPU_COMP_U32; - *r_gl_comp_type = GL_UNSIGNED_INT; *r_fetch_mode = GPU_FETCH_INT; break; default: @@ -424,15 +368,19 @@ void GPU_vertformat_from_interface(GPUVertFormat *format, const GPUShaderInterfa format->name_len++; /* multiname support */ format->attr_len++; + GPUVertCompType comp_type; + GPUVertFetchMode fetch_mode; + get_fetch_mode_and_comp_type(input->gl_type, &comp_type, &fetch_mode); + GPUVertAttr *attr = &format->attrs[input->location]; - attr->name[attr->name_len++] = copy_attr_name( - format, name_buffer + input->name_offset, NULL); + attr->names[attr->name_len++] = copy_attr_name(format, name_buffer + input->name_offset); attr->offset = 0; /* offsets & stride are calculated later (during pack) */ attr->comp_len = calc_input_component_size(input); attr->sz = attr->comp_len * 4; - get_fetch_mode_and_comp_type( - input->gl_type, &attr->comp_type, &attr->gl_comp_type, &attr->fetch_mode); + attr->fetch_mode = fetch_mode; + attr->comp_type = comp_type; + attr->gl_comp_type = convert_comp_type_to_gl(comp_type); } } } |