[Bf-blender-cvs] [b9a7b40924f] master: Geometry Nodes: Get attribute domain and type without allocation

Hans Goudey noreply at git.blender.org
Thu Apr 22 15:05:11 CEST 2021


Commit: b9a7b40924f6284af5867cb63078dc79c714a675
Author: Hans Goudey
Date:   Thu Apr 22 08:05:02 2021 -0500
Branches: master
https://developer.blender.org/rBb9a7b40924f6284af5867cb63078dc79c714a675

Geometry Nodes: Get attribute domain and type without allocation

Because we use virtual classes (and for other reasons), we had to do a
small allocation when simply retrieving the data type and domain of an
existing attribute. This happened quite a lot actually-- to determine
these values for result attributes.

This patch adds a simple function to retrieve this meta data without
building the virtual array. This should lower the overhead of every
attribute node, though the difference probably won't be noticible
unless a tree has very many nodes.

Differential Revision: https://developer.blender.org/D11047

===================================================================

M	source/blender/blenkernel/BKE_geometry_set.hh
M	source/blender/blenkernel/intern/attribute_access.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_clamp.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_color_ramp.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_combine_xyz.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_compare.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_convert.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_fill.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_map_range.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_math.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_mix.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_randomize.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_sample_texture.cc
M	source/blender/nodes/geometry/nodes/node_geo_attribute_separate_xyz.cc
M	source/blender/nodes/geometry/nodes/node_geo_point_distribute.cc
M	source/blender/nodes/intern/node_geometry_exec.cc

===================================================================

diff --git a/source/blender/blenkernel/BKE_geometry_set.hh b/source/blender/blenkernel/BKE_geometry_set.hh
index 38f692fee0e..e9545cba1f1 100644
--- a/source/blender/blenkernel/BKE_geometry_set.hh
+++ b/source/blender/blenkernel/BKE_geometry_set.hh
@@ -102,6 +102,10 @@ class GeometryComponent {
   /* Return true when any attribute with this name exists, including built in attributes. */
   bool attribute_exists(const blender::StringRef attribute_name) const;
 
+  /* Return the data type and domain of an attribute with the given name if it exists. */
+  std::optional<AttributeMetaData> attribute_get_meta_data(
+      const blender::StringRef attribute_name) const;
+
   /* Returns true when the geometry component supports this attribute domain. */
   bool attribute_domain_supported(const AttributeDomain domain) const;
   /* Can only be used with supported domain types. */
diff --git a/source/blender/blenkernel/intern/attribute_access.cc b/source/blender/blenkernel/intern/attribute_access.cc
index 3b2ee126d91..571763e3719 100644
--- a/source/blender/blenkernel/intern/attribute_access.cc
+++ b/source/blender/blenkernel/intern/attribute_access.cc
@@ -729,6 +729,20 @@ bool GeometryComponent::attribute_exists(const blender::StringRef attribute_name
   return false;
 }
 
+std::optional<AttributeMetaData> GeometryComponent::attribute_get_meta_data(
+    const StringRef attribute_name) const
+{
+  std::optional<AttributeMetaData> result{std::nullopt};
+  this->attribute_foreach([&](StringRefNull name, const AttributeMetaData &meta_data) {
+    if (attribute_name == name) {
+      result = meta_data;
+      return false;
+    }
+    return true;
+  });
+  return result;
+}
+
 static std::unique_ptr<blender::fn::GVArray> try_adapt_data_type(
     std::unique_ptr<blender::fn::GVArray> varray, const blender::fn::CPPType &to_type)
 {
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_clamp.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_clamp.cc
index e7677ed41e1..1943971d49f 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_clamp.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_clamp.cc
@@ -126,13 +126,13 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef source_name,
                                          StringRef result_name)
 {
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;
   }
-  ReadAttributeLookup source_attribute = component.attribute_try_get_for_read(source_name);
-  if (source_attribute) {
-    return source_attribute.domain;
+  std::optional<AttributeMetaData> source_info = component.attribute_get_meta_data(source_name);
+  if (source_info) {
+    return source_info->domain;
   }
   return ATTR_DOMAIN_POINT;
 }
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_color_ramp.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_color_ramp.cc
index af65fe110e9..9e697226a01 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_color_ramp.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_color_ramp.cc
@@ -47,15 +47,15 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef result_name)
 {
   /* Use the domain of the result attribute if it already exists. */
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;
   }
 
   /* Otherwise use the input attribute's domain if it exists. */
