import type { TimelineTrackStyle } from "./timelineTheme"; import { memo, type ReactNode } from "react"; import type { TimelineElement } from "../store/playerStore"; import { defaultTimelineTheme, getClipHandleOpacity, type TimelineTheme } from "./timelineTheme"; import type { TimelineEditCapabilities } from "./timelineEditing"; interface TimelineClipProps { el: TimelineElement; pps: number; clipY: number; isSelected: boolean; isHovered: boolean; isDragging?: boolean; hasCustomContent: boolean; capabilities: TimelineEditCapabilities; theme?: TimelineTheme; trackStyle: TimelineTrackStyle; isComposition: boolean; onHoverStart: () => void; onHoverEnd: () => void; onPointerDown?: (e: React.PointerEvent) => void; onResizeStart?: (edge: "start" | "end", e: React.PointerEvent) => void; onClick: (e: React.MouseEvent) => void; onDoubleClick: (e: React.MouseEvent) => void; onContextMenu?: (e: React.MouseEvent) => void; children?: ReactNode; } export const TimelineClip = memo(function TimelineClip({ el, pps, clipY, isSelected, isHovered, isDragging = false, hasCustomContent, capabilities, theme = defaultTimelineTheme, trackStyle, isComposition, onHoverStart, onHoverEnd, onPointerDown, onResizeStart, onClick, onDoubleClick, onContextMenu, children, }: TimelineClipProps) { const leftPx = el.start * pps; const widthPx = Math.max(el.duration * pps, 4); const handleOpacity = getClipHandleOpacity({ isHovered, isSelected, isDragging }); const borderColor = isSelected ? trackStyle.accent : isHovered ? theme.clipBorderHover : theme.clipBorder; const boxShadow = isDragging ? theme.clipShadowDragging : isSelected ? `0 0 0 1px ${trackStyle.accent}80, 0 0 8px ${trackStyle.accent}25` : isHovered ? theme.clipShadowHover : theme.clipShadow; const displayLabel = el.label || el.id || el.tag; const showHandles = handleOpacity > 0.01; return (