diff --git a/crates/engine/src/cmd/blocks/extract.rs b/crates/engine/src/cmd/blocks/extract.rs index 85ed849ce..28df51299 100644 --- a/crates/engine/src/cmd/blocks/extract.rs +++ b/crates/engine/src/cmd/blocks/extract.rs @@ -139,16 +139,15 @@ fn found(s: &Session, p: &Value, o: &Options) -> Result> { } let block = d.block(&ins.block).map(|b| b.name.clone()).unwrap_or_else(|| ins.block.clone()); out.push(Found { - block, handle: e.handle.hex(), layer: e.common.layer.clone(), at: ins.insert.xy(), rotation: ins.rotation.to_degrees(), + block: block.clone(), values: values( ins, - consts - .entry(ins.block.to_ascii_uppercase()) - .or_insert_with(|| d.block(&ins.block).map(|b| constants(b, &o.tags)).unwrap_or_default()), + // Keyed by the resolved definition's exact name: `Part` and `PART` can both exist. + consts.entry(block.clone()).or_insert_with(|| d.block(&ins.block).map(|b| constants(b, &o.tags)).unwrap_or_default()), &o.tags, ), }); diff --git a/crates/engine/src/cmd/modify2/mocoro.rs b/crates/engine/src/cmd/modify2/mocoro.rs index 7a80955d4..6d8f847b0 100644 --- a/crates/engine/src/cmd/modify2/mocoro.rs +++ b/crates/engine/src/cmd/modify2/mocoro.rs @@ -109,7 +109,11 @@ pub(super) fn run_mocoro(s: &mut Session, p: &Value) -> Result { // Every option is checked before the drawing changes. let ops = list.iter().enumerate().map(|(i, v)| parse_op(i, v)).collect::>>()?; // Each Copy clones every selected object: the copies together stay within MAXARRAY, as an array's do. - crate::cmd::array::check_size(s, ops.iter().filter(|o| matches!(o, Op::Copy(_))).count() as u64, objs.len())?; + // Erased handles are skipped by `apply`, so only live objects count (none: nothing is copied). + let live = counts(s, &objs)?.0; + if live > 0 { + crate::cmd::array::check_size(s, ops.iter().filter(|o| matches!(o, Op::Copy(_))).count() as u64, live)?; + } let mut copies = Vec::new(); for op in ops { copies.extend(apply(s, &objs, &mut base, op)?); diff --git a/crates/io/src/pdf.rs b/crates/io/src/pdf.rs index 6a0d85638..6d3cd05f5 100644 --- a/crates/io/src/pdf.rs +++ b/crates/io/src/pdf.rs @@ -462,7 +462,10 @@ fn write_pdf(d: &Drawing, items: &[(Space, PdfOptions)], o: &PdfOptions, text_as // pages times the links must not multiply without a bound. let mut annotations_left = MAX_FILE_ANNOTATIONS; for (s, po) in items { - let mut page = sheet(drawn, s, po, &links)?; + // Once the budget is spent no link is built (scanned and cloned) for later pages. + let mut page = sheet(drawn, s, po, if annotations_left == 0 { &links[..0] } else { &links })?; + // Only targets `write_page` accepts count against the budget. + page.links.retain(|(_, url)| uri(url).is_some()); page.links.truncate(annotations_left); annotations_left -= page.links.len(); let doc = writer.document_mut();