TravelContentCreator/docs/fabric_json_standard.md

7.2 KiB
Raw Blame History

后端Fabric.js JSON格式规范

标准格式要求

1. 根对象结构

{
  "version": "5.3.0",
  "width": 1350,
  "height": 1800,
  "objects": [
    // 对象数组
  ]
}

2. 对象类型要求只使用标准Fabric.js类型

允许的标准类型:

  • rect - 矩形
  • circle - 圆形
  • textbox - 文本框
  • text - 文本
  • image - 图片
  • line - 线条
  • polygon - 多边形
  • path - 路径
  • group - 组

禁止的自定义类型:

  • CustomRect -> 应改为 rect
  • CustomTextbox -> 应改为 textbox
  • CustomCircle -> 应改为 circle
  • CustomGroup -> 应改为 group
  • ThinTailArrow -> 应改为 pathrect
  • Arrow -> 应改为 pathrect

3. 基本对象属性要求

所有对象必须包含:

{
  "type": "rect", // 标准类型
  "left": 100,    // 数值非null
  "top": 50,      // 数值非null
  "width": 200,   // 数值 > 0
  "height": 100,  // 数值 > 0
  "fill": "#ffffff",
  "opacity": 1,
  "angle": 0,
  "scaleX": 1,
  "scaleY": 1
}

文本对象额外属性:

{
  "type": "textbox",
  "text": "实际文本内容", // 非空字符串
  "fontSize": 16,        // 数值 > 0
  "fontFamily": "Arial", // 有效字体名
  "fill": "#000000"
}

图片对象要求:

{
  "type": "image",
  "src": "https://example.com/image.jpg", // 必须是完整有效的URL
  "width": 300,  // 实际图片宽度
  "height": 200  // 实际图片高度
}

重要图片src必须是可访问的完整URL不能是

  • 相对路径如 preview1.jpg
  • 本地路径如 ./images/test.png
  • 占位符如 image1.jpg

4. 组对象格式:

{
  "type": "group",
  "objects": [
    // 组内的标准对象
  ]
}

5. 完整示例:

{
  "version": "5.3.0",
  "width": 1350,
  "height": 1800,
  "objects": [
    {
      "type": "rect",
      "left": 100,
      "top": 100,
      "width": 200,
      "height": 150,
      "fill": "#ff0000",
      "opacity": 1,
      "angle": 0,
      "scaleX": 1,
      "scaleY": 1
    },
    {
      "type": "textbox",
      "left": 50,
      "top": 300,
      "width": 300,
      "height": 50,
      "text": "这是文本内容",
      "fontSize": 24,
      "fontFamily": "Arial",
      "fill": "#000000",
      "opacity": 1
    },
    {
      "type": "image",
      "left": 400,
      "top": 100,
      "width": 200,
      "height": 200,
      "src": "https://example.com/path/to/image.jpg",
      "opacity": 1
    }
  ]
}

复杂装饰元素处理策略

问题:复杂的装饰性元素(如按钮、装饰图案)

  • 旧方案使用多个形状组合rect + circle + path等
  • 新方案:将复杂元素预渲染为图像

实现方式:

  1. 后端预渲染将复杂的按钮样式、装饰图案等渲染为PNG图像
  2. 托管图像将这些装饰图像托管在可访问的URL上
  3. JSON引用在fabric.js JSON中使用标准image对象引用

示例:按钮元素

// ❌ 旧方式:复杂形状组合
{
  "type": "group",
  "objects": [
    {"type": "rect", "fill": "linear-gradient(...)", ...},
    {"type": "circle", "fill": "rgba(...)", ...},
    {"type": "path", "path": "M10,10 L20,20...", ...}
  ]
}

// ✅ 新方式:预渲染图像
{
  "type": "image",
  "left": 100,
  "top": 200,
  "width": 120,
  "height": 40,
  "src": "https://your-domain.com/api/decorative/button_style_1.png",
  "opacity": 1
}

关键要求总结:

  1. 只使用Fabric.js标准对象类型
  2. 所有数值属性必须有效非null、非0宽高
  3. 图片src必须是完整可访问的URL
  4. 包含完整的width/height信息
  5. 遵循标准JSON结构
  6. 复杂装饰元素使用预渲染图像

这样前端就可以直接使用 canvas.loadFromJSON() 而无需任何预处理!

装饰性图像处理流程

完整的端到端流程:

  1. Python端生成装饰图像

  2. Java端处理装饰图像

    • 接收装饰图像的base64数据
    • 上传每个装饰图像到七牛云存储
    • 获取七牛云的真实URL
    • 替换fabric.js JSON中的占位符URL为真实URL
  3. 前端使用

    • 接收更新后的fabric.js JSON包含真实的图像URL
    • 直接使用canvas.loadFromJSON()加载完整设计

API响应结构

{
  "requestId": "poster-20250101-120000-abc123",
  "templateId": "vibrant",
  "resultImagesBase64": [...],
  "fabricJsons": [
    {
      "id": "fabric_json_0",
      "data": "base64_encoded_json...",
      "jsonData": {
        "version": "5.3.0",
        "width": 1350,
        "height": 1800,
        "objects": [
          {
            "type": "image",
            "src": "https://qiniu-domain.com/poster/decorative/2025/01/01/button_1234567890.png",
            "left": 100,
            "top": 200,
            "width": 200,
            "height": 60
          }
        ]
      }
    }
  ],
  "decorativeImages": {
    "button": {
      "originalId": "button",
      "type": "button",
      "qiniuUrl": "https://qiniu-domain.com/poster/decorative/2025/01/01/button_1234567890.png",
      "uploadSuccess": true
    }
  }
}

实现状态

已完成:

  • 标准fabric.js JSON格式输出
  • 简化的文本布局只使用textbox/text
  • 装饰性图像生成器(按钮、标签、价格背景)
  • 装饰图像上传到七牛云的完整流程
  • fabric.js JSON中占位符URL自动替换
  • 统一1350x1800基础尺寸
  • 端到端的装饰图像处理工作流

统一生成架构(重大改进)

问题解决:

原问题fabric.js JSON和PNG分开生成导致参数不一致、位置偏差等问题。

解决方案VibrantTemplate统一生成模式

  • PNG和Fabric.js JSON在同一次render调用中生成
  • 使用完全相同的参数、计算逻辑、渲染上下文
  • 消除任何可能的差异来源

技术实现:

  1. VibrantTemplate.generate()扩展

    # 新增参数
    generation_result = template.generate(
        content=content,
        images=images,
        generate_fabric_json=True  # 启用统一生成
    )
    
    # 返回结构
    {
        'png': PIL.Image,
        'fabric_json': Dict,
        'metadata': {
            'gradient_start': int,
            'theme_color': str,
            'elements_count': int
        }
    }
    
  2. 渲染上下文共享

    • 图像处理参数
    • 渐变起始位置
    • 颜色提取结果
    • 文本布局计算
    • 所有几何计算
  3. 向后兼容性

    • 自动检测模板是否支持新参数
    • 无缝回退到独立生成模式
    • 不影响现有的模板实现

已完成:

  • 标准fabric.js JSON格式输出
  • 简化的文本布局只使用textbox/text
  • 装饰性图像生成器(按钮、标签、价格背景)
  • 装饰图像上传到七牛云的完整流程
  • fabric.js JSON中占位符URL自动替换
  • 统一1350x1800基础尺寸
  • 端到端的装饰图像处理工作流
  • VibrantTemplate统一生成架构
  • PNG和JSON完全一致的渲染逻辑

🔄 进行中:

  • 测试统一生成模式的一致性验证