diff options
Diffstat (limited to 'source/blender/draw/intern/draw_cache_impl_curves.cc')
-rw-r--r-- | source/blender/draw/intern/draw_cache_impl_curves.cc | 126 |
1 files changed, 94 insertions, 32 deletions
diff --git a/source/blender/draw/intern/draw_cache_impl_curves.cc b/source/blender/draw/intern/draw_cache_impl_curves.cc index 6e098e0310d..2460482fbbf 100644 --- a/source/blender/draw/intern/draw_cache_impl_curves.cc +++ b/source/blender/draw/intern/draw_cache_impl_curves.cc @@ -512,40 +512,41 @@ static bool curves_ensure_attributes(const Curves &curves, ThreadMutex *render_mutex = &cache.render_mutex; const CustomData *cd_curve = &curves.geometry.curve_data; const CustomData *cd_point = &curves.geometry.point_data; + CurvesEvalFinalCache &final_cache = cache.curves_cache.final[subdiv]; - DRW_Attributes attrs_needed; - drw_attributes_clear(&attrs_needed); - ListBase gpu_attrs = GPU_material_attributes(gpu_material); - LISTBASE_FOREACH (GPUMaterialAttribute *, gpu_attr, &gpu_attrs) { - const char *name = gpu_attr->name; - - int layer_index; - eCustomDataType type; - eAttrDomain domain; - if (drw_custom_data_match_attribute(cd_curve, name, &layer_index, &type)) { - domain = ATTR_DOMAIN_CURVE; - } - else if (drw_custom_data_match_attribute(cd_point, name, &layer_index, &type)) { - domain = ATTR_DOMAIN_POINT; - } - else { - continue; - } - - drw_attributes_add_request(&attrs_needed, name, type, layer_index, domain); - } + if (gpu_material) { + DRW_Attributes attrs_needed; + drw_attributes_clear(&attrs_needed); + ListBase gpu_attrs = GPU_material_attributes(gpu_material); + LISTBASE_FOREACH (GPUMaterialAttribute *, gpu_attr, &gpu_attrs) { + const char *name = gpu_attr->name; + + int layer_index; + eCustomDataType type; + eAttrDomain domain; + if (drw_custom_data_match_attribute(cd_curve, name, &layer_index, &type)) { + domain = ATTR_DOMAIN_CURVE; + } + else if (drw_custom_data_match_attribute(cd_point, name, &layer_index, &type)) { + domain = ATTR_DOMAIN_POINT; + } + else { + continue; + } - CurvesEvalFinalCache &final_cache = cache.curves_cache.final[subdiv]; + drw_attributes_add_request(&attrs_needed, name, type, layer_index, domain); + } - if (!drw_attributes_overlap(&final_cache.attr_used, &attrs_needed)) { - /* Some new attributes have been added, free all and start over. */ - for (const int i : IndexRange(GPU_MAX_ATTR)) { - GPU_VERTBUF_DISCARD_SAFE(cache.curves_cache.proc_attributes_buf[i]); - DRW_TEXTURE_FREE_SAFE(cache.curves_cache.proc_attributes_tex[i]); + if (!drw_attributes_overlap(&final_cache.attr_used, &attrs_needed)) { + /* Some new attributes have been added, free all and start over. */ + for (const int i : IndexRange(GPU_MAX_ATTR)) { + GPU_VERTBUF_DISCARD_SAFE(cache.curves_cache.proc_attributes_buf[i]); + DRW_TEXTURE_FREE_SAFE(cache.curves_cache.proc_attributes_tex[i]); + } + drw_attributes_merge(&final_cache.attr_used, &attrs_needed, render_mutex); } - drw_attributes_merge(&final_cache.attr_used, &attrs_needed, render_mutex); + drw_attributes_merge(&final_cache.attr_used_over_time, &attrs_needed, render_mutex); } - drw_attributes_merge(&final_cache.attr_used_over_time, &attrs_needed, render_mutex); bool need_tf_update = false; @@ -602,9 +603,7 @@ bool curves_ensure_procedural_data(Curves *curves, *curves, cache.curves_cache, thickness_res, subdiv); } - if (gpu_material) { - need_ft_update |= curves_ensure_attributes(*curves, cache, gpu_material, subdiv); - } + need_ft_update |= curves_ensure_attributes(*curves, cache, gpu_material, subdiv); return need_ft_update; } @@ -620,6 +619,69 @@ GPUBatch *DRW_curves_batch_cache_get_edit_points(Curves *curves) return DRW_batch_request(&cache.edit_points); } +static void request_attribute(Curves &curves, const char *name) +{ + CurvesBatchCache &cache = curves_batch_cache_get(curves); + const DRWContextState *draw_ctx = DRW_context_state_get(); + const Scene *scene = draw_ctx->scene; + const int subdiv = scene->r.hair_subdiv; + CurvesEvalFinalCache &final_cache = cache.curves_cache.final[subdiv]; + + DRW_Attributes attributes{}; + + CurveComponent component; + component.replace(&curves, GeometryOwnershipType::ReadOnly); + std::optional<AttributeMetaData> meta_data = component.attribute_get_meta_data(name); + if (!meta_data) { + return; + } + const eAttrDomain domain = meta_data->domain; + const eCustomDataType type = meta_data->data_type; + const CustomData &custom_data = domain == ATTR_DOMAIN_POINT ? curves.geometry.point_data : + curves.geometry.curve_data; + + drw_attributes_add_request( + &attributes, name, type, CustomData_get_named_layer(&custom_data, type, name), domain); + + drw_attributes_merge(&final_cache.attr_used, &attributes, &cache.render_mutex); +} + +GPUTexture **DRW_curves_texture_for_evaluated_attribute(Curves *curves, + const char *name, + bool *r_is_point_domain) +{ + CurvesBatchCache &cache = curves_batch_cache_get(*curves); + const DRWContextState *draw_ctx = DRW_context_state_get(); + const Scene *scene = draw_ctx->scene; + const int subdiv = scene->r.hair_subdiv; + CurvesEvalFinalCache &final_cache = cache.curves_cache.final[subdiv]; + + request_attribute(*curves, name); + + int request_i = -1; + for (const int i : IndexRange(final_cache.attr_used.num_requests)) { + if (STREQ(final_cache.attr_used.requests[i].attribute_name, name)) { + request_i = i; + break; + } + } + if (request_i == -1) { + *r_is_point_domain = false; + return nullptr; + } + switch (final_cache.attr_used.requests[request_i].domain) { + case ATTR_DOMAIN_POINT: + *r_is_point_domain = true; + return &final_cache.attributes_tex[request_i]; + case ATTR_DOMAIN_CURVE: + *r_is_point_domain = false; + return &cache.curves_cache.proc_attributes_tex[request_i]; + default: + BLI_assert_unreachable(); + return nullptr; + } +} + void DRW_curves_batch_cache_create_requested(Object *ob) { Curves *curves = static_cast<Curves *>(ob->data); |