diff --git a/packages/screen/src/views/3DSituationalAwarenessRefactor/components/LeftPanel/ForcePreset.vue b/packages/screen/src/views/3DSituationalAwarenessRefactor/components/LeftPanel/ForcePreset.vue index f641f24..88cbb80 100644 --- a/packages/screen/src/views/3DSituationalAwarenessRefactor/components/LeftPanel/ForcePreset.vue +++ b/packages/screen/src/views/3DSituationalAwarenessRefactor/components/LeftPanel/ForcePreset.vue @@ -97,7 +97,8 @@
应急人员
- {{ forcePreset.personnel }} + + {{ distance === 30 ? 47 : 69 }}
@@ -177,7 +178,9 @@ const closeDropdown = () => { * 选择选项 * @param {number} value - 选中的距离值 */ +const distance = ref(30); const selectOption = (value) => { + distance.value = value; if (onDistanceChange) { onDistanceChange(value); } diff --git a/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useMapMarkers.js b/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useMapMarkers.js index b2b90ea..f925685 100644 --- a/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useMapMarkers.js +++ b/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useMapMarkers.js @@ -994,6 +994,8 @@ export function useMapMarkers() { ...reserveCenterEntities.value ].filter(e => e.billboard) // 只需要有billboard的实体 + console.log('allEntities', allEntities) + // 存储原始像素偏移量 const entitiesData = allEntities.map(entity => ({ entity, diff --git a/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useRangeCircle.js b/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useRangeCircle.js index 2875468..85245ee 100644 --- a/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useRangeCircle.js +++ b/packages/screen/src/views/3DSituationalAwarenessRefactor/composables/useRangeCircle.js @@ -3,9 +3,9 @@ import { ref } from 'vue' import { DISASTER_CENTER, RANGE_CIRCLE_STYLE } from '../constants' export function useRangeCircle() { - const rangeCircleEntity = ref(null) - const radiusLineEntity = ref(null) // 单独存储半径线实体 - const labelEntity = ref(null) // 单独存储标签实体 + const rangeCircleEntities = ref([]) // 改为数组存储所有范围圈实体 + const radiusLineEntities = ref([]) // 存储所有半径线实体 + const labelEntities = ref([]) // 存储所有标签实体 const createOrUpdateRangeCircle = ( viewer, @@ -25,30 +25,24 @@ export function useRangeCircle() { const radiusMeters = radiusKm * 1000 - // 如果已存在范围圈,先检查半径和中心点是否相同 - if (rangeCircleEntity.value) { - // 获取现有范围圈的半径(从 semiMajorAxis 获取,单位是米,转换为公里) - const existingRadiusKm = rangeCircleEntity.value.ellipse.semiMajorAxis / 1000 + // 检查是否已存在相同半径的范围圈 + const existingCircleIndex = rangeCircleEntities.value.findIndex(entity => { + if (!entity) return false + const existingRadiusKm = entity.ellipse.semiMajorAxis / 1000 + return existingRadiusKm === radiusKm + }) - // 检查中心点是否相同 - const existingPosition = rangeCircleEntity.value.position.getValue() - const newPosition = Cesium.Cartesian3.fromDegrees(centerLon, centerLat, 0) - const centerChanged = !Cesium.Cartesian3.equals(existingPosition, newPosition) - - // 如果半径和中心点都相同,则不需要更新 - if (existingRadiusKm === radiusKm && !centerChanged) { - console.log(`[useRangeCircle] 范围圈半径相同 (${radiusKm}km),无需更新`) - return - } - - // 移除现有实体 - // clearRangeCircle(viewer) + // 如果已存在相同半径的范围圈,则不需要重复创建 + if (existingCircleIndex !== -1) { + showRangeCircle(); + console.log(`[useRangeCircle] 已存在相同半径的范围圈 (${radiusKm}km),无需重复创建`) + return } // 创建中心点坐标 const centerCartesian = Cesium.Cartesian3.fromDegrees(centerLon, centerLat) - // 计算半径线终点(正东方向)- 使用您之前正确的计算方法 + // 计算半径线终点(正东方向) const ellipsoid = Cesium.Ellipsoid.WGS84 const surfaceNormal = ellipsoid.geodeticSurfaceNormal(centerCartesian, new Cesium.Cartesian3()) const tangent = Cesium.Cartesian3.cross(surfaceNormal, Cesium.Cartesian3.UNIT_Z, new Cesium.Cartesian3()) @@ -56,12 +50,17 @@ export function useRangeCircle() { Cesium.Cartesian3.multiplyByScalar(tangent, radiusMeters, tangent) const radiusEndCartesian = Cesium.Cartesian3.add(centerCartesian, tangent, new Cesium.Cartesian3()) - // 计算半径线中点 - const midpointCartesian = new Cesium.Cartesian3() - Cesium.Cartesian3.lerp(centerCartesian, radiusEndCartesian, 0.5, midpointCartesian) + // 计算标签位置(3/4处,并向下偏移) + const labelPositionCartesian = new Cesium.Cartesian3() + Cesium.Cartesian3.lerp(centerCartesian, radiusEndCartesian, 0.75, labelPositionCartesian) + // 计算向下偏移的方向(垂直于半径线方向) + const offsetDirection = Cesium.Cartesian3.cross(Cesium.Cartesian3.UNIT_Z, tangent, new Cesium.Cartesian3()) + Cesium.Cartesian3.normalize(offsetDirection, offsetDirection) + Cesium.Cartesian3.multiplyByScalar(offsetDirection, - radiusMeters * 0.2, offsetDirection) // 向下偏移 20% + Cesium.Cartesian3.add(labelPositionCartesian, offsetDirection, labelPositionCartesian) - // 创建范围圈实体 - rangeCircleEntity.value = viewer.entities.add({ + // 创建范围圈实体并添加到数组 + const circleEntity = viewer.entities.add({ position: centerCartesian, ellipse: { semiMinorAxis: radiusMeters, @@ -74,9 +73,10 @@ export function useRangeCircle() { }, allowPicking: false }) + rangeCircleEntities.value.push(circleEntity) - // 创建半径线实体 - radiusLineEntity.value = viewer.entities.add({ + // 创建半径线实体并添加到数组 + const lineEntity = viewer.entities.add({ polyline: { positions: [centerCartesian, radiusEndCartesian], width: 2, @@ -84,10 +84,11 @@ export function useRangeCircle() { }, allowPicking: false }) + radiusLineEntities.value.push(lineEntity) - // 创建标签实体(单独创建,位置设为半径线中点) - labelEntity.value = viewer.entities.add({ - position: midpointCartesian, + // 创建标签实体并添加到数组 + const currentLabelEntity = viewer.entities.add({ + position: labelPositionCartesian, label: { text: `${radiusKm - 20} km`, font: 'bold 16px sans-serif', @@ -95,55 +96,55 @@ export function useRangeCircle() { outlineColor: Cesium.Color.BLACK, outlineWidth: 2, style: Cesium.LabelStyle.FILL_AND_OUTLINE, - verticalOrigin: Cesium.VerticalOrigin.CENTER, + verticalOrigin: Cesium.VerticalOrigin.BOTTOM, // 调整垂直原点为底部 horizontalOrigin: Cesium.HorizontalOrigin.CENTER, - pixelOffset: new Cesium.Cartesian2(0, 0), + pixelOffset: new Cesium.Cartesian2(0, 10), // 增加像素偏移,确保标签不在半径线上 backgroundColor: Cesium.Color.fromCssColorString('#333').withAlpha(0.7), backgroundPadding: new Cesium.Cartesian2(8, 6), showBackground: true, }, allowPicking: false }) + labelEntities.value.push(currentLabelEntity) - console.log(`[useRangeCircle] 已创建/更新范围圈: ${radiusKm}km`) + console.log(`[useRangeCircle] 已创建范围圈: ${radiusKm}km`) } + // 其他函数也需要相应修改为操作数组 const showRangeCircle = () => { - if (rangeCircleEntity.value) rangeCircleEntity.value.show = true - if (radiusLineEntity.value) radiusLineEntity.value.show = true - if (labelEntity.value) labelEntity.value.show = true + rangeCircleEntities.value.forEach(entity => entity.show = true) + radiusLineEntities.value.forEach(entity => entity.show = true) + labelEntities.value.forEach(entity => entity.show = true) } const hideRangeCircle = () => { - if (rangeCircleEntity.value) rangeCircleEntity.value.show = false - if (radiusLineEntity.value) radiusLineEntity.value.show = false - if (labelEntity.value) labelEntity.value.show = false + rangeCircleEntities.value.forEach(entity => entity.show = false) + radiusLineEntities.value.forEach(entity => entity.show = false) + labelEntities.value.forEach(entity => entity.show = false) } const clearRangeCircle = (viewer) => { if (!viewer) return - - if (rangeCircleEntity.value) { - viewer.entities.remove(rangeCircleEntity.value) - rangeCircleEntity.value = null - } - if (radiusLineEntity.value) { - viewer.entities.remove(radiusLineEntity.value) - radiusLineEntity.value = null - } - if (labelEntity.value) { - viewer.entities.remove(labelEntity.value) - labelEntity.value = null - } - - console.log('[useRangeCircle] 范围圈已清除') + + // 清除所有实体 + rangeCircleEntities.value.forEach(entity => viewer.entities.remove(entity)) + radiusLineEntities.value.forEach(entity => viewer.entities.remove(entity)) + labelEntities.value.forEach(entity => viewer.entities.remove(entity)) + + // 清空数组 + rangeCircleEntities.value = [] + radiusLineEntities.value = [] + labelEntities.value = [] + + console.log('[useRangeCircle] 所有范围圈已清除') } return { - rangeCircleEntity, + rangeCircleEntities, // 返回数组 createOrUpdateRangeCircle, showRangeCircle, hideRangeCircle, clearRangeCircle, } } + diff --git a/packages/screen/src/views/3DSituationalAwarenessRefactor/constants/index.js b/packages/screen/src/views/3DSituationalAwarenessRefactor/constants/index.js index 8770bcc..373f5fd 100644 --- a/packages/screen/src/views/3DSituationalAwarenessRefactor/constants/index.js +++ b/packages/screen/src/views/3DSituationalAwarenessRefactor/constants/index.js @@ -25,7 +25,7 @@ export const VIDEO_MONITORS = [ title: '单兵(张维)设备视角', videoSrc: 'http://222.212.85.86:9000/300bdf2b-a150-406e-be63-d28bd29b409f/demo/ylzg/单兵视角.mp4', - dateRange: '2025/9/1-2025/12/1', + // dateRange: '2025/9/1-2025/12/1', hasAudio: true, hasMegaphone: true, hasZoom: true, @@ -37,7 +37,7 @@ export const VIDEO_MONITORS = [ title: '无人机(001)视角', videoSrc: 'http://222.212.85.86:9000/300bdf2b-a150-406e-be63-d28bd29b409f/demo/ylzg/无人机视角.mp4', - dateRange: '2025/9/1-2025/12/1', + // dateRange: '2025/9/1-2025/12/1', hasAudio: false, hasMegaphone: true, hasZoom: true, @@ -49,7 +49,7 @@ export const VIDEO_MONITORS = [ title: '设备操作视角', videoSrc: 'http://222.212.85.86:9000/300bdf2b-a150-406e-be63-d28bd29b409f/demo/ylzg/设备视角.mp4', - dateRange: '2025/9/1-2025/12/1', + // dateRange: '2025/9/1-2025/12/1', hasAudio: true, hasMegaphone: true, hasZoom: true, @@ -61,7 +61,7 @@ export const VIDEO_MONITORS = [ title: '指挥会议室视角', videoSrc: 'http://222.212.85.86:9000/300bdf2b-a150-406e-be63-d28bd29b409f/demo/ylzg/指挥会议室视角.mp4', - dateRange: '2025/9/1-2025/12/1', + // dateRange: '2025/9/1-2025/12/1', hasAudio: true, hasMegaphone: true, hasZoom: true, diff --git a/packages/screen/src/views/3DSituationalAwarenessRefactor/index.vue b/packages/screen/src/views/3DSituationalAwarenessRefactor/index.vue index 4117894..f9c976f 100644 --- a/packages/screen/src/views/3DSituationalAwarenessRefactor/index.vue +++ b/packages/screen/src/views/3DSituationalAwarenessRefactor/index.vue @@ -564,6 +564,9 @@ const handleVideoModalClose = () => { const handleStartDispatch = async (payload) => { console.log("[index.vue] 启动响应调度"); + await createOrUpdateRangeCircle(mapStore.viewer, 30); + await createOrUpdateRangeCircle(mapStore.viewer, 50); + // Check if Quick Response has been executed if (!quickResponseExecuted.value) { console.log("[index.vue] 快速响应未执行,自动执行..."); @@ -1461,7 +1464,6 @@ const initializeScene = async () => { heightReference: Cesium.HeightReference.CLAMP_TO_GROUND, disableDepthTestDistance: Number.POSITIVE_INFINITY, }, - priority: 10000, // 这个设置好像并不能让中心点位于所有实体之上 我不知道为什么 }); console.log("[index.vue] 中心点标记已添加");