Files
photocraft/docs
Alan Rockefeller f75cfd5a56 Clone Stamp and Healing Brush clone from a source set in another open document (#10381)
* Clone Stamp and Healing Brush clone from a source set in another open document

Alt-clicking a clone source in one document and painting in another sampled the
painted document at the source point: a clone source slot held a point and a layer
but not the document. Slots now record the document (and its layer) they were set
in, and painting elsewhere samples that document, as in Photoshop.

- Engine: CloneSource gains `document` (serde default, so older slots read as
  "the document being painted"). Clone Stamp, Healing Brush, the live stroke, the
  Pattern Preview wrap and the brush-tip preview read the source document. Pixels
  are converted to the painted document's colour mode and depth like Edit > Paste
  (no ICC conversion, same as Paste). Current Layer / Current & Below use the
  layer the source was set on (that document's active layer if it was deleted);
  All Layers uses its composite.
- A source whose document was closed is an error asking for a new source, and
  stores no aligned anchor, instead of silently sampling the wrong document.
- cloneSource.set takes an optional `"document": index` (with `source`);
  cloneSource.list and set report each slot's document index.
- UI: the Clone Source panel names the source document (or says it was closed),
  the source crosshair isn't drawn over another document, and the brush preview
  cache includes the source document's revision.

Tests: engine tests for 8/16/32-bit with and without wrap, colour-mode conversion
(Gray > RGB16, RGB > CMYK), sampled layer, Healing Brush, live stroke vs commit,
preview, closed/invalid documents and cloneSource.set/list; a UI test that
Alt-clicks in one document and paints in another.

* Clone test: the aligned stroke past the smaller source document's edge leaves the destination unchanged

Review follow-up: with "aligned": false the stroke sampled inside the source, so it didn't test the edge its comment named, and nothing was asserted.

* Clone Stamp / Healing Brush: an empty Clone Source slot refuses to paint

clone_params fell back to ui.clone_source / ui.clone_offset when the active
slot was empty. Those coordinates carry no document, so after Alt-clicking in
one document and picking an empty slot in another, the stroke read the first
document's coordinates from the second one's pixels.

* fix: reject stale cross-document clone previews

* Clone Source: a copy opened after the source document closed isn't its source

A native copy keeps its document's ID, and a reopened document may keep its ID. A slot set in
a document that was then closed resolved that ID again once a copy was open, and painted from
the copy instead of reporting the closed source (CodeRabbit, clone_source.rs).

Session::close now marks the slots set in the closing document closed (CloneSources::forget_doc,
next to the other per-feature forget_doc calls). A closed slot refuses the stroke and its live
preview with the closed-source error, shows "Source: document closed" in the panel, reports no
`document` in cloneSource.list/set, and draws no overlay or crosshair, whatever document has the
ID now. Setting a new source clears it.
2026-11-12 18:00:54 +01:00
..