Changeset View
Changeset View
Standalone View
Standalone View
source/blender/nodes/geometry/nodes/node_geo_delete_geometry.cc
| Show First 20 Lines • Show All 191 Lines • ▼ Show 20 Lines | attribute_math::convert_to_static_type(data_type, [&](auto dummy) { | ||||
| GVArray_Span<T> span{*attribute.varray}; | GVArray_Span<T> span{*attribute.varray}; | ||||
| MutableSpan<T> out_span = result_attribute.as_span<T>(); | MutableSpan<T> out_span = result_attribute.as_span<T>(); | ||||
| copy_data(span, out_span, mask); | copy_data(span, out_span, mask); | ||||
| }); | }); | ||||
| result_attribute.save(); | result_attribute.save(); | ||||
| } | } | ||||
| } | } | ||||
| static void copy_face_corner_attributes(const Map<AttributeIDRef, AttributeKind> &attributes, | |||||
| const GeometryComponent &in_component, | |||||
| GeometryComponent &out_component, | |||||
| const int num_selected_loops, | |||||
| const Span<int> selected_poly_indices, | |||||
| const Mesh &mesh_in) | |||||
| { | |||||
HooglyBoogly: Maybe note that a valid optimization would be checking whether there are any face corner domain… | |||||
JacquesLuckeAuthorUnsubmitted Done Inline ActionsWon't do the optimization just yet. The same optimization could be done for the other domains, but that shouldn't be part of 3.0 anymore. JacquesLucke: Won't do the optimization just yet. The same optimization could be done for the other domains… | |||||
| Vector<int64_t> indices; | |||||
| indices.reserve(num_selected_loops); | |||||
| for (const int src_poly_index : selected_poly_indices) { | |||||
| const MPoly &src_poly = mesh_in.mpoly[src_poly_index]; | |||||
| const int src_loop_start = src_poly.loopstart; | |||||
| const int tot_loop = src_poly.totloop; | |||||
| for (const int i : IndexRange(tot_loop)) { | |||||
| indices.append_unchecked(src_loop_start + i); | |||||
| } | |||||
| } | |||||
| copy_attributes_based_on_mask( | |||||
| attributes, in_component, out_component, ATTR_DOMAIN_CORNER, IndexMask(indices)); | |||||
| } | |||||
| static void copy_masked_edges_to_new_mesh(const Mesh &src_mesh, Mesh &dst_mesh, Span<int> edge_map) | static void copy_masked_edges_to_new_mesh(const Mesh &src_mesh, Mesh &dst_mesh, Span<int> edge_map) | ||||
| { | { | ||||
| BLI_assert(src_mesh.totedge == edge_map.size()); | BLI_assert(src_mesh.totedge == edge_map.size()); | ||||
| for (const int i_src : IndexRange(src_mesh.totedge)) { | for (const int i_src : IndexRange(src_mesh.totedge)) { | ||||
| const int i_dst = edge_map[i_src]; | const int i_dst = edge_map[i_src]; | ||||
| if (ELEM(i_dst, -1, -2)) { | if (ELEM(i_dst, -1, -2)) { | ||||
| continue; | continue; | ||||
| } | } | ||||
| ▲ Show 20 Lines • Show All 838 Lines • ▼ Show 20 Lines | case GEO_NODE_DELETE_GEOMETRY_MODE_EDGE_FACE: { | ||||
| copy_masked_polys_to_new_mesh( | copy_masked_polys_to_new_mesh( | ||||
| mesh_in, *mesh_out, edge_map, selected_poly_indices, new_loop_starts); | mesh_in, *mesh_out, edge_map, selected_poly_indices, new_loop_starts); | ||||
| Vector<int64_t> indices; | Vector<int64_t> indices; | ||||
| copy_attributes_based_on_mask(attributes, | copy_attributes_based_on_mask(attributes, | ||||
| in_component, | in_component, | ||||
| out_component, | out_component, | ||||
| ATTR_DOMAIN_EDGE, | ATTR_DOMAIN_EDGE, | ||||
| index_mask_indices(edge_map, num_selected_edges, indices)); | index_mask_indices(edge_map, num_selected_edges, indices)); | ||||
| copy_attributes_based_on_mask( | copy_attributes_based_on_mask(attributes, | ||||
| attributes, | |||||
| in_component, | in_component, | ||||
| out_component, | out_component, | ||||
| ATTR_DOMAIN_FACE, | ATTR_DOMAIN_FACE, | ||||
| index_mask_indices(selected_poly_indices, num_selected_polys, indices)); | IndexMask(Vector<int64_t>(selected_poly_indices.as_span()))); | ||||
| copy_face_corner_attributes(attributes, | |||||
| in_component, | |||||
| out_component, | |||||
| num_selected_loops, | |||||
| selected_poly_indices, | |||||
| mesh_in); | |||||
| break; | break; | ||||
| } | } | ||||
| case GEO_NODE_DELETE_GEOMETRY_MODE_ONLY_FACE: { | case GEO_NODE_DELETE_GEOMETRY_MODE_ONLY_FACE: { | ||||
| /* Fill all the maps based on the selection. */ | /* Fill all the maps based on the selection. */ | ||||
| switch (domain) { | switch (domain) { | ||||
| case ATTR_DOMAIN_POINT: | case ATTR_DOMAIN_POINT: | ||||
| compute_selected_polygons_from_vertex_selection(mesh_in, | compute_selected_polygons_from_vertex_selection(mesh_in, | ||||
| selection, | selection, | ||||
| Show All 30 Lines | case GEO_NODE_DELETE_GEOMETRY_MODE_ONLY_FACE: { | ||||
| out_component.replace(mesh_out, GeometryOwnershipType::Editable); | out_component.replace(mesh_out, GeometryOwnershipType::Editable); | ||||
| /* Copy the selected parts of the mesh over to the new mesh. */ | /* Copy the selected parts of the mesh over to the new mesh. */ | ||||
| memcpy(mesh_out->mvert, mesh_in.mvert, mesh_in.totvert * sizeof(MVert)); | memcpy(mesh_out->mvert, mesh_in.mvert, mesh_in.totvert * sizeof(MVert)); | ||||
| memcpy(mesh_out->medge, mesh_in.medge, mesh_in.totedge * sizeof(MEdge)); | memcpy(mesh_out->medge, mesh_in.medge, mesh_in.totedge * sizeof(MEdge)); | ||||
| copy_attributes( | copy_attributes( | ||||
| attributes, in_component, out_component, {ATTR_DOMAIN_POINT, ATTR_DOMAIN_EDGE}); | attributes, in_component, out_component, {ATTR_DOMAIN_POINT, ATTR_DOMAIN_EDGE}); | ||||
| copy_masked_polys_to_new_mesh(mesh_in, *mesh_out, selected_poly_indices, new_loop_starts); | copy_masked_polys_to_new_mesh(mesh_in, *mesh_out, selected_poly_indices, new_loop_starts); | ||||
| Vector<int64_t> indices; | copy_attributes_based_on_mask(attributes, | ||||
| const IndexMask mask = index_mask_indices( | in_component, | ||||
| selected_poly_indices, num_selected_polys, indices); | out_component, | ||||
| copy_attributes_based_on_mask( | ATTR_DOMAIN_FACE, | ||||
| attributes, in_component, out_component, ATTR_DOMAIN_FACE, mask); | IndexMask(Vector<int64_t>(selected_poly_indices.as_span()))); | ||||
HooglyBooglyUnsubmitted Not Done Inline ActionsWon't this allocate a new int64_t vector? Could probably just change the original vector to int64_t instead? HooglyBoogly: Won't this allocate a new `int64_t` vector? Could probably just change the original vector to… | |||||
JacquesLuckeAuthorUnsubmitted Done Inline ActionsIt does. I think think it would be more correct not to use IndexMask but Span<int> here. But fixing it either way requires changes to quite a few more places in this file that I'd rather avoid right now. The performance overhead probably isn't too bad. It's just copying one integer per polygon in the output mesh. JacquesLucke: It does. I think think it would be more correct not to use `IndexMask` but `Span<int>` here. | |||||
| copy_face_corner_attributes(attributes, | |||||
| in_component, | |||||
| out_component, | |||||
| num_selected_loops, | |||||
| selected_poly_indices, | |||||
| mesh_in); | |||||
| break; | break; | ||||
| } | } | ||||
| } | } | ||||
| BKE_mesh_calc_edges_loose(mesh_out); | BKE_mesh_calc_edges_loose(mesh_out); | ||||
| /* Tag to recalculate normals later. */ | /* Tag to recalculate normals later. */ | ||||
| BKE_mesh_normals_tag_dirty(mesh_out); | BKE_mesh_normals_tag_dirty(mesh_out); | ||||
| geometry_set.replace_mesh(mesh_out); | geometry_set.replace_mesh(mesh_out); | ||||
| ▲ Show 20 Lines • Show All 108 Lines • Show Last 20 Lines | |||||
Maybe note that a valid optimization would be checking whether there are any face corner domain attributes to copy? (Or do the optimization I guess)