Links: Find in Folder copies the files of images in symbols and patterns

With Copy into the document's folder, an image picked in the Links panel by
the id of an object in a symbol, graph design, pattern or opacity mask was
relinked to the found file instead of a copy, because the check for an image
looked only in the layers.
This commit is contained in:
dotCooCoo
2026-11-12 21:38:46 -08:00
parent a7c82ac7f2
commit c2ed2dd3a9
2 changed files with 32 additions and 2 deletions
+3 -2
View File
@@ -112,11 +112,12 @@ pub(crate) fn find_in_folder_command(app: &mut VectorcraftApp, folder: Option<St
Ok(Value::Null)
}
/// Whether object `id` of the active document is an image (and not a placed document).
/// Whether object `id` of the active document is an image (and not a placed document), in the
/// layers or in opacity-mask art or the art of a symbol, graph design or pattern.
fn is_image(app: &VectorcraftApp, id: &Value) -> bool {
let Some(id) = id.as_u64() else { return false };
let st = app.session.active();
st.and_then(|st| st.doc.node(vectorcraft_doc::NodeId(id))).is_some_and(|n| matches!(n.kind, vectorcraft_doc::NodeKind::Image(_)))
st.and_then(|st| st.doc.stored_node(vectorcraft_doc::NodeId(id))).is_some_and(|(n, _)| matches!(n.kind, vectorcraft_doc::NodeKind::Image(_)))
}
/// Make the dialog's document the active one: it may be another tab's.
@@ -255,6 +255,35 @@ fn copy_into_the_documents_folder_copies_before_relinking() {
assert!(!frame(&mut app).contains("Copy into the document's folder"));
}
/// Copy into the document's folder copies the file of an image in a symbol's art too, picked in the
/// Links panel by its id.
#[test]
fn copy_takes_an_image_in_a_symbol_into_the_documents_folder() {
let root = folder("copy-symbol");
let mut app = app_for(&root);
app.run("file.new", json!({"width": 400, "height": 300})).unwrap();
let orig = at(&root, "orig/a.png");
write(&orig, &png(3));
let placed = app.run("file.place", json!({"path": orig})).unwrap()["ids"][0].clone();
app.run("symbol.new", json!({"name": "Mark", "ids": [placed]})).unwrap();
let doc = at(&root, "doc/doc.vectorcraft");
std::fs::create_dir_all(doc.parent().unwrap()).unwrap();
app.run("document.save", json!({"path": doc})).unwrap();
write(&at(&root, "found/a.png"), &png(3));
let list = app.run("links.list", json!({})).unwrap();
let row = list["links"].as_array().unwrap().iter().find(|r| r["owner"]["kind"] == "symbol").cloned().expect("the symbol's image");
app.run("ui.findLinksInFolder", json!({"folder": root.join("found"), "ids": [row["id"]]})).unwrap();
searched(&mut app);
app.ui.dialog.as_mut().unwrap().fields.insert("copy".into(), json!(true));
let r = super::super::confirm(&mut app).unwrap();
assert_eq!((r["relinked"].as_array().map(Vec::len), &r["failed"]), (Some(1), &json!([])), "{r}");
let copy = at(&root, "doc/a.png");
assert_eq!(std::fs::read(&copy).unwrap(), png(3));
let list = app.run("links.list", json!({})).unwrap();
let row = list["links"].as_array().unwrap().iter().find(|r| r["owner"]["kind"] == "symbol").cloned().unwrap();
assert_eq!(row["path"], json!(copy), "{list}");
}
/// With Copy into the document's folder, a placed document is relinked where its file is.
#[test]
fn copy_leaves_placed_documents_where_they_are() {