Fix: Cursor snapping does not work for Curves bezier handles
For this to work, we have to take into account handles in TransVert as well. Behavior is the same as in legacy curves (meaning that if the control point itself is selected, the handles are ignores). Part of #133448 (same thing for grease pencil, which I plan to also make part of TransVert, but better solve for Curves first, so we can share code here). Pull Request: https://projects.blender.org/blender/blender/pulls/134945
This commit is contained in:
committed by
Philipp Oeser
parent
a50144e55c
commit
3589c5489a
@@ -22,22 +22,44 @@ Vector<MutableSpan<float3>> get_curves_positions_for_write(bke::CurvesGeometry &
|
||||
return positions_per_attribute;
|
||||
}
|
||||
|
||||
void transverts_from_curves_positions_create(bke::CurvesGeometry &curves, TransVertStore *tvs)
|
||||
void transverts_from_curves_positions_create(bke::CurvesGeometry &curves,
|
||||
TransVertStore *tvs,
|
||||
const bool skip_handles)
|
||||
{
|
||||
const Span<StringRef> selection_names = ed::curves::get_curves_selection_attribute_names(curves);
|
||||
|
||||
IndexMaskMemory memory;
|
||||
IndexMask selection = retrieve_selected_points(curves, memory);
|
||||
MutableSpan<float3> positions = curves.positions_for_write();
|
||||
std::array<IndexMask, 3> selection;
|
||||
for (const int i : selection_names.index_range()) {
|
||||
selection[i] = ed::curves::retrieve_selected_points(curves, selection_names[i], memory);
|
||||
}
|
||||
|
||||
tvs->transverts = static_cast<TransVert *>(
|
||||
MEM_calloc_arrayN(selection.size(), sizeof(TransVert), __func__));
|
||||
tvs->transverts_tot = selection.size();
|
||||
if (skip_handles) {
|
||||
/* When the control point is selected, both handles are ignored. */
|
||||
selection[1] = IndexMask::from_difference(selection[1], selection[0], memory);
|
||||
selection[2] = IndexMask::from_difference(selection[2], selection[0], memory);
|
||||
}
|
||||
|
||||
selection.foreach_index(GrainSize(1024), [&](const int64_t i, const int64_t pos) {
|
||||
TransVert &tv = tvs->transverts[pos];
|
||||
tv.loc = positions[i];
|
||||
tv.flag = SELECT;
|
||||
copy_v3_v3(tv.oldloc, tv.loc);
|
||||
});
|
||||
const int size = selection[0].size() + selection[1].size() + selection[2].size();
|
||||
if (size == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
tvs->transverts = static_cast<TransVert *>(MEM_calloc_arrayN(size, sizeof(TransVert), __func__));
|
||||
tvs->transverts_tot = size;
|
||||
|
||||
int offset = 0;
|
||||
const Vector<MutableSpan<float3>> positions = ed::curves::get_curves_positions_for_write(curves);
|
||||
for (const int attribute_i : positions.index_range()) {
|
||||
selection[attribute_i].foreach_index(GrainSize(1024), [&](const int64_t i, const int64_t pos) {
|
||||
TransVert &tv = tvs->transverts[pos + offset];
|
||||
tv.loc = positions[attribute_i][i];
|
||||
tv.flag = SELECT;
|
||||
copy_v3_v3(tv.oldloc, tv.loc);
|
||||
});
|
||||
|
||||
offset += selection[attribute_i].size();
|
||||
}
|
||||
}
|
||||
|
||||
float (*point_normals_array_create(const Curves *curves_id))[3]
|
||||
|
||||
@@ -118,7 +118,9 @@ void ensure_surface_deformation_node_exists(bContext &C, Object &curves_ob);
|
||||
* `ED_transverts_create_from_obedit` in `view3d_snap.cc`).
|
||||
* \note The `TransVert` elements in \a tvs are expected to write to the positions of \a curves.
|
||||
*/
|
||||
void transverts_from_curves_positions_create(bke::CurvesGeometry &curves, TransVertStore *tvs);
|
||||
void transverts_from_curves_positions_create(bke::CurvesGeometry &curves,
|
||||
TransVertStore *tvs,
|
||||
const bool skip_handles);
|
||||
|
||||
/* -------------------------------------------------------------------- */
|
||||
/** \name Poll Functions
|
||||
|
||||
@@ -504,7 +504,8 @@ void ED_transverts_create_from_obedit(TransVertStore *tvs, const Object *obedit,
|
||||
}
|
||||
else if (obedit->type == OB_CURVES) {
|
||||
Curves *curves_id = static_cast<Curves *>(obedit->data);
|
||||
blender::ed::curves::transverts_from_curves_positions_create(curves_id->geometry.wrap(), tvs);
|
||||
blender::ed::curves::transverts_from_curves_positions_create(
|
||||
curves_id->geometry.wrap(), tvs, ((mode & TM_SKIP_HANDLES) != 0));
|
||||
}
|
||||
|
||||
if (!tvs->transverts_tot && tvs->transverts) {
|
||||
|
||||
Reference in New Issue
Block a user