Keep line and arc elevation when lengthening with LENGTHEN (#1313)

Found while testing crates/engine/src/cmd/modify2.rs:764

Co-authored-by: Claude Haiku 5.5 <noreply@anthropic.com>
This commit is contained in:
NetterSilver
2026-10-19 02:31:44 -04:00
committed by GitHub
co-authored by Claude Haiku 5.5
parent a3b3e1281f
commit 1ac2ebaad2
2 changed files with 42 additions and 2 deletions
+9 -2
View File
@@ -761,7 +761,13 @@ pub(crate) fn lengthen_kind(k: &EntityKind, pick: Option<Vec2>, mode: LenMode) -
return Err(too_short());
}
let ne = fixed + dir * nl;
Ok(if at_b { line(a, ne) } else { line(ne, b) })
let mut out = l.clone();
if at_b {
out.b = ne.to3(l.b.z);
} else {
out.a = ne.to3(l.a.z);
}
Ok(EntityKind::Line(out))
}
EntityKind::Arc(ar) => {
let g = Arc::new(ar.center.xy(), ar.radius, ar.start, ar.end);
@@ -782,7 +788,8 @@ pub(crate) fn lengthen_kind(k: &EntityKind, pick: Option<Vec2>, mode: LenMode) -
if !(ns > 1e-12 && ns < TAU - 1e-9) {
return Err(other("The new arc would be zero length or a full circle."));
}
Ok(if at_end { arc(&Arc::new(g.center, g.radius, g.start, g.start + ns)) } else { arc(&Arc::new(g.center, g.radius, g.end - ns, g.end)) })
let na = if at_end { Arc::new(g.center, g.radius, g.start, g.start + ns) } else { Arc::new(g.center, g.radius, g.end - ns, g.end) };
Ok(EntityKind::Arc(cadcraft_doc::Arc { radius: na.radius, start: na.start, end: na.end, ..ar.clone() }))
}
EntityKind::LwPolyline(p) if !p.closed && p.vertices.len() >= 2 => {
let total = Polyline { vertices: p.vertices.clone(), closed: false }.len();
+33
View File
@@ -214,6 +214,39 @@ fn lengthen_json() {
assert!(near(poly(&kind(&s, &p)).vertices[0].p, -5.0, 10.0));
}
#[test]
fn lengthen_keeps_elevation() {
let mut s = Session::new();
let l = h(&s.execute("line", &json!({"points": [[0, 0], [10, 0]]})).unwrap());
let a = h(&s.execute("arc", &json!({"center": [0, 0], "radius": 1, "start": 0, "end": 90})).unwrap());
let doc = s.doc_mut().unwrap();
doc.modify_entity(Handle::parse_hex(&l).unwrap(), |e| {
if let EntityKind::Line(x) = &mut e.kind {
x.a.z = 5.0;
x.b.z = 5.0;
}
})
.unwrap();
doc.modify_entity(Handle::parse_hex(&a).unwrap(), |e| {
if let EntityKind::Arc(x) = &mut e.kind {
x.center.z = 3.0;
}
})
.unwrap();
s.execute("lengthen", &json!({"handle": l, "delta": 2})).unwrap();
let EntityKind::Line(x) = kind(&s, &l) else { panic!("not a line") };
assert_eq!((x.a.x, x.a.y, x.a.z), (0.0, 0.0, 5.0));
assert_eq!((x.b.x, x.b.y, x.b.z), (12.0, 0.0, 5.0));
s.execute("lengthen", &json!({"handle": l, "delta": 1, "pick": [0, 0]})).unwrap();
let EntityKind::Line(x) = kind(&s, &l) else { panic!("not a line") };
assert_eq!((x.a.x, x.a.y, x.a.z), (-1.0, 0.0, 5.0));
assert_eq!((x.b.x, x.b.y, x.b.z), (12.0, 0.0, 5.0));
s.execute("lengthen", &json!({"handle": a, "deltaAngle": 10})).unwrap();
let EntityKind::Arc(x) = kind(&s, &a) else { panic!("not an arc") };
assert_eq!(x.center.z, 3.0);
assert!((arc_of(&kind(&s, &a)).sweep() - 100f64.to_radians()).abs() < 1e-9);
}
#[test]
fn lengthen_command_line() {
let mut s = Session::new();