🐛 Clear source grid cells when relocating children

Recalculate cell positions in the previous grids after moving children.
The destination update alone left cell references to shapes that moved.

Validation: reset and move suites, 21 tests / 92 assertions. The grid
move regression failed before the fix and checks exact undo.

Benchmark ratios against Phase 1e: main 10/100/1000 copies
0.54/0.56/0.60; three levels 0.52; chain 0.52; library 0.55;
many shapes 0.58; variant switch 0.61. No regression flag.

AI-assisted-by: GPT-6
This commit is contained in:
alonso.torres 2026-10-23 13:56:29 +02:00
parent e2b47a91fe
commit e4e02a4753
2 changed files with 27 additions and 0 deletions

View File

@ -555,6 +555,14 @@
shapes
to-index)
;; A move also removes children from their previous layout.
(pcb/update-shapes (disj all-parents parent-id)
(fn [shape objects]
(if (ctl/grid-layout? shape)
(ctl/assign-cell-positions shape objects)
shape))
{:ignore-touched true :with-objects? true})
;; Remove empty groups
(pcb/remove-objects groups-to-delete)

View File

@ -21,6 +21,25 @@
(t/use-fixtures :each thi/test-fixture)
(t/deftest moving-a-child-out-of-a-grid-clears-its-old-cell
(let [file (-> (thf/sample-file :file1)
(tho/add-grid-frame :grid :width 200 :height 100)
(tho/add-rect :first :parent-label :grid)
(tho/add-rect :second :parent-label :grid)
(tho/place-in-grid-columns :grid 2 {1 :first 2 :second})
(tho/add-frame :destination))
page (thf/current-page file)
changes (cls/generate-relocate (-> (pcb/empty-changes nil (:id page))
(pcb/with-objects (:objects page))
(pcb/with-library-data (:data file)))
(thi/id :destination) 0 #{(thi/id :first)})
moved (thf/apply-changes file changes)
grid (ths/get-shape moved :grid)
members (mapcat :shapes (vals (:layout-grid-cells grid)))
undone (thf/apply-changes moved {:redo-changes (:undo-changes changes)})]
(t/is (= #{(thi/id :second)} (set members)))
(t/is (= (thn/normalize-file file) (thn/normalize-file undone)))))
(t/deftest deleting-a-grid-child-clears-its-cell-and-keeps-undo
(let [file (-> (thf/sample-file :file1)
(tho/add-grid-frame :grid :width 200 :height 100)