diff --git a/src/pages/scene-editor.vue b/src/pages/scene-editor.vue index 699b7c8..908cb51 100644 --- a/src/pages/scene-editor.vue +++ b/src/pages/scene-editor.vue @@ -277,7 +277,7 @@ const importScene = async () => { currentFloorIndex.value = 0; previousFloorIndex.value = 0; // 加载第一个楼层到编辑器 - await editor.value?.load(floorScenes.value[0], editable.value, undefined, requireImportTransform.value); + await editor.value?.load(floorScenes.value[0], editable.value, undefined, requireImportTransform.value, true); message.success(`成功导入 ${sceneData.length} 个楼层,当前显示第一层。`); } else { message.warn('导入的场景文件是一个空数组,已加载空场景。'); @@ -293,7 +293,7 @@ const importScene = async () => { currentFloorIndex.value = 0; previousFloorIndex.value = 0; // 直接加载(editor.load可以接受对象或字符串) - await editor.value?.load(sceneData, editable.value, undefined, requireImportTransform.value); + await editor.value?.load(sceneData, editable.value, undefined, requireImportTransform.value, true); message.success('成功导入单楼层场景。'); } else { message.error('导入失败,场景文件为空或格式不正确。'); @@ -332,7 +332,7 @@ const handleImportSmapConfirm = async ({ smapFile, keepProperties }: { smapFile: if (sceneJson) { requireImportTransform.value = true; - editor.value?.load(sceneJson, editable.value, undefined, requireImportTransform.value); + editor.value?.load(sceneJson, editable.value, undefined, requireImportTransform.value, true); } }; @@ -450,7 +450,13 @@ const handleFloorChange = async (value: any) => { // 加载新楼层 currentFloorIndex.value = newFloorIndex; previousFloorIndex.value = newFloorIndex; - await editor.value.load(floorScenes.value[newFloorIndex], editable.value, undefined, requireImportTransform.value); + await editor.value.load( + floorScenes.value[newFloorIndex], + editable.value, + undefined, + requireImportTransform.value, + true, // Merge robot data + ); } else { currentFloorIndex.value = newFloorIndex; previousFloorIndex.value = newFloorIndex; diff --git a/src/services/editor-robot.service.ts b/src/services/editor-robot.service.ts index 766a36e..b8c4c1d 100644 --- a/src/services/editor-robot.service.ts +++ b/src/services/editor-robot.service.ts @@ -55,6 +55,55 @@ export class EditorRobotService { this.syncRobotLabels(); } + public mergeRobotsData(groups?: RobotGroup[], robots?: RobotInfo[], labels?: RobotLabel[]): void { + const existingGroups = clone(this.robotGroups$$.value); + const existingLabels = clone(this.robotLabels$$.value); + + // Merge robot groups + groups?.forEach(newGroup => { + const existingGroup = existingGroups.find(g => g.id === newGroup.id || g.label === newGroup.label); + if (existingGroup) { + // Merge robots within the group + newGroup.robots?.forEach(robotId => { + if (!existingGroup.robots?.includes(robotId)) { + existingGroup.robots?.push(robotId); + } + }); + } else { + existingGroups.push(newGroup); + } + }); + + // Merge robot labels + labels?.forEach(newLabel => { + const existingLabel = existingLabels.find(l => l.id === newLabel.id || l.label === newLabel.label); + if (existingLabel) { + // Merge robots within the label + newLabel.robots?.forEach(robotId => { + if (!existingLabel.robots?.includes(robotId)) { + existingLabel.robots?.push(robotId); + } + }); + } else { + existingLabels.push(newLabel); + } + }); + + // Merge robots + robots?.forEach(robot => { + if (!this.robotMap.has(robot.id)) { + this.robotMap.set(robot.id, robot); + } + }); + + this.robotGroups$$.next(existingGroups); + this.robotLabels$$.next(existingLabels); + + this.syncRobots(); + this.syncRobotGroups(); + this.syncRobotLabels(); + } + public get robots(): RobotInfo[] { return Array.from(this.robotMap.values()); } diff --git a/src/services/editor.service.ts b/src/services/editor.service.ts index 0c5b1c6..6739a4d 100644 --- a/src/services/editor.service.ts +++ b/src/services/editor.service.ts @@ -78,6 +78,7 @@ export class EditorService extends Meta2d { editable = false, detail?: Partial, isImport = false, + isMerge = false, ): Promise { const sceneData = (isString(map) ? (map ? JSON.parse(map) : {}) : map); const scene: StandardScene = sceneData || {}; @@ -93,7 +94,11 @@ export class EditorService extends Meta2d { this.open(); this.setState(editable); - this.robotService.loadInitialData(robotGroups, robots, robotLabels); + if (isMerge) { + this.robotService.mergeRobotsData(robotGroups, robots, robotLabels); + } else { + this.robotService.loadInitialData(robotGroups, robots, robotLabels); + } await this.#loadScenePoints(points, isImport); this.#loadSceneRoutes(routes, isImport); await this.#loadSceneAreas(areas, isImport);