feat(annotation): 添加模板示例数据配置功能

- 在模板配置表单中新增示例数据输入区域
- 实现不同数据类型的示例输入框(文本、图片、音频、视频等)
- 添加图片类型示例的实时预览功能
- 在模板详情页增加示例数据预览卡片
- 支持多种媒体类型的示例展示(图片、音频、视频、文本)
- 更新前后端数据模型以支持exampleData字段
- 添加示例数据的placeholder提示文案
This commit is contained in:
2026-01-18 21:59:41 +08:00
parent 5057457329
commit a2b0fc3674
4 changed files with 177 additions and 2 deletions

View File

@@ -1,5 +1,5 @@
import React from "react";
import { Modal, Descriptions, Tag, Space, Divider, Card, Typography } from "antd";
import { Modal, Descriptions, Tag, Space, Divider, Card, Typography, Image, Empty } from "antd";
import type { AnnotationTemplate } from "../annotation.model";
const { Text, Paragraph } = Typography;
@@ -81,6 +81,69 @@ const TemplateDetail: React.FC<TemplateDetailProps> = ({
</Space>
</Card>
{/* 示例数据预览 */}
<Card title="示例数据预览" size="small" style={{ marginBottom: 16 }}>
{template.configuration.exampleData &&
Object.keys(template.configuration.exampleData).length > 0 ? (
<Space direction="vertical" style={{ width: "100%" }} size="middle">
{template.configuration.objects.map((obj, index) => {
const varName = obj.value?.replace(/^\$/, "") || obj.name;
const exampleValue = template.configuration.exampleData?.[varName];
if (!exampleValue) return null;
return (
<Card key={index} size="small" type="inner">
<Space direction="vertical" style={{ width: "100%" }}>
<div>
<Text strong>{obj.name}</Text>
<Text type="secondary" style={{ marginLeft: 8 }}>
({obj.type})
</Text>
</div>
{/* 根据类型渲染不同的预览 */}
{obj.type === "Image" ? (
<Image
src={exampleValue}
alt={`示例: ${obj.name}`}
style={{ maxHeight: 200, maxWidth: "100%" }}
fallback="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAMIAAADDCAYAAADQvc6UAAABRWlDQ1BJQ0MgUHJvZmlsZQAAKJFjYGASSSwoyGFhYGDIzSspCnJ3UoiIjFJgf8LAwSDCIMogwMCcmFxc4BgQ4ANUwgCjUcG3awyMIPqyLsis7PPOq3QdDFcvjV3jOD1boQVTPQrgSkktTgbSf4A4LbmgqISBgTEFyFYuLykAsTuAbJEioKOA7DkgdjqEvQHEToKwj4DVhAQ5A9k3gGyB5IxEoBmML4BsnSQk8XQkNtReEOBxcfXxUQg1Mjc0dyHgXNJBSWpFCYh2zi+oLMpMzyhRcASGUqqCZ16yno6CkYGRAQMDKMwhqj/fAIcloxgHQqxAjIHBEugw5sUIsSQpBobtQPdLciLEVJYzMPBHMDBsayhILEqEO4DxG0txmrERhM29nYGBddr//5/DGRjYNRkY/l7////39v///y4Dmn+LgesAAN4TeleOJA8AAAA="
/>
) : obj.type === "Audio" ? (
<audio
src={exampleValue}
controls
style={{ width: "100%" }}
/>
) : obj.type === "Video" ? (
<video
src={exampleValue}
controls
style={{ maxHeight: 200, maxWidth: "100%" }}
/>
) : (
<Paragraph
style={{
background: "#f5f5f5",
padding: 12,
borderRadius: 4,
margin: 0,
whiteSpace: "pre-wrap",
}}
>
{exampleValue}
</Paragraph>
)}
</Space>
</Card>
);
})}
</Space>
) : (
<Empty description="暂无示例数据" image={Empty.PRESENTED_IMAGE_SIMPLE} />
)}
</Card>
<Card title="标注控件" size="small" style={{ marginBottom: 16 }}>
<Space direction="vertical" style={{ width: "100%" }} size="middle">
{template.configuration.labels.map((label, index) => (