fix(snap): arc segments of a polyline offer their centre and quadrants

Center and Quadrant found nothing on a polyline's bulge segments: the
lightweight and heavy polylines carried no snap points for them, and a
polyline split into several wires kept its points on one piece whose box
the others' never reached. Each arc segment now carries its centre and
quadrants, hovering the segment offers its centre, and a wire's box
covers its snap points.

Fixes #1640

Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
Hakan SevenandClaude Opus 5.5 committed 2026-10-07 08:50:05 +03:00
1 parent 29392de267
commit fae64886ee
6 files changed
+150 -28

No files matched your search

+17
View File
@@ -1766,6 +1766,23 @@ pub(crate) fn set_wire_aabb(w: &mut WireModel, entity_box: [f32; 4]) {
for (i, &p) in w.pick_tris.iter().enumerate() {
extend(p, w.pick_tris_low.get(i).copied().unwrap_or([0.0; 3]));
}
// The entity's snap points ride one wire, which may be only one piece of
// it (a polyline drawn per segment): its box must reach them, or a snap
// on another piece — an arc segment's quadrant — is never tried.
let split = |x: f64| {
let high = x as f32;
[high, (x - high as f64) as f32]
};
let points = w
.snap_pts
.iter()
.map(|(p, _)| [p.x, p.y])
.chain(w.key_vertices.iter().map(|p| [p[0], p[1]]))
.collect::<Vec<_>>();
for [x, y] in points {
let ([xh, xl], [yh, yl]) = (split(x), split(y));
extend([xh, yh, 0.0], [xl, yl, 0.0]);
}
w.aabb = out;
}
+3
View File
@@ -4,6 +4,9 @@
pub enum SnapHint {
/// Geometric center of a circle, arc, or ellipse.
Center,
/// Centre of one arc segment of a chain (a polyline). Snaps like
/// `Center`, but does not make the wire count as round.
ArcCenter,
/// Area centroid of a closed polyline.
GeometricCenter,
/// Point entity location.