From 0f75f8e9dae1f5a7c78625109092efa272cf46ee Mon Sep 17 00:00:00 2001 From: Drew Dibble Date: Mon, 9 Nov 2026 09:48:50 -0700 Subject: [PATCH] Canvas redraw: each version's trace source read from its own node; the 3D-bounds map's bound documented Diff took the Image Trace flag of the old version for both sides when it read each version's first member. Both versions have the same extras there (same_but_members), so the result was right, but each side now reads its own node. The doc of Renderer's three_d_bounds now says what adds an entry, when entries are swept, and the bound that follows: about twice the live 3D art plus 1024 entries. --- crates/render/src/changed.rs | 4 ++-- crates/render/src/lib.rs | 6 +++++- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/crates/render/src/changed.rs b/crates/render/src/changed.rs index c1612f0c9..1c1524703 100644 --- a/crates/render/src/changed.rs +++ b/crates/render/src/changed.rs @@ -183,8 +183,8 @@ impl Diff<'_, '_> { { // An Image Trace object draws its hidden source image, its first member, in some views. // Each version's own: an edit can put another member first (undoing Send to Back). - let first = |m: &[Arc]| old.extras().trace.is_some().then(|| m.first().map(|s| s.id)).flatten(); - let outer = std::mem::replace(&mut self.sources, (first(a), first(b))); + let first = |n: &Node, m: &[Arc]| n.extras().trace.is_some().then(|| m.first().map(|s| s.id)).flatten(); + let outer = std::mem::replace(&mut self.sources, (first(old, a), first(new, b))); self.children(a, b); self.sources = outer; } else if let Some((area, moved, anchors)) = moved_anchors(old, new) { diff --git a/crates/render/src/lib.rs b/crates/render/src/lib.rs index 32fb8fd02..4b2434282 100644 --- a/crates/render/src/lib.rs +++ b/crates/render/src/lib.rs @@ -175,7 +175,11 @@ pub struct Renderer { /// let go when a frame ends. pub(crate) pass_bounds: PtrMap, Option)>, /// The 3D effects' art among the art `fx_art` made, by its address, with the art (weakly: what - /// keeps the art is `fx_arts` and `measured`) and its bounds once measured. + /// keeps the art is `fx_arts` and `measured`) and its bounds once measured. An entry is added + /// for every 3D art made, measured or not, and entries whose art is gone are swept when the map + /// reaches twice the size it kept at the last sweep (at least 1024), so it holds at most about + /// twice the live 3D art plus 1024 entries. Until swept, an entry's weak pointer keeps the art's + /// allocation (not its contents) alive. three_d_bounds: PtrMap, /// How many entries `three_d_bounds` kept when it last let go of the art no longer held: it /// does so again when it holds twice as many.