# 资源轨道 Items 显示修复 **日期**: 2026-02-02 **类型**: Bug Fix **影响范围**: 分镜看板 - 资源轨道 ## 问题描述 资源轨道无法显示任何内容,虽然分镜数据中包含资源信息(`items` 字段中 `itemType=2` 的项),但 `getStoryboardBoardByProjectId` 函数错误地查找 `storyboard.resources` 字段(不存在),导致资源轨道的 items 数组为空。 ### 症状 - 分镜轨道、视频轨道、音效轨道等正常显示 - 资源轨道完全空白,无任何块显示 - 控制台日志显示资源轨道 `itemsCount: 0` ### 根本原因 **数据结构不匹配**: 1. **分镜数据结构**(`mockStoryboards`)使用 v3.0 统一关联表设计: ```typescript { id: '018e1234-5678-7abc-8def-300000000001', items: [ { itemType: 1, // ElementTag elementTagId: '...', }, { itemType: 2, // Resource ✅ 资源数据在这里 resourceId: '...', } ] } ``` 2. **Mock 数据生成函数**(`getStoryboardBoardByProjectId`)错误地查找: ```typescript if (storyboard.resources) { // ❌ 这个字段不存在 storyboard.resources.characters?.forEach(...) } ``` 3. 结果:资源轨道的 items 数组始终为空 ## 解决方案 ### 修复 Mock 数据生成逻辑 修改 `client/src/mocks/storyboard-board.ts` 中的 `getStoryboardBoardByProjectId` 函数: **修改前**: ```typescript // 2. 资源轨道项(从 storyboard.resources 获取) if (storyboard.resources) { storyboard.resources.characters?.forEach((charRef) => { // ... }); } ``` **修改后**: ```typescript // 2. 资源轨道项(从 storyboard.items 中提取 itemType=2 的资源项) if (storyboard.items) { const resourceItems = storyboard.items.filter((item) => item.itemType === 2); resourceItems.forEach((resourceItem) => { if (resourceItem.resourceId) { items.push({ id: `${storyboard.id}-resource-${resourceItem.resourceId}`, trackId: `track-resource-${projectId}`, itemType: 'storyboard', storyboardId: storyboard.id, startTime, endTime, displayOrder: resourceItem.displayOrder || 0, createdAt: resourceItem.createdAt || storyboard.createdAt, updatedAt: storyboard.updatedAt, }); } }); } ``` ### 关键改动 1. **数据源**:从 `storyboard.resources` 改为 `storyboard.items` 2. **过滤条件**:使用 `itemType === 2` 筛选资源项 3. **ID 生成**:统一使用 `${storyboard.id}-resource-${resourceId}` 格式 4. **简化逻辑**:不再区分角色、场景、道具、实拍,统一处理 ## 技术细节 ### 数据流 1. **分镜数据**(`mockStoryboards`) - 每个分镜包含 `items` 数组 - `items` 中 `itemType=2` 的项表示资源关联 2. **Mock 数据生成**(`getStoryboardBoardByProjectId`) - 遍历所有分镜 - 从 `items` 中提取资源项 - 生成资源轨道的 `StoryboardBoardItem` 3. **Mock API**(`storyboardBoardApi.getByProjectId`) - 按 `trackId` 分组 items - 返回包含 items 的 tracks 4. **前端渲染**(`StoryboardBoardTrack`) - 接收 `track.items` - 渲染资源块 ### 资源轨道 Item 结构 ```typescript { id: '018e1234-5678-7abc-8def-300000000001-resource-018e1234-5678-7abc-8def-200000000001', trackId: 'track-resource-018e1234-5678-7abc-8def-100000000001', itemType: 'storyboard', storyboardId: '018e1234-5678-7abc-8def-300000000001', startTime: 0, endTime: 4, displayOrder: 0, } ``` ## 测试验证 ### 验证步骤 1. 刷新浏览器,清除缓存 2. 打开控制台,查看日志: ``` [storyboardBoardApi] 初始化数据: { resourceTrackItems: 24 // ✅ 应该有 24 个(每个分镜至少 1 个资源) } ``` 3. 检查资源轨道是否显示分镜块 ### 预期结果 - 资源轨道显示 24 个分镜块 - 每个块对应一个分镜的时间范围 - 点击资源块时打开资源面板,显示该分镜的资源列表 ## 相关文件 - `client/src/mocks/storyboard-board.ts` - Mock 数据生成(已修复) - `client/src/mocks/storyboards.ts` - 分镜数据定义(使用 items 字段) - `client/src/services/mock/storyboardBoardApi.ts` - Mock API - `client/src/hooks/useStoryboardBoardLogic.ts` - 数据合并逻辑 - `client/src/components/features/storyboard-board/StoryboardBoardTrack.tsx` - 轨道渲染 ## 后续优化 1. 统一数据结构文档,避免类似的字段不匹配问题 2. 添加类型检查,确保 Mock 数据生成函数与实际数据结构一致 3. 考虑添加单元测试验证 `getStoryboardBoardByProjectId` 的输出 ## 参考文档 - [分镜数据结构 v3.0](../../mocks/storyboards.ts) - 使用统一关联表 `items` - [资源轨道与分镜项目集成](./2026-02-02-resource-track-storyboard-items-integration.md)