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:
authorPhilipp Oeser <info@graphics-engineer.com>2022-04-04 13:26:50 +0300
committerPhilipp Oeser <info@graphics-engineer.com>2022-06-16 21:34:27 +0300
commite2975cb701692574504967178699c9ab083dc3f8 (patch)
tree835f1bb625607b2595bfdecf364b97070c3f67a5 /source/blender/nodes
parent209bf7780e7c005650482fa843062864f91845af (diff)
Geometry Nodes: add 'Intersecting Edges' output for boolean node
This patch adds a 'Intersecting Edges' output with a boolean selection that only gives you the new edges on intersections. Will work on a couple of examples next, this should make some interesting effects possible (including getting us closer to the "bevel- after-boolean-usecase") To achieve this, a Vector is passed to `direct_mesh_boolean` when the iMesh is still available (and intersecting edges appended), then from those edge indices a selection will be stored as attribute. Differential Revision: https://developer.blender.org/D15151
Diffstat (limited to 'source/blender/nodes')
-rw-r--r--source/blender/nodes/geometry/nodes/node_geo_boolean.cc47
1 files changed, 40 insertions, 7 deletions
diff --git a/source/blender/nodes/geometry/nodes/node_geo_boolean.cc b/source/blender/nodes/geometry/nodes/node_geo_boolean.cc
index e485172d3e1..daeca311e08 100644
--- a/source/blender/nodes/geometry/nodes/node_geo_boolean.cc
+++ b/source/blender/nodes/geometry/nodes/node_geo_boolean.cc
@@ -20,6 +20,7 @@ static void node_declare(NodeDeclarationBuilder &b)
b.add_input<decl::Bool>(N_("Self Intersection"));
b.add_input<decl::Bool>(N_("Hole Tolerant"));
b.add_output<decl::Geometry>(N_("Mesh"));
+ b.add_output<decl::Bool>(N_("Intersecting Edges")).field_source();
}
static void node_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr)
@@ -27,6 +28,10 @@ static void node_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr)
uiItemR(layout, ptr, "operation", 0, "", ICON_NONE);
}
+struct AttributeOutputs {
+ StrongAnonymousAttributeID intersecting_edges_id;
+};
+
static void node_update(bNodeTree *ntree, bNode *node)
{
GeometryNodeBooleanOperation operation = (GeometryNodeBooleanOperation)node->custom1;
@@ -121,13 +126,21 @@ static void node_geo_exec(GeoNodeExecParams params)
}
}
- Mesh *result = blender::meshintersect::direct_mesh_boolean(meshes,
- transforms,
- float4x4::identity(),
- material_remaps,
- use_self,
- hole_tolerant,
- operation);
+ AttributeOutputs attribute_outputs;
+ if (params.output_is_required("Intersecting Edges")) {
+ attribute_outputs.intersecting_edges_id = StrongAnonymousAttributeID("Intersecting Edges");
+ }
+
+ Vector<int> intersecting_edges;
+ Mesh *result = blender::meshintersect::direct_mesh_boolean(
+ meshes,
+ transforms,
+ float4x4::identity(),
+ material_remaps,
+ use_self,
+ hole_tolerant,
+ operation,
+ attribute_outputs.intersecting_edges_id ? &intersecting_edges : nullptr);
if (!result) {
params.set_default_remaining_outputs();
return;
@@ -138,6 +151,26 @@ static void node_geo_exec(GeoNodeExecParams params)
result->totcol = materials.size();
MutableSpan(result->mat, result->totcol).copy_from(materials);
+ /* Store intersecting edges in attribute. */
+ if (attribute_outputs.intersecting_edges_id) {
+ MeshComponent mesh_component;
+ mesh_component.replace(result, GeometryOwnershipType::Editable);
+ OutputAttribute_Typed<bool> attribute = mesh_component.attribute_try_get_for_output_only<bool>(
+ attribute_outputs.intersecting_edges_id.get(), ATTR_DOMAIN_EDGE);
+ MutableSpan<bool> selection = attribute.as_span();
+ selection.fill(false);
+ for (const int i : intersecting_edges) {
+ selection[i] = true;
+ }
+
+ attribute.save();
+
+ params.set_output(
+ "Intersecting Edges",
+ AnonymousAttributeFieldInput::Create<bool>(
+ std::move(attribute_outputs.intersecting_edges_id), params.attribute_producer_name()));
+ }
+
params.set_output("Mesh", GeometrySet::create_with_mesh(result));
#else
params.error_message_add(NodeWarningType::Error,