-  ReadAttributeLookup input_attribute = component.attribute_try_get_for_read(input_name);
-  if (input_attribute) {
-    return input_attribute.domain;
+  std::optional<AttributeMetaData> source_info = component.attribute_get_meta_data(input_name);
+  if (source_info) {
+    return source_info->domain;
   }
 
   return ATTR_DOMAIN_POINT;
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_combine_xyz.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_combine_xyz.cc
index c3db26c7299..69e628267a4 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_combine_xyz.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_combine_xyz.cc
@@ -77,9 +77,9 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef result_name)
 {
   /* Use the domain of the result attribute if it already exists. */
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;
   }
 
   /* Otherwise use the highest priority domain from existing input attributes, or the default. */
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_compare.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_compare.cc
index 22855787ab0..ccfaeb9bb47 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_compare.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_compare.cc
@@ -234,9 +234,9 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef result_name)
 {
   /* Use the domain of the result attribute if it already exists. */
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;
   }
 
   /* Otherwise use the highest priority domain from existing input attributes, or the default. */
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_convert.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_convert.cc
index bb46c5c84cd..60bb27191b4 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_convert.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_convert.cc
@@ -55,13 +55,13 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef source_name,
                                          StringRef result_name)
 {
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;
   }
-  ReadAttributeLookup source_attribute = component.attribute_try_get_for_read(source_name);
-  if (source_attribute) {
-    return source_attribute.domain;
+  std::optional<AttributeMetaData> source_info = component.attribute_get_meta_data(source_name);
+  if (source_info) {
+    return source_info->domain;
   }
   return ATTR_DOMAIN_POINT;
 }
@@ -75,14 +75,14 @@ static bool conversion_can_be_skipped(const GeometryComponent &component,
   if (source_name != result_name) {
     return false;
   }
-  ReadAttributeLookup read_attribute = component.attribute_try_get_for_read(source_name);
-  if (!read_attribute) {
+  std::optional<AttributeMetaData> info = component.attribute_get_meta_data(result_name);
+  if (!info) {
     return false;
   }
-  if (read_attribute.domain != result_domain) {
+  if (info->domain != result_domain) {
     return false;
   }
-  if (read_attribute.varray->type() != *bke::custom_data_type_to_cpp_type(result_type)) {
+  if (info->data_type != result_type) {
     return false;
   }
   return true;
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_fill.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_fill.cc
index 8287313e400..3df64625b99 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_fill.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_fill.cc
@@ -68,13 +68,12 @@ static void geo_node_attribute_fill_update(bNodeTree *UNUSED(ntree), bNode *node
 
 namespace blender::nodes {
 
-static AttributeDomain get_result_domain(const GeometryComponent &component,
-                                         StringRef attribute_name)
+static AttributeDomain get_result_domain(const GeometryComponent &component, const StringRef name)
 {
   /* Use the domain of the result attribute if it already exists. */
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(attribute_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(name);
+  if (result_info) {
+    return result_info->domain;
   }
   return ATTR_DOMAIN_POINT;
 }
diff --git a/source/blender/nodes/geometry/nodes/node_geo_attribute_map_range.cc b/source/blender/nodes/geometry/nodes/node_geo_attribute_map_range.cc
index 4a98d6caed2..5d82897e9db 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_attribute_map_range.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_attribute_map_range.cc
@@ -318,13 +318,13 @@ static AttributeDomain get_result_domain(const GeometryComponent &component,
                                          StringRef source_name,
                                          StringRef result_name)
 {
-  ReadAttributeLookup result_attribute = component.attribute_try_get_for_read(result_name);
-  if (result_attribute) {
-    return result_attribute.domain;
+  std::optional<AttributeMetaData> result_info = component.attribute_get_meta_data(result_name);
+  if (result_info) {
+    return result_info->domain;


@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list