diff options
| author | Maze Winther <mazewinther@gmail.com> | 2025-07-17 19:46:23 +0200 |
|---|---|---|
| committer | Maze Winther <mazewinther@gmail.com> | 2025-07-17 19:46:23 +0200 |
| commit | 648f0b8529b9f3bafb3bfd9a84a31bc9ac6623ae (patch) | |
| tree | 00a438ce93f12b3b58f705189142a9385d497e4a /apps/web/src/components/editor/timeline/timeline-action-handlers.tsx | |
| parent | 0b919d4df84ea523ac9e069bdad5c3b34b7c603d (diff) | |
| download | opencut-648f0b8529b9f3bafb3bfd9a84a31bc9ac6623ae.tar.gz | |
stable timeline
Diffstat (limited to 'apps/web/src/components/editor/timeline/timeline-action-handlers.tsx')
| -rw-r--r-- | apps/web/src/components/editor/timeline/timeline-action-handlers.tsx | 178 |
1 files changed, 0 insertions, 178 deletions
diff --git a/apps/web/src/components/editor/timeline/timeline-action-handlers.tsx b/apps/web/src/components/editor/timeline/timeline-action-handlers.tsx deleted file mode 100644 index 22c1efa5..00000000 --- a/apps/web/src/components/editor/timeline/timeline-action-handlers.tsx +++ /dev/null @@ -1,178 +0,0 @@ -import { useMemo } from "react"; -import { toast } from "sonner"; -import { useTimelineStore } from "@/stores/timeline-store"; -import { usePlaybackStore } from "@/stores/playback-store"; - -export function useTimelineActionHandlers() { - const { - tracks, - addElementToTrack, - removeElementFromTrack, - selectedElements, - clearSelectedElements, - splitElement, - splitAndKeepLeft, - splitAndKeepRight, - separateAudio, - } = useTimelineStore(); - const { currentTime } = usePlaybackStore(); - - // Create optimized lookup maps for O(1) access instead of O(n) find operations - const trackMap = useMemo(() => { - const map = new Map(); - tracks.forEach((track) => { - map.set(track.id, track); - // Also create element lookup for this track - const elementMap = new Map(); - track.elements.forEach((element) => { - elementMap.set(element.id, element); - }); - map.set(`${track.id}_elements`, elementMap); - }); - return map; - }, [tracks]); - - // Helper function for O(1) track/element lookup - const findTrackAndElement = (trackId: string, elementId: string) => { - const track = trackMap.get(trackId); - const elementMap = trackMap.get(`${trackId}_elements`); - const element = elementMap?.get(elementId); - return { track, element }; - }; - - // Action handlers for toolbar - const handleSplitSelected = () => { - if (selectedElements.length === 0) { - toast.error("No elements selected"); - return; - } - let splitCount = 0; - selectedElements.forEach(({ trackId, elementId }) => { - const { track, element } = findTrackAndElement(trackId, elementId); - if (element && track) { - const effectiveStart = element.startTime; - const effectiveEnd = - element.startTime + - (element.duration - element.trimStart - element.trimEnd); - - if (currentTime > effectiveStart && currentTime < effectiveEnd) { - const newElementId = splitElement(trackId, elementId, currentTime); - if (newElementId) splitCount++; - } - } - }); - if (splitCount === 0) { - toast.error("Playhead must be within selected elements to split"); - } - }; - - const handleDuplicateSelected = () => { - if (selectedElements.length === 0) { - toast.error("No elements selected"); - return; - } - const canDuplicate = selectedElements.length === 1; - if (!canDuplicate) return; - - selectedElements.forEach(({ trackId, elementId }) => { - const { element } = findTrackAndElement(trackId, elementId); - - if (element) { - const newStartTime = - element.startTime + - (element.duration - element.trimStart - element.trimEnd) + - 0.1; - - // Create element without id (will be generated by store) - const { id, ...elementWithoutId } = element; - - addElementToTrack(trackId, { - ...elementWithoutId, - startTime: newStartTime, - }); - - // We can't predict the new id, so just clear selection for now - // TODO: addElementToTrack could return the new element id - } - }); - - clearSelectedElements(); - }; - - const handleFreezeSelected = () => { - toast.info("Freeze frame functionality coming soon!"); - }; - - const handleSplitAndKeepLeft = () => { - if (selectedElements.length !== 1) { - toast.error("Select exactly one element"); - return; - } - const { trackId, elementId } = selectedElements[0]; - const { element } = findTrackAndElement(trackId, elementId); - if (!element) return; - const effectiveStart = element.startTime; - const effectiveEnd = - element.startTime + - (element.duration - element.trimStart - element.trimEnd); - if (currentTime <= effectiveStart || currentTime >= effectiveEnd) { - toast.error("Playhead must be within selected element"); - return; - } - splitAndKeepLeft(trackId, elementId, currentTime); - }; - - const handleSplitAndKeepRight = () => { - if (selectedElements.length !== 1) { - toast.error("Select exactly one element"); - return; - } - const { trackId, elementId } = selectedElements[0]; - const { element } = findTrackAndElement(trackId, elementId); - if (!element) return; - const effectiveStart = element.startTime; - const effectiveEnd = - element.startTime + - (element.duration - element.trimStart - element.trimEnd); - if (currentTime <= effectiveStart || currentTime >= effectiveEnd) { - toast.error("Playhead must be within selected element"); - return; - } - splitAndKeepRight(trackId, elementId, currentTime); - }; - - const handleSeparateAudio = () => { - if (selectedElements.length !== 1) { - toast.error("Select exactly one media element to separate audio"); - return; - } - const { trackId, elementId } = selectedElements[0]; - const { track } = findTrackAndElement(trackId, elementId); - if (!track || track.type !== "media") { - toast.error("Select a media element to separate audio"); - return; - } - separateAudio(trackId, elementId); - }; - - const handleDeleteSelected = () => { - if (selectedElements.length === 0) { - toast.error("No elements selected"); - return; - } - selectedElements.forEach(({ trackId, elementId }) => { - removeElementFromTrack(trackId, elementId); - }); - clearSelectedElements(); - }; - - return { - handleSplitSelected, - handleDuplicateSelected, - handleFreezeSelected, - handleSplitAndKeepLeft, - handleSplitAndKeepRight, - handleSeparateAudio, - handleDeleteSelected, - }; -} |
