import { useCallback, useMemo, useState } from "react"; import { Link, createFileRoute } from "@tanstack/react-router"; import { useSuspenseQuery } from "@tanstack/react-query"; import { ArrowLeft, Moon, Plus, Sun } from "lucide-react"; import type { FlutterEvent, FlutterTimelineState } from "@/lib/flutter-bridge"; import { timelineQueryOptions } from "@/functions/get-timeline"; import { FlutterView } from "@/components/flutter-view"; import { Button } from "@/components/ui/button"; import UserMenu from "@/components/user-menu"; import ItemFormDrawer from "@/components/item-form-drawer"; import { useEntryMovedMutation } from "@/hooks/use-entry-moved-mutation"; import { useEntryResizedMutation } from "@/hooks/use-entry-resized-mutation"; import { useTheme } from "@/lib/theme"; export const Route = createFileRoute("/timeline/$timelineId")({ loader: async ({ context, params }) => { await context.queryClient.ensureQueryData( timelineQueryOptions(params.timelineId) ); }, component: RouteComponent, }); function RouteComponent() { const { timelineId } = Route.useParams(); const { data: timeline } = useSuspenseQuery(timelineQueryOptions(timelineId)); const [selectedItemId, setSelectedItemId] = useState(null); const [drawerOpen, setDrawerOpen] = useState(false); const [flutterHeight, setFlutterHeight] = useState(); const entryMoved = useEntryMovedMutation(timelineId); const entryResized = useEntryResizedMutation(timelineId); const { theme, toggleTheme } = useTheme(); const editItem = selectedItemId ? (timeline.items[selectedItemId] ?? null) : null; const flutterState: FlutterTimelineState = useMemo( () => ({ timeline: { id: timeline.id, title: timeline.title }, groups: timeline.groups, items: Object.fromEntries( Object.entries(timeline.items).map(([id, item]) => [ id, { id: item.id, groupId: item.groupId, title: item.title, description: item.description, start: item.start.toISOString(), end: item.end?.toISOString() ?? null, lane: item.lane, }, ]) ), groupOrder: timeline.groupOrder, selectedItemId, darkMode: theme === "dark", }), [timeline, selectedItemId, theme] ); const handleEvent = useCallback( (event: FlutterEvent) => { switch (event.type) { case "content_height": setFlutterHeight(event.payload.height); break; case "item_selected": setSelectedItemId(event.payload.itemId); setDrawerOpen(true); break; case "item_deselected": setSelectedItemId(null); setDrawerOpen(false); break; case "entry_moved": entryMoved.mutate(event.payload); break; case "entry_resized": entryResized.mutate(event.payload); break; } }, [entryMoved, entryResized] ); const handleDrawerOpenChange = useCallback((open: boolean) => { setDrawerOpen(open); if (!open) { setSelectedItemId(null); } }, []); const handleAddItem = useCallback(() => { setSelectedItemId(null); setDrawerOpen(true); }, []); return (

{timeline.title}


); }