Skip to content

v0.3.2

tagged this 17 May 20:56
The 0.3.1 fast-pan installer engaged on ANY pan event but only
committed on `animation-finish`. That's correct for spring motion
(`panTo(target, false)`), but pan events with `immediately=true`
(touch drag, wheel scroll, custom per-rAF `panBy(delta, true)`
loops) never fire `animation-finish` — they're synchronous viewport
updates. Result: fast-pan started, drawer got suppressed, the
commit signal never arrived, drawer stayed suppressed indefinitely,
user saw stale tiles until the next spring pan flushed the state.

Two fixes (defense in depth):

1. Skip `pan` events with `e.immediately === true`. Immediate
   panners don't benefit from fast-pan anyway — they're already
   snappy because there's no spring redraw to skip. The win is
   specifically for spring momentum / programmatic
   `panTo(target, false)`, which is the slow case on iOS.

2. Add a 1s watchdog timer as defensive backup. Armed on
   startFastPan, re-armed on every tickFastPan, cleared on
   commitFastPan. If no animation events arrive within the
   window (custom OSD plugin, future OSD release with a pan
   path we don't know about), watchdog fires commitFastPan with
   a console.warn. Belt-and-suspenders so no future case can
   stick the drawer for more than a second.

Found in the field by a reader app using a custom RAF inertia
loop that panned via `panBy(delta, true)` per frame.

No public API changes — `:pan_optimized` attr and `fast-pan`
event surface identical to 0.3.0/0.3.1. Etcher 0.2.8's listener
continues to work unchanged.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Assets 2
Loading