import type { CSSProperties, MouseEvent as ReactMouseEvent, ReactNode, RefObject } from "react"; import { useRef, useState } from "react"; import { Button, Segmented } from "antd"; import { CircleDot, Eraser, FolderOpen, Grid2x2, Hand, Image as ImageIcon, Library, Moon, Palette, Redo2, Settings2, Square, Sun, Trash2, Type, Undo2, Upload, Video } from "lucide-react"; import { canvasThemes, type CanvasBackgroundMode, type CanvasColorTheme, type CanvasTheme } from "@/lib/canvas-theme"; import { useThemeStore } from "@/stores/use-theme-store"; import { AnimatedThemeToggler } from "@/components/ui/animated-theme-toggler"; export function CanvasToolbar({ selectedCount, canUndo, canRedo, backgroundMode, onAddImage, onAddVideo, onAddText, onAddConfig, onUndo, onRedo, onUpload, onDelete, onClear, onDeselect, onBackgroundModeChange, onOpenAssetLibrary, onOpenMyAssets, }: { selectedCount: number; canUndo: boolean; canRedo: boolean; backgroundMode: CanvasBackgroundMode; onAddImage: () => void; onAddVideo: () => void; onAddText: () => void; onAddConfig: () => void; onUndo: () => void; onRedo: () => void; onUpload: () => void; onDelete: () => void; onClear: () => void; onDeselect: () => void; onBackgroundModeChange: (mode: CanvasBackgroundMode) => void; onOpenAssetLibrary: () => void; onOpenMyAssets: () => void; }) { const wrapRef = useRef(null); const colorTheme = useThemeStore((state) => state.theme); const setTheme = useThemeStore((state) => state.setTheme); const theme = canvasThemes[colorTheme]; const [hovered, setHovered] = useState(null); const [tipX, setTipX] = useState(0); const [appearanceOpen, setAppearanceOpen] = useState(false); const [panelX, setPanelX] = useState(0); const dockStyle = { background: theme.toolbar.panel, borderColor: theme.toolbar.border, color: theme.toolbar.item, boxShadow: colorTheme === "dark" ? "0 18px 45px rgba(0,0,0,.32)" : "0 16px 40px rgba(28,25,23,.12)" }; const hoverStyle = { background: theme.toolbar.itemHover, color: theme.toolbar.activeText }; const activeStyle = { background: theme.toolbar.activeBg, color: theme.toolbar.activeText }; const tip = hovered ? toolLabel(hovered) : ""; return (
{tip ? : null}
{ setPanelX(getTipX(wrapRef.current, event.currentTarget)); setAppearanceOpen((value) => !value); }} > {selectedCount ? ( <> ) : null}
{appearanceOpen ? (
画布外观
主题模式
浅色 深色
网格样式
onBackgroundModeChange(value as CanvasBackgroundMode)} options={[ { value: "dots", label: ( ), }, { value: "lines", label: ( 线 ), }, { value: "blank", label: ( 空白 ), }, ]} />
) : null}
); } function ToolbarButton({ id, label, active, hovered, activeStyle, hoverStyle, wrapRef, onTipX, onHover, onClick, disabled = false, danger = false, children, }: { id: string; label: string; active?: boolean; hovered: string | null; activeStyle?: CSSProperties; hoverStyle: CSSProperties; wrapRef: RefObject; onTipX: (x: number) => void; onHover: (id: string | null) => void; onClick?: (event: ReactMouseEvent) => void; disabled?: boolean; danger?: boolean; children: ReactNode; }) { const theme = canvasThemes[useThemeStore((state) => state.theme)]; return (