feat(canvas): 添加视频模型配置和生成功能
- 在系统配置中新增 defaultVideoModel 字段用于设置默认视频模型 - 更新应用配置模态框以支持视频模型的选择和验证 - 修改画布节点逻辑以支持视频类型的生成配置 - 实现视频节点的生成和上传功能 - 更新模型选择器组件以支持视频模型选择 - 在管理后台设置页面添加视频模型配置选项 - 优化模型选择器的层级和交互体验 - 添加对 DeepSeek 和 GLM 模型图标的支持
This commit is contained in:
@@ -30,6 +30,7 @@ const emptySettings: AdminSettings = {
|
||||
availableModels: [],
|
||||
defaultModel: "",
|
||||
defaultImageModel: "",
|
||||
defaultVideoModel: "",
|
||||
defaultTextModel: "",
|
||||
systemPrompt: "",
|
||||
allowCustomChannel: true,
|
||||
@@ -315,17 +316,22 @@ export default function AdminSettingsPage() {
|
||||
<Select mode="tags" tokenSeparators={[",", "\n"]} options={modelOptions.map((item) => ({ label: item, value: item }))} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col xs={24} md={8}>
|
||||
<Col xs={24} md={6}>
|
||||
<Form.Item name={["public", "modelChannel", "defaultModel"]} label="默认模型">
|
||||
<Select showSearch allowClear options={publicModels.map((item) => ({ label: item, value: item }))} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col xs={24} md={8}>
|
||||
<Col xs={24} md={6}>
|
||||
<Form.Item name={["public", "modelChannel", "defaultImageModel"]} label="默认图片模型">
|
||||
<Select showSearch allowClear options={publicModels.map((item) => ({ label: item, value: item }))} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col xs={24} md={8}>
|
||||
<Col xs={24} md={6}>
|
||||
<Form.Item name={["public", "modelChannel", "defaultVideoModel"]} label="默认视频模型">
|
||||
<Select showSearch allowClear options={publicModels.map((item) => ({ label: item, value: item }))} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col xs={24} md={6}>
|
||||
<Form.Item name={["public", "modelChannel", "defaultTextModel"]} label="默认文本模型">
|
||||
<Select showSearch allowClear options={publicModels.map((item) => ({ label: item, value: item }))} />
|
||||
</Form.Item>
|
||||
|
||||
@@ -1819,7 +1819,7 @@ function InfiniteCanvasPage() {
|
||||
size: savedImageMetadata.size || effectiveConfig.size,
|
||||
count: "1",
|
||||
}
|
||||
: { ...buildGenerationConfig(effectiveConfig, sourceNode, node.type === CanvasNodeType.Text ? "text" : "image"), count: "1" };
|
||||
: { ...buildGenerationConfig(effectiveConfig, sourceNode, node.type === CanvasNodeType.Text ? "text" : node.type === CanvasNodeType.Video ? "video" : "image"), count: "1" };
|
||||
if (!isAiConfigReady(generationConfig, generationConfig.model)) {
|
||||
openConfigDialog(true);
|
||||
return;
|
||||
@@ -1855,6 +1855,11 @@ function InfiniteCanvasPage() {
|
||||
setNodes((prev) => prev.map((item) => (item.id === node.id ? { ...item, type: CanvasNodeType.Text, metadata: { ...item.metadata, content: answer || streamed, prompt, status: NODE_STATUS_SUCCESS } } : item)));
|
||||
return;
|
||||
}
|
||||
if (node.type === CanvasNodeType.Video) {
|
||||
const video = await uploadMediaFile(await requestVideoGeneration(generationConfig, prompt), "video");
|
||||
setNodes((prev) => prev.map((item) => (item.id === node.id ? { ...item, metadata: { ...item.metadata, ...videoMetadata(video), prompt, model: generationConfig.model, size: generationConfig.size } } : item)));
|
||||
return;
|
||||
}
|
||||
|
||||
const image = useReferenceImages ? await requestEdit(generationConfig, prompt, retryReferenceImages).then((items) => items[0]) : await requestGeneration(generationConfig, prompt).then((items) => items[0]);
|
||||
const uploadedImage = await uploadImage(image.dataUrl);
|
||||
|
||||
@@ -461,7 +461,7 @@ function VideoNodeContent({ node, theme }: NodeContentRendererProps) {
|
||||
return (
|
||||
<div className="flex h-full w-full flex-col items-center justify-center gap-3" style={{ color: theme.node.placeholder }}>
|
||||
<Video className="size-7 opacity-35" />
|
||||
<span className="text-sm">视频节点</span>
|
||||
<span className="text-sm">视频节点(未开发完,请勿使用)</span>
|
||||
</div>
|
||||
);
|
||||
return <video src={node.metadata.content} controls className="h-full w-full rounded-[18px] bg-black object-contain" data-canvas-no-zoom />;
|
||||
|
||||
Reference in New Issue
Block a user