🐛 Fix hover bugs in wasm guides

This commit is contained in:
Belén Albeza 2026-06-19 11:47:33 +02:00
parent 2a5c29421f
commit 2fbff5816c

View File

@ -752,6 +752,12 @@
(drops the edit without committing)."
[{:keys [wasm-guides zoom wasm-guides? disabled-guides? on-guide-change
on-guide-drag on-guide-hover get-hover-frame focus]}]
;; NOTE: Some of the refs below are live mirrors of state, needed for DOM
;; listeners registered via `mf/with-effect`. Reading the state might return
;; a stale value or an invalid one (triggered right after a re-render)
;; Reading the ref instead gives the current, real value, so hover detection
;; and other pointer events ompares against the real guide data.
(let [dragging-ref (mf/use-ref false)
moved-ref (mf/use-ref false)
editing-ref (mf/use-ref false)
@ -762,6 +768,7 @@
hover-axis-ref (mf/use-ref nil)
hover-guide-id-ref (mf/use-ref nil)
state (mf/use-state nil)
state-ref (mf/use-ref nil)
snap-pixel?
(mf/deref refs/snap-pixel?)
@ -769,6 +776,13 @@
read-only?
(mf/use-ctx ctx/workspace-read-only?)
;; Always mutate the overlay state through this so `state-ref` stays in
;; sync with the `use-state` value the renderer derefs.
set-state
(fn [value]
(mf/set-ref-val! state-ref value)
(reset! state value))
;; The handlers are defined here so they close directly over the refs and
;; the current render's props (guides, zoom, ...). The pointerdown /
;; dblclick listeners are re-registered by the effect below whenever those
@ -819,7 +833,7 @@
(on-guide-drag nil))
(emit-hover-axis nil)
(emit-hover-guide-id nil)
(reset! state nil))
(set-state nil))
finish-drag
(fn [event]
@ -873,7 +887,7 @@
(when (some? on-guide-drag)
(on-guide-drag (:id guide))))
(mf/set-ref-val! pending-ref pending)
(reset! state pending)))))))
(set-state pending)))))))
editing?
(fn [] (mf/ref-val editing-ref))
@ -905,7 +919,7 @@
(not (editing?))
(not (mf/ref-val dragging-ref)))
(let [guide (visible-guide-at-event event)
current-state @state
current-state (mf/ref-val state-ref)
current-hover-id (when (= :hover (:mode current-state))
(-> current-state :guide :id))]
(emit-hover-axis (:axis guide))
@ -914,20 +928,20 @@
(and (some? guide)
(not= (:id guide) current-hover-id))
(let [frame (some-> (:frame-id guide) refs/object-by-id deref)]
(reset! state {:guide guide
:new-position (:position guide)
:frame-offset (guide-frame-offset guide)
;; Only root, non-rotated frames get the
;; segmented line (matching the SVG renderer),
;; so we only overlay dotted extensions there.
:frame (when (and frame
(cfh/root-frame? frame)
(not (ctst/rotated-frame? frame)))
frame)
:mode :hover}))
(set-state {:guide guide
:new-position (:position guide)
:frame-offset (guide-frame-offset guide)
;; Only root, non-rotated frames get the
;; segmented line (matching the SVG renderer),
;; so we only overlay dotted extensions there.
:frame (when (and frame
(cfh/root-frame? frame)
(not (ctst/rotated-frame? frame)))
frame)
:mode :hover}))
(and (nil? guide) (some? current-hover-id))
(reset! state nil)))))
(set-state nil)))))
pointer-down
(fn [event]
@ -983,16 +997,16 @@
offset (if frame
(if (= :x axis) (:x frame) (:y frame))
0)]
(reset! state {:guide guide
:new-position position
:new-frame-id frame-id
:frame-offset offset
:mode :edit}))))))
(set-state {:guide guide
:new-position position
:new-frame-id frame-id
:frame-offset offset
:mode :edit}))))))
commit-edit
(fn [raw-value]
(when (editing?)
(let [{:keys [guide new-frame-id frame-offset]} @state
(let [{:keys [guide new-frame-id frame-offset]} (mf/ref-val state-ref)
parsed (some-> raw-value str/trim d/parse-double)]
(when (and (some? parsed) (some? on-guide-change))
(on-guide-change (assoc guide