mirror of
https://github.com/storytold/vectorcraft.git
synced 2026-11-14 21:44:57 +00:00
Merge pull request #7464 from dotCooCoo/fix/followup-7305
Path: path.setHandle to the handle's own point leaves a smooth anchor unchanged
This commit is contained in:
@@ -315,13 +315,13 @@ fn set_handle(s: &mut Session, p: &Value) -> Result<Value> {
|
||||
let pos = Point::new(f64_req(p, "x", "path.setHandle")?, f64_req(p, "y", "path.setHandle")?);
|
||||
let independent = switch_or(p, "independent", false, "path.setHandle")?;
|
||||
// A handle already there, on an anchor already of the kind it would get, changes nothing and
|
||||
// records no undo step.
|
||||
if let Some(a) = anchor_of(s, id, si, ai)? {
|
||||
let mut b = a;
|
||||
b.set_handle(out, pos, independent);
|
||||
if b == a {
|
||||
return ok();
|
||||
}
|
||||
// records no undo step. The handle is compared directly: `set_handle` would recompute the
|
||||
// other handle of a smooth anchor, which need not give back the same value.
|
||||
if let Some(a) = anchor_of(s, id, si, ai)?
|
||||
&& (if out { a.h_out } else { a.h_in }) == pos
|
||||
&& !(independent && a.kind != AnchorKind::Corner)
|
||||
{
|
||||
return ok();
|
||||
}
|
||||
s.edit("Reshape", |d, _| {
|
||||
let path = path_mut(d, id)?;
|
||||
|
||||
@@ -8,7 +8,7 @@ use std::sync::Arc;
|
||||
use serde_json::{Value, json};
|
||||
use vectorcraft_doc::{Appearance, Document, Node, NodeId};
|
||||
use vectorcraft_geom::path::measured_segments;
|
||||
use vectorcraft_geom::{Anchor, PathData, Point, SubPath};
|
||||
use vectorcraft_geom::{Anchor, AnchorKind, PathData, Point, SubPath, Vec2};
|
||||
|
||||
use crate::*;
|
||||
|
||||
@@ -109,3 +109,29 @@ fn an_anchor_edit_that_changes_nothing_records_no_undo_step() {
|
||||
s.execute("path.moveAnchor", &json!({"id": id.0, "anchor": 5, "x": a.p.x + 1.0, "y": a.p.y})).unwrap();
|
||||
assert_eq!(undo_steps(&s), 1);
|
||||
}
|
||||
|
||||
/// `path.setHandle` to where the handle already is, on a smooth anchor whose other handle is not in
|
||||
/// line with it, leaves both handles as they are and records no undo step. With `independent` it
|
||||
/// makes the anchor a corner, which records one.
|
||||
#[test]
|
||||
fn a_handle_already_in_place_on_a_smooth_anchor_records_no_undo_step() {
|
||||
let (mut s, id) = long_path(100);
|
||||
let p = anchor(&s, id, 5).p;
|
||||
let smooth = Anchor { p, h_in: p + Vec2::new(-3.0, 0.0), h_out: p + Vec2::new(0.0, 4.0), kind: AnchorKind::Smooth };
|
||||
let path = Arc::make_mut(&mut s.doc_mut().unwrap().doc).node_mut(id).unwrap().path_data_mut().unwrap();
|
||||
path.subpaths[0].anchors[5] = smooth;
|
||||
for which in ["out", "in"] {
|
||||
let h = if which == "out" { smooth.h_out } else { smooth.h_in };
|
||||
s.execute("path.setHandle", &json!({"id": id.0, "anchor": 5, "which": which, "x": h.x, "y": h.y})).unwrap();
|
||||
assert_eq!(undo_steps(&s), 0, "path.setHandle on the {which} handle recorded an undo step");
|
||||
assert_eq!(anchor(&s, id, 5), smooth, "path.setHandle on the {which} handle changed the anchor");
|
||||
}
|
||||
s.execute("path.setHandle", &json!({"id": id.0, "anchor": 5, "which": "out", "x": smooth.h_out.x, "y": smooth.h_out.y, "independent": true}))
|
||||
.unwrap();
|
||||
assert_eq!(undo_steps(&s), 1);
|
||||
assert_eq!(anchor(&s, id, 5).kind, AnchorKind::Corner);
|
||||
// On a corner, the same independent request changes nothing.
|
||||
s.execute("path.setHandle", &json!({"id": id.0, "anchor": 5, "which": "out", "x": smooth.h_out.x, "y": smooth.h_out.y, "independent": true}))
|
||||
.unwrap();
|
||||
assert_eq!(undo_steps(&s), 1);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user