From 8bbbd307a40187b3b3fd9bc70ca9e6eefa768bfa Mon Sep 17 00:00:00 2001 From: Sameer2748 Date: Thu, 19 Mar 2026 15:21:18 +0530 Subject: [PATCH] fix: sync zoom preview with timeline during seeking (#67) --- src/components/video-editor/VideoPlayback.tsx | 12 +++++++++++- .../videoPlayback/zoomRegionUtils.ts | 19 +++++++++---------- 2 files changed, 20 insertions(+), 11 deletions(-) diff --git a/src/components/video-editor/VideoPlayback.tsx b/src/components/video-editor/VideoPlayback.tsx index de3c58a..d79d25e 100644 --- a/src/components/video-editor/VideoPlayback.tsx +++ b/src/components/video-editor/VideoPlayback.tsx @@ -597,6 +597,11 @@ const VideoPlayback = forwardRef( cursorSwayRef.current = cursorSway; }, [cursorSway]); + // Sync currentTime prop to internal ref (in milliseconds) + useEffect(() => { + currentTimeRef.current = currentTime * 1000; + }, [currentTime]); + useEffect(() => { if (!pixiReady || !videoReady) return; @@ -1003,11 +1008,16 @@ const VideoPlayback = forwardRef( }; const ticker = () => { + const timeMs = currentTimeRef.current; const { region, strength, blendedScale, transition } = - findDominantRegion(zoomRegionsRef.current, currentTimeRef.current, { + findDominantRegion(zoomRegionsRef.current, timeMs, { connectZooms: connectZoomsRef.current, }); + if (region && Math.abs(timeMs - region.startMs) > 1000) { + // console.log(`[ZoomDebug] timeMs: ${timeMs}, dominantRegion_startMs: ${region.startMs}, strength: ${strength}`); + } + const defaultFocus = DEFAULT_FOCUS; let targetScaleFactor = 1; let targetFocus = defaultFocus; diff --git a/src/components/video-editor/videoPlayback/zoomRegionUtils.ts b/src/components/video-editor/videoPlayback/zoomRegionUtils.ts index 0b9080f..f1116b3 100644 --- a/src/components/video-editor/videoPlayback/zoomRegionUtils.ts +++ b/src/components/video-editor/videoPlayback/zoomRegionUtils.ts @@ -1,12 +1,11 @@ import type { ZoomFocus, ZoomRegion } from "../types"; import { ZOOM_DEPTH_SCALES } from "../types"; -import { TRANSITION_WINDOW_MS, ZOOM_IN_TRANSITION_WINDOW_MS } from "./constants"; +import { TRANSITION_WINDOW_MS } from "./constants"; import { clampFocusToScale } from "./focusUtils"; import { clamp01, cubicBezier, easeOutScreenStudio } from "./mathUtils"; const CHAINED_ZOOM_PAN_GAP_MS = 1500; const CONNECTED_ZOOM_PAN_DURATION_MS = 1000; -const ZOOM_IN_OVERLAP_MS = 500; type DominantRegionOptions = { connectZooms?: boolean; @@ -36,24 +35,25 @@ function easeConnectedPan(value: number) { } export function computeRegionStrength(region: ZoomRegion, timeMs: number) { - const zoomInEnd = region.startMs + ZOOM_IN_OVERLAP_MS; - const leadInStart = zoomInEnd - ZOOM_IN_TRANSITION_WINDOW_MS; - const leadOutEnd = region.endMs + TRANSITION_WINDOW_MS; + const leadInStart = region.startMs; + const leadInEnd = leadInStart + TRANSITION_WINDOW_MS; + const leadOutStart = region.endMs; + const leadOutEnd = leadOutStart + TRANSITION_WINDOW_MS; if (timeMs < leadInStart || timeMs > leadOutEnd) { return 0; } - if (timeMs < zoomInEnd) { - const progress = (timeMs - leadInStart) / ZOOM_IN_TRANSITION_WINDOW_MS; + if (timeMs < leadInEnd) { + const progress = Math.max(0, Math.min(1, (timeMs - leadInStart) / TRANSITION_WINDOW_MS)); return easeOutScreenStudio(progress); } - if (timeMs <= region.endMs) { + if (timeMs <= leadOutStart) { return 1; } - const progress = clamp01((timeMs - region.endMs) / TRANSITION_WINDOW_MS); + const progress = clamp01((timeMs - leadOutStart) / TRANSITION_WINDOW_MS); return 1 - easeOutScreenStudio(progress); } @@ -217,4 +217,3 @@ export function findDominantRegion(regions: ZoomRegion[], timeMs: number, option ? { ...activeRegion, transition: null } : { region: null, strength: 0, blendedScale: null, transition: null }; } -