From f1e4e5843ff9ae37ccecd0ea391911f67de0e50d Mon Sep 17 00:00:00 2001
From: 罗广辉 <guanghui.luo@foxmail.com>
Date: Sat, 29 Mar 2025 16:02:53 +0800
Subject: [PATCH] feat: 机巢点击交互
---
src/views/Home/useAggregation.js | 74 ++++++++++++++++++++++++++++++++-----
1 files changed, 64 insertions(+), 10 deletions(-)
diff --git a/src/views/Home/useAggregation.js b/src/views/Home/useAggregation.js
index 32756bd..db6ec45 100644
--- a/src/views/Home/useAggregation.js
+++ b/src/views/Home/useAggregation.js
@@ -4,19 +4,24 @@
import jiangxishi from '@/assets/geojson/jiangxishi.json';
import jiangxi from '@/assets/geojson/jiangxi.json';
import zg from '@/assets/geojson/zg.json';
+import MapPopUpBox from '@/views/Home/MapPopUpBox.vue';
+import { render } from 'vue';
/**
* 机巢聚合功能
*/
export const useAggregation = () => {
- let viewer = null;
const scalingJudgment = [
{ name: '县', value: [0, 48651], gJson: null },
{ name: '市', value: [48651, 314863], gJson: jiangxishi },
{ name: '省', value: [314863, 1169651], gJson: jiangxi },
{ name: '国', value: [1169651, 37962800], gJson: zg },
];
+ let viewer = null;
const active = ref('');
+ let handler = null;
+ let labelDiv = null;
+ let positionC3 = null;
const init = () => {
determineScaling();
viewer.camera.moveEnd.addEventListener(() => {
@@ -24,18 +29,15 @@
});
};
- const removeFun = () => {
- viewer.dataSources.removeAll(true);
- viewer.entities.removeAll();
- };
-
+ // 确定缩放比例
const determineScaling = () => {
let height = viewer.camera.positionCartographic.height;
// 根据高度展示对应的 gJson
for (let item of scalingJudgment) {
if (height > item.value[0] && height <= item.value[1]) {
if (active.value !== item.name) {
- removeFun();
+ removeEntities();
+ removeLabel();
active.value = item.name;
item.gJson ? aggregation(item) : splashed();
}
@@ -83,6 +85,7 @@
if (!feature.position) return;
const position = Cesium.Cartesian3.fromDegrees(feature.position[0], feature.position[1]);
viewer.entities.add({
+ id: feature.id,
position: position,
label: {
// 随机整数
@@ -99,6 +102,12 @@
image: new Cesium.ConstantProperty(data2),
width: 24,
height: 24,
+ },
+ properties: {
+ id: feature.id,
+ customData: {
+ name: feature.name,
+ },
},
});
});
@@ -118,15 +127,60 @@
});
};
+ const getLabelDom = () => {
+ const vNode = h(MapPopUpBox, { data: '参数',removeLabel });
+ const tooltipContainer = document.createElement('div');
+ tooltipContainer.style.position = 'absolute';
+ tooltipContainer.style.transform = 'translateY(-50%)';
+ tooltipContainer.style.pointerEvents = 'none';
+ document.querySelector('.page-index').append(tooltipContainer);
+ render(vNode, tooltipContainer);
+ return tooltipContainer;
+ };
+
+ const labelBox = () => {
+ if (!labelDiv) {
+ labelDiv = getLabelDom();
+ }
+ const screenPosition = viewer.scene.cartesianToCanvasCoordinates(positionC3);
+ if (screenPosition) {
+ labelDiv.style.left = `${screenPosition.x}px`;
+ labelDiv.style.top = `${screenPosition.y}px`;
+ }
+ };
+
+ const clickFun = click => {
+ const pickedObject = viewer.scene.pick(click.position);
+ if (Cesium.defined(pickedObject) && pickedObject.id) {
+ const entity = pickedObject.id;
+ positionC3 = entity.position._value;
+ viewer.scene.postRender.addEventListener(labelBox);
+ }
+ };
+
+ const removeEntities = () => {
+ viewer.dataSources.removeAll(true);
+ viewer.entities.removeAll();
+ };
+ const removeLabel = () => {
+ viewer.scene.postRender.removeEventListener(labelBox);
+ if (labelDiv && labelDiv.parentNode) {
+ labelDiv.parentNode.removeChild(labelDiv);
+ labelDiv = null;
+ }
+ };
+
onUnmounted(() => {
- console.log('xiezai');
- removeFun();
+ removeEntities();
+ removeLabel();
+ handler?.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_CLICK);
});
onMounted(() => {
- console.log('触发');
nextTick(() => {
viewer = window.$viewer;
+ handler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);
+ handler.setInputAction(clickFun, Cesium.ScreenSpaceEventType.LEFT_CLICK);
init();
});
});
--
Gitblit v1.9.3