feat: scroll vertically to the clip's track when jumping via link/jump
goto! with follow? already recentred horizontally on the playhead. Now it also scrolls the tracks container vertically so the clip under the landing frame is brought into view — for link chips, annotation jump buttons, and script highlights. No-op when the tracks already fit. Accounts for the pinned annotation-lane header height in the scroll math. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
96da4a6bd8
commit
967ca97e84
1 changed files with 22 additions and 2 deletions
|
|
@ -12,6 +12,7 @@
|
|||
(defonce video-el (atom nil))
|
||||
(defonce raf (atom nil))
|
||||
(defonce scroll-el (atom nil))
|
||||
(defonce body-scroll-el (atom nil)) ; the vertical (tracks) scroll container
|
||||
(defonce playhead-el (atom nil)) ; the single full-height playhead overlay
|
||||
(defonce play (atom nil)) ; {:ctx :segs :fps :idx} while playing, else nil
|
||||
(defonce active-insert! (atom nil)) ; the live content-editor's (insert! link) fn
|
||||
|
|
@ -174,6 +175,23 @@
|
|||
(rf/reg-fx :player/pause (fn [_] (when-let [v @video-el] (.pause v))))
|
||||
(rf/reg-fx :player/seek (fn [secs] (when (and @video-el secs) (set! (.-currentTime @video-el) secs))))
|
||||
|
||||
(defn- scroll-to-seg-track!
|
||||
"Scroll the tracks vertically so the clip under local frame `local` is visible.
|
||||
No-op when there's no vertical overflow. The annotation lanes are a pinned
|
||||
header of height `lane-h`, so the clip rows live below that in scroll space."
|
||||
[segs local]
|
||||
(when-let [el @body-scroll-el]
|
||||
(let [tracks @(rf/subscribe [::subs/tracks])
|
||||
row-h @(rf/subscribe [::subs/row-h])
|
||||
anns @(rf/subscribe [::subs/annotations])
|
||||
lane-h (max 18 (* 18 (count anns)))
|
||||
track (:track (nth segs (seg-at segs local) nil))
|
||||
i (first (keep-indexed (fn [idx t] (when (= (:id t) track) idx)) tracks))]
|
||||
(when i
|
||||
(let [target (+ lane-h (* i row-h) (/ row-h 2))]
|
||||
(.scrollTo el #js {:top (max 0 (- target (/ (.-clientHeight el) 2)))
|
||||
:behavior "smooth"}))))))
|
||||
|
||||
(defn- goto!
|
||||
"Move the playhead to local frame `local` and seek the video to match."
|
||||
([local] (goto! local false))
|
||||
|
|
@ -186,7 +204,8 @@
|
|||
(seek-video! fps (scene/local->source segs local))
|
||||
(when @play (swap! play assoc :idx (seg-at segs local))) ; keep playback in sync
|
||||
(when follow?
|
||||
(r/after-render #(follow! fps zoom local))))))
|
||||
(r/after-render #(do (follow! fps zoom local)
|
||||
(scroll-to-seg-track! segs local)))))))
|
||||
|
||||
(defn video-monitor []
|
||||
[:video {:src @(rf/subscribe [::subs/clip-url]) :controls true :preload "auto"
|
||||
|
|
@ -322,7 +341,8 @@
|
|||
^{:key (str "lbl-" (:id a))}
|
||||
[:div.ann-bar-label {:style {:top (* i 18)
|
||||
:left (+ 4 (px lo fps zoom))}} (:name a)])]]]
|
||||
[:div.timeline-body-scroll {:style {:padding-top lane-h}}
|
||||
[:div.timeline-body-scroll {:ref (fn [n] (reset! body-scroll-el n))
|
||||
:style {:padding-top lane-h}}
|
||||
[:div.gutter-tracks
|
||||
(for [t tracks]
|
||||
^{:key (:id t)}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue