import { useState } from "react"; import { Button } from "@/components/ui/button"; import { Card, CardContent, CardHeader, CardTitle, CardDescription } from "@/components/ui/card"; import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger, DialogDescription, DialogFooter } from "@/components/ui/dialog"; import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"; import { Code, Table as TableIcon, BarChart as ChartIcon, LayoutDashboard } from "lucide-react"; import { ScrollArea } from "@/components/ui/scroll-area"; import { useDashboardStore, type ChartConfig } from "@/store/dashboardStore"; import type { ChartSpec } from "@/store/visualizationStore"; import { VegaChart } from "./VegaChart"; interface InlineVisualizationCardProps { viz: { sql: string; rows: unknown[]; chartSpec: ChartSpec | null; canVisualize: boolean; reasoning?: string; error?: string | null; }; } export function InlineVisualizationCard({ viz }: InlineVisualizationCardProps) { const [view, setView] = useState<'table' | 'chart'>('chart'); const [confirmOpen, setConfirmOpen] = useState(false); const [pendingChart, setPendingChart] = useState | null>(null); const { addChart } = useDashboardStore(); const objectRows = viz.rows.filter((row) => row && typeof row === "object" && !Array.isArray(row)) as Record[]; const columns = objectRows.length > 0 ? Object.keys(objectRows[0]) : []; const buildPendingChart = (): Omit => { const mark = viz.chartSpec?.mark; const markType = typeof mark === "string" ? mark : mark?.type; const dashboardType = markType === "line" ? "line" : "bar"; return { id: Date.now().toString(), title: viz.chartSpec?.title || "Generated Analysis", type: dashboardType, data: objectRows, sql: viz.sql, chartSpec: viz.chartSpec, }; }; const handleAddToDashboard = () => { const chart = buildPendingChart(); setPendingChart(chart); setConfirmOpen(true); }; const handleConfirmAdd = () => { if (!pendingChart) return; addChart(pendingChart); setConfirmOpen(false); setPendingChart(null); }; if (viz.error) { return
{viz.error}
; } return ( {viz.chartSpec?.title || "可视化结果"} {viz.reasoning || "根据当前回答生成的可视化"}
SQL } /> Generated SQL Query 用于生成当前图表的数据查询语句。
{viz.sql || "--"}
{view === "chart" ? ( viz.canVisualize && viz.chartSpec && objectRows.length > 0 ? (
) : (
本次结果不适合图表展示。
) ) : objectRows.length > 0 ? ( {columns.map((col) => {col})} {objectRows.map((row, i) => ( {columns.map((col) => ( {String(row[col] ?? "")} ))} ))}
) : (
当前结果没有可渲染的结构化数据。
)}
确认加入 Dashboard 将当前图表添加到 Dashboard,是否继续?
); }