Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJacques Lucke <jacques@blender.org>2021-03-30 13:34:05 +0300
committerJacques Lucke <jacques@blender.org>2021-03-30 13:34:16 +0300
commit5da5a1cc2da885346efe47ed1ea39a82e5aa42d5 (patch)
treebc669369ae93d4b3fe6d36f92ec2349254efd463
parent05fa5ca337eb786707b71a54e42db262e8640646 (diff)
Geometry Nodes: support multiple group input nodes
Previously this was only supported within nested node groups. Now it is also supported for the root node group that is referenced by the modifier.
-rw-r--r--source/blender/blenkernel/BKE_geometry_set.hh2
-rw-r--r--source/blender/blenkernel/intern/geometry_set.cc6
-rw-r--r--source/blender/modifiers/intern/MOD_nodes.cc24
3 files changed, 20 insertions, 12 deletions
diff --git a/source/blender/blenkernel/BKE_geometry_set.hh b/source/blender/blenkernel/BKE_geometry_set.hh
index 8cc37a3e711..4454669b59a 100644
--- a/source/blender/blenkernel/BKE_geometry_set.hh
+++ b/source/blender/blenkernel/BKE_geometry_set.hh
@@ -313,6 +313,8 @@ struct GeometrySet {
friend bool operator==(const GeometrySet &a, const GeometrySet &b);
uint64_t hash() const;
+ void clear();
+
/* Utility methods for creation. */
static GeometrySet create_with_mesh(
Mesh *mesh, GeometryOwnershipType ownership = GeometryOwnershipType::Owned);
diff --git a/source/blender/blenkernel/intern/geometry_set.cc b/source/blender/blenkernel/intern/geometry_set.cc
index a09c3f5f3d3..9f57fcfb2ba 100644
--- a/source/blender/blenkernel/intern/geometry_set.cc
+++ b/source/blender/blenkernel/intern/geometry_set.cc
@@ -205,6 +205,12 @@ uint64_t GeometrySet::hash() const
return reinterpret_cast<uint64_t>(this);
}
+/* Remove all geometry components from the geometry set. */
+void GeometrySet::clear()
+{
+ components_.clear();
+}
+
/* Returns a read-only mesh or null. */
const Mesh *GeometrySet::get_mesh_for_read() const
{
diff --git a/source/blender/modifiers/intern/MOD_nodes.cc b/source/blender/modifiers/intern/MOD_nodes.cc
index d6f7b4c8561..8f9aa5c89ad 100644
--- a/source/blender/modifiers/intern/MOD_nodes.cc
+++ b/source/blender/modifiers/intern/MOD_nodes.cc
@@ -1057,7 +1057,7 @@ static void reset_tree_ui_storage(Span<const blender::nodes::NodeTreeRef *> tree
* often than necessary. It's going to be replaced soon.
*/
static GeometrySet compute_geometry(const DerivedNodeTree &tree,
- Span<const OutputSocketRef *> group_input_sockets,
+ Span<const NodeRef *> group_input_nodes,
const InputSocketRef &socket_to_compute,
GeometrySet input_geometry_set,
NodesModifierData *nmd,
@@ -1073,7 +1073,12 @@ static GeometrySet compute_geometry(const DerivedNodeTree &tree,
Map<DOutputSocket, GMutablePointer> group_inputs;
const DTreeContext *root_context = &tree.root_context();
- if (group_input_sockets.size() > 0) {
+ for (const NodeRef *group_input_node : group_input_nodes) {
+ Span<const OutputSocketRef *> group_input_sockets = group_input_node->outputs().drop_back(1);
+ if (group_input_sockets.is_empty()) {
+ continue;
+ }
+
Span<const OutputSocketRef *> remaining_input_sockets = group_input_sockets;
/* If the group expects a geometry as first input, use the geometry that has been passed to
@@ -1081,7 +1086,7 @@ static GeometrySet compute_geometry(const DerivedNodeTree &tree,
const OutputSocketRef *first_input_socket = group_input_sockets[0];
if (first_input_socket->bsocket()->type == SOCK_GEOMETRY) {
GeometrySet *geometry_set_in =
- allocator.construct<GeometrySet>(std::move(input_geometry_set)).release();
+ allocator.construct<GeometrySet>(input_geometry_set).release();
group_inputs.add_new({root_context, first_input_socket}, geometry_set_in);
remaining_input_sockets = remaining_input_sockets.drop_front(1);
}
@@ -1095,6 +1100,9 @@ static GeometrySet compute_geometry(const DerivedNodeTree &tree,
}
}
+ /* Don't keep a reference to the input geometry components to avoid copies during evaluation. */
+ input_geometry_set.clear();
+
Vector<DInputSocket> group_outputs;
group_outputs.append({root_context, &socket_to_compute});
@@ -1183,18 +1191,10 @@ static void modifyGeometry(ModifierData *md,
Span<const NodeRef *> input_nodes = root_tree_ref.nodes_by_type("NodeGroupInput");
Span<const NodeRef *> output_nodes = root_tree_ref.nodes_by_type("NodeGroupOutput");
- if (input_nodes.size() > 1) {
- return;
- }
if (output_nodes.size() != 1) {
return;
}
- Span<const OutputSocketRef *> group_inputs;
- if (input_nodes.size() == 1) {
- group_inputs = input_nodes[0]->outputs().drop_back(1);
- }
-
Span<const InputSocketRef *> group_outputs = output_nodes[0]->inputs().drop_back(1);
if (group_outputs.size() == 0) {
@@ -1211,7 +1211,7 @@ static void modifyGeometry(ModifierData *md,
}
geometry_set = compute_geometry(
- tree, group_inputs, *group_outputs[0], std::move(geometry_set), nmd, ctx);
+ tree, input_nodes, *group_outputs[0], std::move(geometry_set), nmd, ctx);
}
static Mesh *modifyMesh(ModifierData *md, const ModifierEvalContext *ctx, Mesh *mesh)