diff options
author | Colin Basnett <cmbasnett@gmail.com> | 2022-09-17 03:50:37 +0300 |
---|---|---|
committer | Colin Basnett <cmbasnett@gmail.com> | 2022-09-17 03:50:37 +0300 |
commit | 564bda241a973396da51d7c3ccd9efd97d51728a (patch) | |
tree | 4d9aa4cccd82e2e606b47774afa5e1015bf14768 /source/blender/draw/intern/draw_cache_impl_particles.c | |
parent | 0fff238150d076576053c25b646f653d6e3b0edb (diff) | |
parent | 48d7ff68f0df209c77bbb081ab46fbc109fd825a (diff) |
Merge branch 'master' into feature-imformatfeature-imformat
Diffstat (limited to 'source/blender/draw/intern/draw_cache_impl_particles.c')
-rw-r--r-- | source/blender/draw/intern/draw_cache_impl_particles.c | 77 |
1 files changed, 60 insertions, 17 deletions
diff --git a/source/blender/draw/intern/draw_cache_impl_particles.c b/source/blender/draw/intern/draw_cache_impl_particles.c index c1d609bf648..9c1784b1de2 100644 --- a/source/blender/draw/intern/draw_cache_impl_particles.c +++ b/source/blender/draw/intern/draw_cache_impl_particles.c @@ -11,6 +11,7 @@ #include "MEM_guardedalloc.h" +#include "BLI_alloca.h" #include "BLI_ghash.h" #include "BLI_math_vector.h" #include "BLI_string.h" @@ -24,12 +25,15 @@ #include "BKE_customdata.h" #include "BKE_mesh.h" +#include "BKE_mesh_legacy_convert.h" #include "BKE_particle.h" #include "BKE_pointcache.h" #include "ED_particle.h" #include "GPU_batch.h" +#include "GPU_capabilities.h" +#include "GPU_context.h" #include "GPU_material.h" #include "DEG_depsgraph_query.h" @@ -181,10 +185,11 @@ static void particle_batch_cache_clear_hair(ParticleHairCache *hair_cache) GPU_VERTBUF_DISCARD_SAFE(hair_cache->proc_uv_buf[i]); DRW_TEXTURE_FREE_SAFE(hair_cache->uv_tex[i]); } - for (int i = 0; i < MAX_MCOL; i++) { + for (int i = 0; i < hair_cache->num_col_layers; i++) { GPU_VERTBUF_DISCARD_SAFE(hair_cache->proc_col_buf[i]); DRW_TEXTURE_FREE_SAFE(hair_cache->col_tex[i]); } + for (int i = 0; i < MAX_HAIR_SUBDIV; i++) { GPU_VERTBUF_DISCARD_SAFE(hair_cache->final[i].proc_buf); DRW_TEXTURE_FREE_SAFE(hair_cache->final[i].proc_tex); @@ -217,9 +222,24 @@ static void particle_batch_cache_clear(ParticleSystem *psys) GPU_VERTBUF_DISCARD_SAFE(cache->edit_tip_pos); } +static void particle_batch_cache_free_hair(ParticleHairCache *hair) +{ + MEM_SAFE_FREE(hair->proc_col_buf); + MEM_SAFE_FREE(hair->col_tex); + MEM_SAFE_FREE(hair->col_layer_names); +} + void DRW_particle_batch_cache_free(ParticleSystem *psys) { particle_batch_cache_clear(psys); + + ParticleBatchCache *cache = psys->batch_cache; + + if (cache) { + particle_batch_cache_free_hair(&cache->hair); + particle_batch_cache_free_hair(&cache->edit_hair); + } + MEM_SAFE_FREE(psys->batch_cache); } @@ -295,7 +315,8 @@ static void particle_calculate_parent_uvs(ParticleSystem *psys, } } if (!ELEM(num, DMCACHE_NOTFOUND, DMCACHE_ISCHILD)) { - MFace *mface = &psmd->mesh_final->mface[num]; + MFace *mfaces = CustomData_get_layer(&psmd->mesh_final->fdata, CD_MFACE); + MFace *mface = &mfaces[num]; for (int j = 0; j < num_uv_layers; j++) { psys_interpolate_uvs(mtfaces[j] + num, mface->v4, particle->fuv, r_uv[j]); } @@ -324,7 +345,8 @@ static void particle_calculate_parent_mcol(ParticleSystem *psys, } } if (!ELEM(num, DMCACHE_NOTFOUND, DMCACHE_ISCHILD)) { - MFace *mface = &psmd->mesh_final->mface[num]; + MFace *mfaces = CustomData_get_layer(&psmd->mesh_final->fdata, CD_MFACE); + MFace *mface = &mfaces[num]; for (int j = 0; j < num_col_layers; j++) { /* CustomDataLayer CD_MCOL has 4 structs per face. */ psys_interpolate_mcol(mcols[j] + num * 4, mface->v4, particle->fuv, &r_mcol[j]); @@ -350,7 +372,8 @@ static void particle_interpolate_children_uvs(ParticleSystem *psys, ChildParticle *particle = &psys->child[child_index]; int num = particle->num; if (num != DMCACHE_NOTFOUND) { - MFace *mface = &psmd->mesh_final->mface[num]; + MFace *mfaces = CustomData_get_layer(&psmd->mesh_final->fdata, CD_MFACE); + MFace *mface = &mfaces[num]; for (int j = 0; j < num_uv_layers; j++) { psys_interpolate_uvs(mtfaces[j] + num, mface->v4, particle->fuv, r_uv[j]); } @@ -374,7 +397,8 @@ static void particle_interpolate_children_mcol(ParticleSystem *psys, ChildParticle *particle = &psys->child[child_index]; int num = particle->num; if (num != DMCACHE_NOTFOUND) { - MFace *mface = &psmd->mesh_final->mface[num]; + MFace *mfaces = CustomData_get_layer(&psmd->mesh_final->fdata, CD_MFACE); + MFace *mface = &mfaces[num]; for (int j = 0; j < num_col_layers; j++) { /* CustomDataLayer CD_MCOL has 4 structs per face. */ psys_interpolate_mcol(mcols[j] + num * 4, mface->v4, particle->fuv, &r_mcol[j]); @@ -790,7 +814,10 @@ static void particle_batch_cache_ensure_procedural_final_points(ParticleHairCach GPUVertFormat format = {0}; GPU_vertformat_attr_add(&format, "pos", GPU_COMP_F32, 4, GPU_FETCH_FLOAT); - cache->final[subdiv].proc_buf = GPU_vertbuf_create_with_format(&format); + /* Transform feedback buffer only needs to be resident in device memory. */ + GPUUsageType type = GPU_transform_feedback_support() ? GPU_USAGE_DEVICE_ONLY : GPU_USAGE_STATIC; + cache->final[subdiv].proc_buf = GPU_vertbuf_create_with_format_ex( + &format, type | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); /* Create a destination buffer for the transform feedback. Sized appropriately */ /* Those are points! not line segments. */ @@ -832,10 +859,10 @@ static void particle_batch_cache_ensure_procedural_strand_data(PTCacheEdit *edit GPUVertBufRaw data_step, seg_step; GPUVertBufRaw uv_step[MAX_MTFACE]; - GPUVertBufRaw col_step[MAX_MCOL]; + GPUVertBufRaw *col_step = BLI_array_alloca(col_step, cache->num_col_layers); const MTFace *mtfaces[MAX_MTFACE] = {NULL}; - const MCol *mcols[MAX_MCOL] = {NULL}; + const MCol **mcols = BLI_array_alloca(mcols, cache->num_col_layers); float(**parent_uvs)[2] = NULL; MCol **parent_mcol = NULL; @@ -853,20 +880,22 @@ static void particle_batch_cache_ensure_procedural_strand_data(PTCacheEdit *edit &format_col, "col", GPU_COMP_U16, 4, GPU_FETCH_INT_TO_FLOAT_UNIT); memset(cache->uv_layer_names, 0, sizeof(cache->uv_layer_names)); - memset(cache->col_layer_names, 0, sizeof(cache->col_layer_names)); /* Strand Data */ - cache->proc_strand_buf = GPU_vertbuf_create_with_format(&format_data); + cache->proc_strand_buf = GPU_vertbuf_create_with_format_ex( + &format_data, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_strand_buf, cache->strands_len); GPU_vertbuf_attr_get_raw_data(cache->proc_strand_buf, data_id, &data_step); - cache->proc_strand_seg_buf = GPU_vertbuf_create_with_format(&format_seg); + cache->proc_strand_seg_buf = GPU_vertbuf_create_with_format_ex( + &format_seg, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_strand_seg_buf, cache->strands_len); GPU_vertbuf_attr_get_raw_data(cache->proc_strand_seg_buf, seg_id, &seg_step); /* UV layers */ for (int i = 0; i < cache->num_uv_layers; i++) { - cache->proc_uv_buf[i] = GPU_vertbuf_create_with_format(&format_uv); + cache->proc_uv_buf[i] = GPU_vertbuf_create_with_format_ex( + &format_uv, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_uv_buf[i], cache->strands_len); GPU_vertbuf_attr_get_raw_data(cache->proc_uv_buf[i], uv_id, &uv_step[i]); @@ -884,9 +913,20 @@ static void particle_batch_cache_ensure_procedural_strand_data(PTCacheEdit *edit BLI_strncpy(cache->uv_layer_names[i][n++], "a", MAX_LAYER_NAME_LEN); } } + + MEM_SAFE_FREE(cache->proc_col_buf); + MEM_SAFE_FREE(cache->col_tex); + MEM_SAFE_FREE(cache->col_layer_names); + + cache->proc_col_buf = MEM_calloc_arrayN(cache->num_col_layers, sizeof(void *), "proc_col_buf"); + cache->col_tex = MEM_calloc_arrayN(cache->num_col_layers, sizeof(void *), "col_tex"); + cache->col_layer_names = MEM_calloc_arrayN( + cache->num_col_layers, sizeof(*cache->col_layer_names), "col_layer_names"); + /* Vertex colors */ for (int i = 0; i < cache->num_col_layers; i++) { - cache->proc_col_buf[i] = GPU_vertbuf_create_with_format(&format_col); + cache->proc_col_buf[i] = GPU_vertbuf_create_with_format_ex( + &format_col, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_col_buf[i], cache->strands_len); GPU_vertbuf_attr_get_raw_data(cache->proc_col_buf[i], col_id, &col_step[i]); @@ -1032,8 +1072,9 @@ static void particle_batch_cache_ensure_procedural_indices(PTCacheEdit *edit, static GPUVertFormat format = {0}; GPU_vertformat_clear(&format); - /* initialize vertex format */ - GPU_vertformat_attr_add(&format, "dummy", GPU_COMP_U8, 1, GPU_FETCH_INT_TO_FLOAT_UNIT); + /* NOTE: initialize vertex format. Using GPU_COMP_U32 to satisfy Metal's 4-byte minimum + * stride requirement. */ + GPU_vertformat_attr_add(&format, "dummy", GPU_COMP_U32, 1, GPU_FETCH_INT_TO_FLOAT_UNIT); GPUVertBuf *vbo = GPU_vertbuf_create_with_format(&format); GPU_vertbuf_data_alloc(vbo, 1); @@ -1074,7 +1115,8 @@ static void particle_batch_cache_ensure_procedural_pos(PTCacheEdit *edit, uint pos_id = GPU_vertformat_attr_add( &pos_format, "posTime", GPU_COMP_F32, 4, GPU_FETCH_FLOAT); - cache->proc_point_buf = GPU_vertbuf_create_with_format(&pos_format); + cache->proc_point_buf = GPU_vertbuf_create_with_format_ex( + &pos_format, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_point_buf, cache->point_len); GPUVertBufRaw pos_step; @@ -1084,7 +1126,8 @@ static void particle_batch_cache_ensure_procedural_pos(PTCacheEdit *edit, uint length_id = GPU_vertformat_attr_add( &length_format, "hairLength", GPU_COMP_F32, 1, GPU_FETCH_FLOAT); - cache->proc_length_buf = GPU_vertbuf_create_with_format(&length_format); + cache->proc_length_buf = GPU_vertbuf_create_with_format_ex( + &length_format, GPU_USAGE_STATIC | GPU_USAGE_FLAG_BUFFER_TEXTURE_ONLY); GPU_vertbuf_data_alloc(cache->proc_length_buf, cache->strands_len); GPUVertBufRaw length_step; |