diff options
Diffstat (limited to 'source/blender/gpu/intern/gpu_element.c')
-rw-r--r-- | source/blender/gpu/intern/gpu_element.c | 100 |
1 files changed, 99 insertions, 1 deletions
diff --git a/source/blender/gpu/intern/gpu_element.c b/source/blender/gpu/intern/gpu_element.c index 50e7df96503..6c9331b4903 100644 --- a/source/blender/gpu/intern/gpu_element.c +++ b/source/blender/gpu/intern/gpu_element.c @@ -162,6 +162,100 @@ void GPU_indexbuf_add_line_adj_verts( GPU_indexbuf_add_generic_vert(builder, v4); } +void GPU_indexbuf_set_point_vert(GPUIndexBufBuilder *builder, uint elem, uint v1) +{ + BLI_assert(builder->prim_type == GPU_PRIM_POINTS); + BLI_assert(elem < builder->max_index_len); + builder->data[elem++] = v1; + if (builder->index_len < elem) { + builder->index_len = elem; + } +} + +void GPU_indexbuf_set_line_verts(GPUIndexBufBuilder *builder, uint elem, uint v1, uint v2) +{ + BLI_assert(builder->prim_type == GPU_PRIM_LINES); + BLI_assert(v1 != v2); + BLI_assert(v1 <= builder->max_allowed_index); + BLI_assert(v2 <= builder->max_allowed_index); + BLI_assert((elem + 1) * 2 <= builder->max_index_len); + uint idx = elem * 2; + builder->data[idx++] = v1; + builder->data[idx++] = v2; + if (builder->index_len < idx) { + builder->index_len = idx; + } +} + +void GPU_indexbuf_set_tri_verts(GPUIndexBufBuilder *builder, uint elem, uint v1, uint v2, uint v3) +{ + BLI_assert(builder->prim_type == GPU_PRIM_TRIS); + BLI_assert(v1 != v2 && v2 != v3 && v3 != v1); + BLI_assert(v1 <= builder->max_allowed_index); + BLI_assert(v2 <= builder->max_allowed_index); + BLI_assert(v3 <= builder->max_allowed_index); + BLI_assert((elem + 1) * 3 <= builder->max_index_len); + uint idx = elem * 3; + builder->data[idx++] = v1; + builder->data[idx++] = v2; + builder->data[idx++] = v3; + if (builder->index_len < idx) { + builder->index_len = idx; + } +} + +void GPU_indexbuf_set_point_restart(GPUIndexBufBuilder *builder, uint elem) +{ + BLI_assert(builder->prim_type == GPU_PRIM_POINTS); + BLI_assert(elem < builder->max_index_len); + builder->data[elem++] = RESTART_INDEX; + if (builder->index_len < elem) { + builder->index_len = elem; + } +} + +void GPU_indexbuf_set_line_restart(GPUIndexBufBuilder *builder, uint elem) +{ + BLI_assert(builder->prim_type == GPU_PRIM_LINES); + BLI_assert((elem + 1) * 2 <= builder->max_index_len); + uint idx = elem * 2; + builder->data[idx++] = RESTART_INDEX; + builder->data[idx++] = RESTART_INDEX; + if (builder->index_len < idx) { + builder->index_len = idx; + } +} + +void GPU_indexbuf_set_tri_restart(GPUIndexBufBuilder *builder, uint elem) +{ + BLI_assert(builder->prim_type == GPU_PRIM_TRIS); + BLI_assert((elem + 1) * 3 <= builder->max_index_len); + uint idx = elem * 3; + builder->data[idx++] = RESTART_INDEX; + builder->data[idx++] = RESTART_INDEX; + builder->data[idx++] = RESTART_INDEX; + if (builder->index_len < idx) { + builder->index_len = idx; + } +} + +GPUIndexBuf *GPU_indexbuf_create_subrange(GPUIndexBuf *elem_src, uint start, uint length) +{ + GPUIndexBuf *elem = MEM_callocN(sizeof(GPUIndexBuf), "GPUIndexBuf"); + BLI_assert(elem_src && !elem_src->is_subrange); + BLI_assert(start + length <= elem_src->index_len); +#if GPU_TRACK_INDEX_RANGE + elem->index_type = elem_src->index_type; + elem->gl_index_type = elem_src->gl_index_type; + elem->base_index = elem_src->base_index; +#endif + elem->is_subrange = true; + elem->src = elem_src; + elem->index_start = start; + elem->index_len = length; + return elem; +} + #if GPU_TRACK_INDEX_RANGE /* Everything remains 32 bit while building to keep things simple. * Find min/max after, then convert to smallest index type possible. */ @@ -271,6 +365,10 @@ static void indexbuf_upload_data(GPUIndexBuf *elem) void GPU_indexbuf_use(GPUIndexBuf *elem) { + if (elem->is_subrange) { + GPU_indexbuf_use(elem->src); + return; + } if (elem->ibo_id == 0) { elem->ibo_id = GPU_buf_alloc(); } @@ -285,7 +383,7 @@ void GPU_indexbuf_discard(GPUIndexBuf *elem) if (elem->ibo_id) { GPU_buf_free(elem->ibo_id); } - if (elem->data) { + if (!elem->is_subrange && elem->data) { MEM_freeN(elem->data); } MEM_freeN(elem); |