feat(movement-supervision): 增强场景数据解析逻辑,适配多种后端数据格式并优化楼层切换后定位功能
This commit is contained in:
parent
8cde103ac9
commit
e69b0419de
@ -38,6 +38,25 @@ const props = defineProps<Props>();
|
||||
// 获取路由信息以判断当前模式
|
||||
const route = useRoute();
|
||||
|
||||
// 适配多种后端数据格式的解析(参考 scene-editor.vue)
|
||||
const normalizeSceneJson = (raw: unknown): unknown => {
|
||||
if (raw == null) return raw;
|
||||
let result: unknown = raw;
|
||||
const maxDepth = 2;
|
||||
let depth = 0;
|
||||
while (typeof result === 'string' && depth < maxDepth) {
|
||||
const trimmed = (result as string).trim();
|
||||
if (!trimmed) break;
|
||||
try {
|
||||
result = JSON.parse(trimmed);
|
||||
} catch {
|
||||
break;
|
||||
}
|
||||
depth += 1;
|
||||
}
|
||||
return result;
|
||||
};
|
||||
|
||||
//#region Playback Mode
|
||||
const mode = computed(() => (route.path.includes('/playback') ? 'playback' : 'live'));
|
||||
const isPlaybackMode = computed(() => mode.value === 'playback');
|
||||
@ -162,30 +181,33 @@ provide(EDITOR_KEY, editor);
|
||||
const readScene = async () => {
|
||||
const res = props.id ? await getSceneByGroupId(props.id, props.sid) : await getSceneById(props.sid);
|
||||
title.value = res?.label ?? '';
|
||||
const sceneJson = normalizeSceneJson(res?.json);
|
||||
|
||||
// 检查返回的json是数组(多楼层)还是对象(单楼层)
|
||||
if (Array.isArray(res?.json)) {
|
||||
if (res.json.length > 0) {
|
||||
if (Array.isArray(sceneJson)) {
|
||||
if (sceneJson.length > 0) {
|
||||
// 多楼层
|
||||
floorScenes.value = res.json;
|
||||
floorScenes.value = sceneJson as any[];
|
||||
currentFloorIndex.value = 0; // 默认显示第一层
|
||||
editor.value?.load(floorScenes.value[0]);
|
||||
await editor.value?.load(floorScenes.value[0]);
|
||||
} else {
|
||||
// 空数组,当作空场景处理
|
||||
floorScenes.value = [];
|
||||
editor.value?.load('{}'); // 加载空场景
|
||||
message.warn('场景文件为空');
|
||||
message.warn('场景文件为空数组');
|
||||
floorScenes.value = [{}];
|
||||
currentFloorIndex.value = 0;
|
||||
await editor.value?.load('{}'); // 加载空场景
|
||||
}
|
||||
} else if (res?.json && Object.keys(res.json).length > 0) {
|
||||
} else if (sceneJson && typeof sceneJson === 'object' && Object.keys(sceneJson as any).length > 0) {
|
||||
// 单楼层,包装成数组以统一处理
|
||||
floorScenes.value = [res.json];
|
||||
floorScenes.value = [sceneJson];
|
||||
currentFloorIndex.value = 0;
|
||||
editor.value?.load(res.json);
|
||||
await editor.value?.load(sceneJson as any);
|
||||
} else {
|
||||
// 空对象或null/undefined,也当作空场景处理
|
||||
floorScenes.value = [];
|
||||
editor.value?.load('{}'); // 加载空场景
|
||||
message.warn('场景文件为空或格式不正确');
|
||||
floorScenes.value = [{}];
|
||||
currentFloorIndex.value = 0;
|
||||
await editor.value?.load('{}'); // 加载空场景
|
||||
}
|
||||
};
|
||||
|
||||
@ -597,7 +619,7 @@ const selectRobot = (id: string) => {
|
||||
//#endregion
|
||||
|
||||
//#region 视图状态管理
|
||||
const { saveViewState, autoSaveAndRestoreViewState, isSaving } = useViewState();
|
||||
const { saveViewState, autoSaveAndRestoreViewState, isSaving, jumpToPosition, calculateCenterPoint } = useViewState();
|
||||
|
||||
/**
|
||||
* 保存当前视图状态
|
||||
@ -634,6 +656,13 @@ const handleFloorChange = async (value: any) => {
|
||||
if (mode.value === 'live') {
|
||||
await monitorScene();
|
||||
}
|
||||
// 楼层切换后定位到中心(参考 map-toolbar.vue)
|
||||
try {
|
||||
const { centerX, centerY } = calculateCenterPoint(editor.value);
|
||||
jumpToPosition(editor.value, centerX, centerY, false, 0.05);
|
||||
} catch {
|
||||
// ignore
|
||||
}
|
||||
}
|
||||
};
|
||||
//#endregion
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user