import { useLayoutEffect, useRef, useState } from 'react' import type { ReactNode } from 'react' import type { PanelImperativeHandle } from 'react-resizable-panels' import { ResizableHandle, ResizablePanel, ResizablePanelGroup } from '../../components/ui/resizable' import { cn } from '../../lib/cn' import type { WorkspaceSplitLayoutConstraints } from './useFitsSplitLayout' type WorkspaceSplitLayoutProps = WorkspaceSplitLayoutConstraints & { workspace: ReactNode chat: ReactNode open: boolean chatWidth: number onCollapse: () => void onChatWidthChange: (width: number) => void } export function WorkspaceSplitLayout({ workspace, chat, open, workspaceMinWidth, chatMinWidth, chatMaxWidth, chatWidth, onCollapse, onChatWidthChange }: WorkspaceSplitLayoutProps) { const chatPanelRef = useRef(null) const transitionFrameRef = useRef(null) const [transitionsEnabled, setTransitionsEnabled] = useState(false) const openChatWidth = Math.min(Math.max(chatWidth, chatMinWidth), chatMaxWidth) const defaultChatSize = useRef(open ? openChatWidth : 0).current useLayoutEffect(() => { const chatPanel = chatPanelRef.current if (!chatPanel) return if (open) { chatPanel.resize(openChatWidth) } else { chatPanel.collapse() } }, [openChatWidth, open]) return ( #chat]:transition-[flex-grow] [&>#chat]:duration-200 [&>#chat]:ease-in-out motion-reduce:[&>#chat]:transition-none!', transitionsEnabled && 'has-[[data-separator=active]]:[&>#chat]:transition-none!' )} onLayoutChanged={(_layout, meta) => { if (!transitionsEnabled && transitionFrameRef.current === null) { transitionFrameRef.current = requestAnimationFrame(() => { setTransitionsEnabled(true) }) } if (meta.isUserInteraction) { requestAnimationFrame(() => { const chatPanel = chatPanelRef.current if (!chatPanel) return const size = chatPanel.getSize() if (size.inPixels > 0) onChatWidthChange(Math.round(size.inPixels)) }) } }} >
{workspace}
) }