import type { ReactNode } from "react"; import type { EffectElement, GraphicElement, ImageElement, MaskableElement, RetimableElement, StickerElement, TextElement, VisualElement, VideoElement, AudioElement, TimelineElement, } from "@/lib/timeline"; import type { MediaAsset } from "@/lib/media/types"; import { HugeiconsIcon } from "@hugeicons/react"; import { TextFontIcon, ArrowExpandIcon, RainDropIcon, MusicNote03Icon, MagicWand05Icon, DashboardSpeed02Icon, } from "@hugeicons/core-free-icons"; import { TransformTab } from "./tabs/transform-tab"; import { BlendingTab } from "./tabs/blending-tab"; import { AudioTab } from "./tabs/audio-tab"; import { TextTab } from "./tabs/text-tab"; import { ClipEffectsTab, StandaloneEffectTab } from "./tabs/effects-tab"; import { MasksTab } from "./tabs/masks-tab"; import { SpeedTab } from "./tabs/speed-tab"; import { GraphicTab } from "./tabs/graphic-tab"; import { OcShapesIcon } from "@/components/icons"; export type TabContentProps = { trackId: string; }; export type PropertiesTabDef = { id: string; label: string; icon: ReactNode; content: (props: TabContentProps) => ReactNode; }; export type ElementPropertiesConfig = { defaultTab: string; tabs: PropertiesTabDef[]; }; function buildTransformTab({ element, }: { element: VisualElement; }): PropertiesTabDef { return { id: "transform", label: "Transform", icon: , content: ({ trackId }) => ( ), }; } function buildBlendingTab({ element, }: { element: VisualElement; }): PropertiesTabDef { return { id: "blending", label: "Blending", icon: , content: ({ trackId }) => ( ), }; } function buildAudioTab({ element, }: { element: AudioElement | VideoElement; }): PropertiesTabDef { return { id: "audio", label: "Audio", icon: , content: ({ trackId }) => , }; } function buildSpeedTab({ element, }: { element: RetimableElement; }): PropertiesTabDef { return { id: "speed", label: "Speed", icon: , content: ({ trackId }) => , }; } function buildMasksTab({ element, }: { element: MaskableElement; }): PropertiesTabDef { return { id: "masks", label: "Masks", icon: , content: ({ trackId }) => , }; } function buildClipEffectsTab({ element, }: { element: VisualElement; }): PropertiesTabDef { return { id: "effects", label: "Effects", icon: , content: ({ trackId }) => ( ), }; } function buildTextTab({ element }: { element: TextElement }): PropertiesTabDef { return { id: "text", label: "Text", icon: , content: ({ trackId }) => , }; } function buildGraphicTab({ element, }: { element: GraphicElement; }): PropertiesTabDef { return { id: "graphic", label: "Graphic", icon: , content: ({ trackId }) => , }; } function buildStandaloneEffectTab({ element, }: { element: EffectElement; }): PropertiesTabDef { return { id: "effects", label: "Effects", icon: , content: ({ trackId }) => ( ), }; } function getTextConfig({ element, }: { element: TextElement; }): ElementPropertiesConfig { return { defaultTab: "text", tabs: [ buildTextTab({ element }), buildTransformTab({ element }), buildBlendingTab({ element }), ], }; } function getVideoConfig({ element, mediaAsset, }: { element: VideoElement; mediaAsset: MediaAsset | undefined; }): ElementPropertiesConfig { const showAudioTab = mediaAsset?.hasAudio !== false; return { defaultTab: "transform", tabs: [ buildTransformTab({ element }), ...(showAudioTab ? [buildAudioTab({ element })] : []), buildSpeedTab({ element }), buildBlendingTab({ element }), buildMasksTab({ element }), buildClipEffectsTab({ element }), ], }; } function getImageConfig({ element, }: { element: ImageElement; }): ElementPropertiesConfig { return { defaultTab: "transform", tabs: [ buildTransformTab({ element }), buildBlendingTab({ element }), buildMasksTab({ element }), buildClipEffectsTab({ element }), ], }; } function getStickerConfig({ element, }: { element: StickerElement; }): ElementPropertiesConfig { return { defaultTab: "transform", tabs: [ buildTransformTab({ element }), buildBlendingTab({ element }), buildClipEffectsTab({ element }), ], }; } function getGraphicConfig({ element, }: { element: GraphicElement; }): ElementPropertiesConfig { return { defaultTab: "graphic", tabs: [ buildGraphicTab({ element }), buildTransformTab({ element }), buildBlendingTab({ element }), buildMasksTab({ element }), buildClipEffectsTab({ element }), ], }; } function getAudioConfig({ element, }: { element: AudioElement; }): ElementPropertiesConfig { return { defaultTab: "audio", tabs: [buildAudioTab({ element }), buildSpeedTab({ element })], }; } function getEffectConfig({ element, }: { element: EffectElement; }): ElementPropertiesConfig { return { defaultTab: "effects", tabs: [buildStandaloneEffectTab({ element })], }; } export function getPropertiesConfig({ element, mediaAssets, }: { element: TimelineElement; mediaAssets: MediaAsset[]; }): ElementPropertiesConfig { switch (element.type) { case "text": return getTextConfig({ element }); case "video": { const mediaAsset = mediaAssets.find((a) => a.id === element.mediaId); return getVideoConfig({ element, mediaAsset }); } case "image": return getImageConfig({ element }); case "sticker": return getStickerConfig({ element }); case "graphic": return getGraphicConfig({ element }); case "audio": return getAudioConfig({ element }); case "effect": return getEffectConfig({ element }); } }