ai-chatbot/components/canvas/CanvasGroupToolbar.tsx

126 lines
3.6 KiB
TypeScript

"use client";
import {
Download,
Play,
Ungroup,
Share2,
Grid3X3,
ScanLine,
} from "lucide-react";
export function CanvasGroupToolbar({
title,
color,
status,
busy,
storyboard,
canStoryboard,
onRename,
onColor,
onLayout,
onRun,
onUngroup,
onSave,
onDownload,
onStoryboard,
onCancel,
}: {
title: string;
color: string;
status: string;
busy: boolean;
storyboard: boolean;
canStoryboard: boolean;
onRename: (s: string) => void;
onColor: (s: string) => void;
onLayout: (s: "grid" | "horizontal" | "vertical") => void;
onRun: () => void;
onUngroup: () => void;
onSave: () => void;
onDownload: () => void;
onStoryboard: () => void;
onCancel: () => void;
}) {
return (
<div
data-canvas-overlay="true"
data-group-toolbar="true"
className="absolute left-1/2 top-[80px] z-[70] -translate-x-1/2 rounded-[22px] border border-white/10 bg-[#252525] p-4 text-white shadow-xl"
onPointerDown={(e) => e.stopPropagation()}
>
<div className="flex items-center gap-5 whitespace-nowrap text-[16px]">
<input
aria-label="编组颜色"
type="color"
value={color}
onChange={(e) => onColor(e.target.value)}
className="h-7 w-7 cursor-pointer rounded-full border-0 bg-transparent"
/>
<label title="编组布局" className="flex items-center gap-1">
<Grid3X3 size={20} />
<select
aria-label="编组布局"
defaultValue=""
onChange={(e) => {
onLayout(e.target.value as any);
e.target.value = "";
}}
className="w-5 bg-[#252525]"
>
<option value="" disabled>
⌄
</option>
<option value="grid">网格布局</option>
<option value="horizontal">横向布局</option>
<option value="vertical">纵向布局</option>
</select>
</label>
<span className="h-8 w-px bg-white/10" />
<button
type="button"
disabled={busy}
onClick={onRun}
className="flex items-center gap-2 disabled:opacity-40"
>
<Play size={22} />
整组执行
</button>
<button onClick={onSave} className="flex items-center gap-2">
<Share2 size={22} />
添加到工具箱
</button>
<button
type="button"
disabled={!canStoryboard}
title={
canStoryboard ? "" : "分镜组需要全部成员都是已就绪的图片或视频"
}
onClick={onStoryboard}
className="flex items-center gap-2 disabled:opacity-35"
>
<ScanLine size={22} />
{storyboard ? "预览分镜" : "转分镜组"}
</button>
<button onClick={onUngroup} className="flex items-center gap-2">
<Ungroup size={22} />
解组
</button>
<span className="h-8 w-px bg-white/10" />
<button title="下载编组模板" onClick={onDownload}>
<Download size={22} />
</button>
</div>
<div className="mt-3 flex items-center justify-between gap-4 text-xs text-white/55">
<input
aria-label="编组名称"
value={title}
onChange={(e) => onRename(e.target.value)}
maxLength={120}
className="w-48 border-b border-white/10 bg-transparent py-1"
/>
<span>{status || "Shift 点击多选 · ⌘/Ctrl+G 编组"}</span>
{busy && <button onClick={onCancel}>取消未开始任务</button>}
</div>
</div>
);
}