Merge branch 'qzc-dev'

qzc-dev
秦子超 2025-10-28 15:23:53 +08:00
commit 3dc6a55529
12 changed files with 1558 additions and 255 deletions

10
.cnb.yml Normal file
View File

@ -0,0 +1,10 @@
$:
vscode:
- docker:
image: docker.cnb.cool/qzc120/dev-java-env
services:
- vscode
- docker
stages:
- name: node version
script: node -v

362
public/data/json/czml1.json Normal file

File diff suppressed because one or more lines are too long

421
public/data/json/czml2.json Normal file

File diff suppressed because one or more lines are too long

View File

@ -290,27 +290,6 @@ export default class Map3D extends BaseMap {
}
});
// 假设你已经有了一个Viewer实例名为viewer
var handler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);
handler.setInputAction(function(click) {
// 在这里处理点击事件
var cartesian = viewer.camera.pickEllipsoid(click.position, viewer.scene.globe.ellipsoid);
if (cartesian) {
var cartographic = Cesium.Cartographic.fromCartesian(cartesian);
var longitudeString = Cesium.Math.toDegrees(cartographic.longitude).toFixed(12);
var latitudeString = Cesium.Math.toDegrees(cartographic.latitude).toFixed(12);
// console.log(longitudeString+','+latitudeString+','+0+',');
let list = sessionStorage.getItem('myList')||''
list = list + longitudeString+','+latitudeString+','+0+','
sessionStorage.setItem('myList',list)
// 你可以在这里添加更多的逻辑,比如创建一个标记或者显示信息等
} else {
console.log('点击位置不在地面上');
}
}, Cesium.ScreenSpaceEventType.LEFT_CLICK); // 或者使用其他类型的点击事件如RIGHT_CLICK等
this._map = viewer;
const toremove = document.getElementsByClassName('cesium-widget-credits');
if (toremove && toremove[0]) {
@ -376,11 +355,40 @@ export default class Map3D extends BaseMap {
demo.getQxsy(viewer) //倾斜摄影 先加载模型
// demo.getDem(viewer) //地形图
// this.demo.getCzml2(viewer) //demo
// this.demo.getWater(viewer)//简单淹没分析
// demo.getWater(viewer)//水面
// this.demo.getWater3(viewer)
// demo.getTool(viewer)//工具
// await this.demo.getWater2(viewer,[
// 114.784551451219,31.505432945988,10,
// 114.783956879057,31.505116255788,20,
// 114.783778529129,31.504685509343,10,
// 114.784339602099,31.504773152014,20
// ],1)//简单淹没分析
// await this.demo.getWater2(viewer,[
// 114.785551451219,31.505432945988,10,
// 114.784956879057,31.505116255788,20,
// 114.784778529129,31.504685509343,10,
// 114.785339602099,31.504773152014,20
// ],2)//简单淹没分析
// await this.demo.getWater2(viewer,[
// 114.786551451219,31.505432945988,10,
// 114.785956879057,31.505116255788,20,
// 114.785778529129,31.504685509343,10,
// 114.786339602099,31.504773152014,20
// ],3)//简单淹没分析
// await this.demo.getWater2(viewer,[
// 114.786551451219,31.505432945988,50,
// 114.785956879057,31.505116255788,50,
// 114.785778529129,31.504685509343,50,
// 114.786339602099,31.504773152014,50
// ],4)//简单淹没分析
// this.demo.getWater2(viewer)
// this.demo.getRlt2(viewer)
// this.demo.getRlt3(viewer) //热力图
// this.demo.getCzml(viewer) //czml模型
// demo.getCzml3(viewer,`${process.env.PUBLIC_URL}/data/json/czml2.json`)
}
}

View File

@ -1,3 +1,4 @@
import { message } from "antd";
const { Cesium } = window;
@ -30,26 +31,52 @@ export default class LayerMgr {
}
getWater(viewer) {
const positions = [
114.740091973135,31.473712641972,
114.745265596247,31.479994736875,
114.750329463975,31.483633959554,
114.750661051206,31.484780352333,
114.754886312331,31.487387419599,
114.754490646828,31.489155789295,
114.755516914722,31.491816181377,
114.768854784357,31.501109797855,
114.772457389836,31.499611674743,
114.775859436013,31.495997057327,
114.776856155438,31.489458448100,
114.775657108202,31.485776315034,
114.771130342603,31.484720767205,
114.766996228018,31.483154944661,
114.763789073715,31.482059512488,
114.763333322583,31.479400016248,
114.763240976393,31.478143088357,
114.757178107927,31.474480278261,
114.754716711764,31.473552597977,
114.750378828013,31.473575767594,
114.77675678813289,
31.50180546471619,
114.77634098370115,
31.50542393675391,
114.77550528273461,
31.510034091676733,
114.76181457280028,
31.510550354470166,
114.75164827411291,
31.50237363184094,
114.74693792078983,
31.494305094539648,
114.75089835768581,
31.489323507071866,
114.74828759533041,
31.484564784156298,
114.73831609660566,
31.47788612938418,
114.73648859987517,
31.476034790740655,
114.73503896337203,
31.464304557468044,
114.73441754819322,
31.459120238450918,
114.73210787659028,
31.45435138945089,
114.73361772956933,
31.448659230621846,
114.74062065745993,
31.446548384991367,
114.74785114548382,
31.449778180265145,
114.752398578536,
31.4601089608599,
114.75267025727172,
31.468191348475756,
114.76405296055991,
31.474934726034768,
114.77030456751463,
31.480634200338496,
114.77669634290318,
31.482151917363133,
114.77890327320979,
31.491028304714956,
114.77765207166381,
31.499999605228414
]
// let initialHeight = 74
// let initialHeight = 76
@ -57,33 +84,29 @@ export default class LayerMgr {
// let initialHeight = 80
// let initialHeight = 82
// let initialHeight = 84
let initialHeight = 86
let initialHeight = 16
const geometry = new Cesium.PolygonGeometry({
polygonHierarchy: new Cesium.PolygonHierarchy(
Cesium.Cartesian3.fromDegreesArray(positions)
// Cesium.Cartesian3.fromDegreesArrayHeights([
// 114.783551451219,31.505432945988,80,
// 114.782956879057,31.505116255788,75,
// 114.781892213916,31.504914405850,70,
// 114.781157359053,31.504636741222,60,
// 114.780745721874,31.504325618018,60,
// 114.780212874098,31.504512397056,60,
// 114.779408140669,31.504317896297,60,
// 114.778706035963,31.503755212927,60,
// 114.779390892782,31.503920292944,60,
// 114.779897537800,31.504217938631,60,
// 114.780613891771,31.504189821141,60,
// 114.781129433998,31.504145193492,60,
// 114.781906501107,31.504529518304,70,
// 114.782778529129,31.504685509343,75,
// 114.783339602099,31.504773152014,80
// ])
// Cesium.Cartesian3.fromDegreesArray(positions)
Cesium.Cartesian3.fromDegreesArrayHeights([
114.75030666905982,
31.514474802727907,
56,
114.78743878565982,
31.49794345691234,
56,
114.7473100168242,
31.441979278096152,
53,
114.72212525085469,
31.453807583577174,
53
])
),
extrudedHeight: initialHeight,
// extrudedHeight: 0,
// extrudedHeight: initialHeight,
extrudedHeight: -100,
perPositionHeight:true,
});
const waterPrimitive = new Cesium.Primitive({
@ -107,6 +130,7 @@ export default class LayerMgr {
show: true,
// releaseGeometryInstances: false
});
waterPrimitive.id = 'Water1'
viewer.scene.primitives.add(waterPrimitive);
// 自动抬升
let height = 0;
@ -127,20 +151,254 @@ export default class LayerMgr {
// }, 100);
}
getWater2(viewer) {
// const waterSurface = viewer.entities.add({
// rectangle: {
// coordinates: Cesium.Rectangle.fromDegrees(114.9, 31.4, 115.9, 32.4),
// material: new Cesium.WaterMaterial({
// normalMapUrl: `${process.env.PUBLIC_URL}/models/waternormals.jpg`, // 水波纹法线贴图
// frequency: 1000.0, // 波纹密度
// animationSpeed: 0.05, // 波动速度
// amplitude: 5.0 // 波高
// }),
// height: 130.0 // 水面高度(可动态调整)
// }
// });
async getWater2(viewer,data,index) {
let positions = data|| [
114.783551451219,31.505432945988,80,
114.782956879057,31.505116255788,75,
114.782778529129,31.504685509343,75,
114.783339602099,31.504773152014,80
]
const primitives = viewer.scene.primitives;
let WaterPrimitives = null
// //判断是否存在Primitive
for (let i = primitives.length - 1; i >= 0; i--) {
if (primitives.get(i).id ===('myWater'+(index-1))) {
setTimeout(() => {
viewer.scene.primitives.remove(primitives.get(i));
}, 500);
// WaterPrimitives = primitives.get(i)
}
}
if(false){
//已经创建Primitive只需要更新数据
// const attributes = WaterPrimitives.getGeometryInstanceAttributes();
// const newCartesians = Cesium.Cartesian3.fromDegreesArrayHeights(positions);
// // 计算高精度坐标
// const newPositions = new Float64Array(newCartesians.length * 3);
// const newPositionsHigh = new Float32Array(newCartesians.length * 3);
// const newPositionsLow = new Float32Array(newCartesians.length * 3);
// for (let i = 0; i < newCartesians.length; ++i) {
// // 将 Cartesian3 转换为高精度表示
// Cesium.Cartesian3.pack(newCartesians[i], newPositions, i * 3);
// // 编码高精度坐标
// Cesium.EncodedCartesian3.encode(newCartesians[i], newPositionsHigh, newPositionsLow, i * 3);
// }
// // 更新几何实例的顶点坐标
// attributes.position = newPositions;
// attributes.position3DHigh = newPositionsHigh;
// attributes.position3DLow = newPositionsLow;
// // 告诉 Cesium 该属性的值需要更新
// attributes.position.needsUpdate = true;
// attributes.position3DHigh.needsUpdate = true;
// attributes.position3DLow.needsUpdate = true;
}else{
//需要创建Primitive
const waterPrimitive = new Cesium.Primitive({
geometryInstances: new Cesium.GeometryInstance({
geometry:new Cesium.PolygonGeometry({
polygonHierarchy: new Cesium.PolygonHierarchy(
Cesium.Cartesian3.fromDegreesArrayHeights(positions)
),
extrudedHeight: 0,
perPositionHeight:true,
})
}),
appearance: new Cesium.EllipsoidSurfaceAppearance({
aboveGround: true,
material: new Cesium.Material({
fabric: {
type: 'Water',
uniforms: {
baseWaterColor: new Cesium.Color(64 / 255.0, 157 / 255.0, 253 / 255.0, 1), // 水的基本颜色
// normalMap: Cesium.buildModuleUrl(
// `${process.env.PUBLIC_URL}/models/waternormals.jpg`
// ),
frequency: 1000.0,
animationSpeed: 0.01,
amplitude: 10,
specularIntensity: 1, // 镜面反射强度
},
},
}),
}),
releaseGeometryInstances:false,
show: true,
});
waterPrimitive.id = 'myWater'+index
viewer.scene.primitives.add(waterPrimitive);
}
await this.sleep(5000)
// const attributes = WaterPrimitives.getGeometryInstanceAttributes();
// const newCartesians = Cesium.Cartesian3.fromDegreesArrayHeights(positions);
// // 计算高精度坐标
// const newPositions = new Float64Array(newCartesians.length * 3);
// const newPositionsHigh = new Float32Array(newCartesians.length * 3);
// const newPositionsLow = new Float32Array(newCartesians.length * 3);
// for (let i = 0; i < newCartesians.length; ++i) {
// // 将 Cartesian3 转换为高精度表示
// Cesium.Cartesian3.pack(newCartesians[i], newPositions, i * 3);
// // 编码高精度坐标
// Cesium.EncodedCartesian3.encode(newCartesians[i], newPositionsHigh, newPositionsLow, i * 3);
// }
// // 更新几何实例的顶点坐标
// attributes.position = newPositions;
// attributes.position3DHigh = newPositionsHigh;
// attributes.position3DLow = newPositionsLow;
// // 告诉 Cesium 该属性的值需要更新
// attributes.position.needsUpdate = true;
// attributes.position3DHigh.needsUpdate = true;
// attributes.position3DLow.needsUpdate = true;
}
//全村的希望
async getWater3(viewer) {
// baseWaterColor: new Cesium.Color(64 / 255.0, 157 / 255.0, 253 / 255.0, 1), // 水的基本颜色
// normalMap: normalMap,
// // normalMap: Cesium.buildModuleUrl(
// // `${process.env.PUBLIC_URL}/models/waternormals.jpg`
// // ),
// frequency: 1000.0,
// animationSpeed: 0.01,
// amplitude: 10,
// specularIntensity: 1, // 镜面反射强度
const simpleWaterMaterial = new Cesium.Material({
fabric: {
type: 'FixedWater',
uniforms: {
color: new Cesium.Color(64 / 255.0, 157 / 255.0, 253 / 255.0, 1),
highlightColor: new Cesium.Color(0.5, 0.8, 1.0, 1),
speed: 0.01,
// frequency: 50.0
frequency: 1000.0,
animationSpeed: 0.01,
amplitude: 10,
specularIntensity: 1, // 镜面反射强度
},
source:
`
czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
vec2 st = materialInput.st;
float time = czm_frameNumber * speed;
// 创建多层波纹
float wave1 = sin(st.x * frequency * 2.0 + st.y * frequency + time) * 0.4;
float wave2 = cos(st.x * frequency * 1.5 - st.y * frequency * 1.2 + time * 1.7) * 0.3;
float wave3 = sin(st.x * frequency * 3.0 + st.y * frequency * 0.8 + time * 0.6) * 0.2;
float combinedWave = (wave1 + wave2 + wave3) / 3.0;
// 颜色混合 - 基础色与高光色
vec3 waterColor = mix(color.rgb, highlightColor.rgb,
abs(combinedWave) * 2.0);
// 透明度变化
float alpha = color.a * (0.6 + combinedWave * 0.4);
material.diffuse = waterColor;
material.alpha = alpha;
material.specular = 0.7 + combinedWave * 0.3;
material.shininess = 50.0; // 增加光泽度
return material;
}
`
}
});
// 创建水面Primitive
const waterPrimitive = new Cesium.Primitive({
geometryInstances: new Cesium.GeometryInstance({
geometry: new Cesium.PolygonGeometry({
polygonHierarchy: new Cesium.PolygonHierarchy(
Cesium.Cartesian3.fromDegreesArrayHeights([
114.740091973135,31.473712641972,10,
114.745265596247,31.479994736875,10,
114.750329463975,31.483633959554,10,
114.750661051206,31.484780352333,10,
114.754886312331,31.487387419599,10,
114.754490646828,31.489155789295,10,
114.755516914722,31.491816181377,10,
114.768854784357,31.501109797855,10,
114.772457389836,31.499611674743,10,
114.775859436013,31.495997057327,10,
114.776856155438,31.489458448100,10,
114.775657108202,31.485776315034,10,
114.771130342603,31.484720767205,10,
114.766996228018,31.483154944661,10,
114.763789073715,31.482059512488,10,
114.763333322583,31.479400016248,10,
114.763240976393,31.478143088357,10,
114.757178107927,31.474480278261,10,
114.754716711764,31.473552597977,10,
114.750378828013,31.473575767594,10,
])
),
// extrudedHeight: 0.1,
perPositionHeight: true,
vertexFormat: Cesium.MaterialAppearance.VERTEX_FORMAT
})
}),
appearance: new Cesium.MaterialAppearance({
material: simpleWaterMaterial,
translucent: true
}),
show:true,
});
const waterPrimitive2 = new Cesium.Primitive({
geometryInstances: new Cesium.GeometryInstance({
geometry: new Cesium.PolygonGeometry({
polygonHierarchy: new Cesium.PolygonHierarchy(
Cesium.Cartesian3.fromDegreesArrayHeights([
114.740091973135,31.473712641972,200,
114.745265596247,31.479994736875,200,
114.750329463975,31.483633959554,200,
114.750661051206,31.484780352333,200,
114.754886312331,31.487387419599,200,
114.754490646828,31.489155789295,200,
114.755516914722,31.491816181377,200,
114.768854784357,31.501109797855,200,
114.772457389836,31.499611674743,200,
114.775859436013,31.495997057327,200,
114.776856155438,31.489458448200,200,
114.775657108202,31.485776315034,200,
114.771130342603,31.484720767205,200,
114.766996228018,31.483154944661,200,
114.763789073715,31.482059512488,200,
114.763333322583,31.479400016248,200,
114.763240976393,31.478143088357,200,
114.757178107927,31.474480278261,200,
114.754716711764,31.473552597977,200,
114.750378828013,31.473575767594,200,
])
),
// extrudedHeight: 0.1,
perPositionHeight: true,
vertexFormat: Cesium.MaterialAppearance.VERTEX_FORMAT
})
}),
appearance: new Cesium.MaterialAppearance({
material: simpleWaterMaterial,
translucent: true
}),
show:false,
});
// 添加到场景
viewer.scene.primitives.add(waterPrimitive);
viewer.scene.primitives.add(waterPrimitive2);
await this.sleep(6000)
waterPrimitive.show = false
waterPrimitive2.show = true
}
async getQxsy(viewer) {
@ -1237,85 +1495,80 @@ export default class LayerMgr {
];
// const czml = [
// {
// id: "document",
// name: "CZML Polygon - Intervals and Availability",
// version: "1.0",
// clock: {
// interval: "2000-01-01T04:00:00Z/2000-01-01T04:00:02Z",
// currentTime: "2000-01-01T04:00:12Z",
// multiplier: 1,
// // range:'CLAMPED'
// },
// },
// {
// id: "blueRiverRight",
// name: "blueRiverRightName",
// availability: "2000-01-01T04:00:00Z/2000-01-01T04:00:14Z",
// polygon: {
// positions: [
// {
// interval: "2000-01-01T04:00:00Z/2000-01-01T04:00:01Z",
// cartographicDegrees: [
// 114.783551451219,31.505432945988,80,
// 114.782956879057,31.505116255788,75,
// 114.781892213916,31.504914405850,70,
// 114.781157359053,31.504636741222,60,
// 114.780745721874,31.504325618018,60,
// 114.780212874098,31.504512397056,60,
// 114.779408140669,31.504317896297,60,
// 114.778706035963,31.503755212927,60,
// 114.779390892782,31.503920292944,60,
// 114.779897537800,31.504217938631,60,
// 114.780613891771,31.504189821141,60,
// 114.781129433998,31.504145193492,60,
// 114.781906501107,31.504529518304,70,
// 114.782778529129,31.504685509343,75,
// 114.783339602099,31.504773152014,80
// ],
// },
// {
// interval: "2000-01-01T04:00:01Z/2000-01-01T04:00:02Z",
// cartographicDegrees: [
// 114.783551451219,31.505432945988,60,
// 114.782956879057,31.505116255788,60,
// 114.781892213916,31.504914405850,60,
// 114.781157359053,31.504636741222,60,
// 114.780745721874,31.504325618018,60,
// 114.780212874098,31.504512397056,60,
// 114.779408140669,31.504317896297,60,
// 114.778706035963,31.503755212927,60,
// 114.778671438258,31.503393234354,60,
// 114.779390892782,31.503920292944,60,
// 114.779897537800,31.504217938631,60,
// 114.780613891771,31.504189821141,60,
// 114.781129433998,31.504145193492,60,
// 114.781906501107,31.504529518304,60,
// 114.782778529129,31.504685509343,60,
// 114.783339602099,31.504773152014,60,
// ],
// },
// ],
// material: {
// solidColor: {
// color: [
// {
// rgba: [85, 119, 243, 125],
// },
// ],
// },
// },
// extrudedHeight: 50,
// perPositionHeight: true,
// },
// },
// ];
const czml2 = [
{
id: "document",
name: "CZML Polygon - Intervals and Availability",
version: "1.0",
clock: {
interval: "2000-01-01T04:00:00Z/2000-01-01T04:00:20Z",
currentTime: "2000-01-01T04:00:00Z",
multiplier: 1,
},
},
{
id: "testdata",
name: "testdata",
availability: "2000-01-01T04:00:00Z/2000-01-01T04:00:20Z",
polygon: {
positions: [
{
interval: "2000-01-01T04:00:00Z/2000-01-01T04:00:01Z",
cartographicDegrees: [
114.783551451219,31.505432945988,80,
114.782956879057,31.505116255788,75,
114.782778529129,31.504685509343,75,
114.783339602099,31.504773152014,80
],
},
{
interval: "2000-01-01T04:00:01Z/2000-01-01T04:00:02Z",
cartographicDegrees: [
114.783551451219,31.505432945988,180,
114.782956879057,31.505116255788,175,
114.782778529129,31.504685509343,175,
114.783339602099,31.504773152014,180
],
},
{
interval: "2000-01-01T04:00:02Z/2000-01-01T04:00:03Z",
cartographicDegrees: [
114.783551451219,31.505432945988,280,
114.782956879057,31.505116255788,275,
114.782778529129,31.504685509343,275,
114.783339602099,31.504773152014,280
],
},
],
// material: {
// solidColor: {
// color: [
// {
// rgba: [85, 119, 243, 125],
// },
// ],
// },
// },
// material: {
// image: {
// image: {
// uri: `${process.env.PUBLIC_URL}/models/waternormals.jpg`
// },
// repeat: {
// cartesian2: [2, 2] // 控制纹理重复次数,可根据需要调整
// },
// color: {
// rgba: [255, 255, 255, 125] // 控制纹理颜色和透明度
// }
// }
// },
extrudedHeight: 50,
perPositionHeight: true,
},
},
];
viewer.dataSources.add(Cesium.CzmlDataSource.load(czml));
viewer.dataSources.add(Cesium.CzmlDataSource.load(czml2));
viewer.clock.shouldAnimate = false; // 暂停动画
// var specificTime = Cesium.JulianDate.fromIso8601('2000-01-01T04:00:04Z');
@ -1327,6 +1580,157 @@ export default class LayerMgr {
// viewer.clock.currentTime = Cesium.JulianDate.fromDate(new Date(2000, 1, 1, 0, 0, 8));
}
//地图取点工具
getTool(viewer) {
// 存储点击的坐标
var clickedPositions = [];
const jwd = []
var hoverPoint = null;
var polygonEntity = null;
var polylineEntity = null;
// 创建悬浮点
hoverPoint = viewer.entities.add({
position: Cesium.Cartesian3.ZERO,
point: {
pixelSize: 8,
color: Cesium.Color.YELLOW,
outlineColor: Cesium.Color.BLACK,
outlineWidth: 1,
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND
},
show: false
});
// 鼠标移动事件
var handler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);
handler.setInputAction(function(movement) {
// // 获取鼠标位置的地球表面的点
// var ray = viewer.camera.getPickRay(movement.endPosition);
// var position = viewer.scene.globe.pick(ray, viewer.scene);
// if (position) {
// // 更新悬浮点位置
// hoverPoint.position = position;
// hoverPoint.show = true;
// } else {
// hoverPoint.show = false;
// }
// 使用更精确的拾取方法支持3D Tiles
const pickedObject = viewer.scene.pick(movement.endPosition);
// if (pickedObject && pickedObject.id && pickedObject.id instanceof Cesium.Entity) {
// // 如果是实体对象,跳过处理
// return;
// }
// 使用pickPosition获取精确的3D坐标支持3D Tiles
const position = viewer.scene.pickPosition(movement.endPosition);
if (position) {
// 更新悬浮点位置
// 移除之前的临时点
if (hoverPoint) {
viewer.entities.remove(hoverPoint);
}
// 创建新的临时悬浮点
hoverPoint = viewer.entities.add({
position: position,
point: {
pixelSize: 8,
color: Cesium.Color.YELLOW,
outlineColor: Cesium.Color.BLACK,
outlineWidth: 1,
heightReference: Cesium.HeightReference.NONE // 不使用贴地,使用精确坐标
}
});
} else {
// hoverPoint.show = false;
}
}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
// 鼠标点击事件
handler.setInputAction(function(click) {
var ray = viewer.camera.getPickRay(click.position);
// var position = viewer.scene.globe.pick(ray, viewer.scene);
const position = viewer.scene.pickPosition(click.position);
if (position) {
// 将点击的点添加到数组中
clickedPositions.push(position);
// 新增:将笛卡尔坐标转换为经纬度并存储
const cartographic = Cesium.Cartographic.fromCartesian(position);
const longitude = Cesium.Math.toDegrees(cartographic.longitude);
const latitude = Cesium.Math.toDegrees(cartographic.latitude);
jwd.push(longitude)
jwd.push(latitude)
jwd.push(614179224)
message.success(longitude+','+latitude,1)
// 如果点击点数大于等于2则更新折线
if (clickedPositions.length >= 2) {
// 如果折线已经存在,则更新,否则创建
if (polylineEntity) {
viewer.entities.remove(polylineEntity);
}
polylineEntity = viewer.entities.add({
polyline: {
positions: clickedPositions,
width: 3,
material: Cesium.Color.YELLOW,
clampToGround: true
}
});
}
}
}, Cesium.ScreenSpaceEventType.LEFT_CLICK);
// 右键点击删除最后一个点
handler.setInputAction(function(click) {
if (clickedPositions.length > 0) {
// 删除最后一个点
clickedPositions.pop();
jwd.pop()
jwd.pop()
jwd.pop()
message.info('删除')
console.log(jwd);
// 更新折线
if (polylineEntity) {
viewer.entities.remove(polylineEntity);
polylineEntity = null;
}
// 如果有剩余的点,重新创建折线
if (clickedPositions.length >= 2) {
polylineEntity = viewer.entities.add({
polyline: {
positions: clickedPositions,
width: 3,
material: Cesium.Color.YELLOW,
clampToGround: true
}
});
}
}
}, Cesium.ScreenSpaceEventType.RIGHT_CLICK);
}
async getCzml3(viewer,path) {
viewer.dataSources._dataSources.forEach(dataSource => {
if (dataSource.name === 'CZML1111') { // 确保你知道你想要移除的数据源名称
viewer.dataSources.remove(dataSource);
}
});
const { czml } = await fetch(path)
.then(resp => resp.json())
.then(data => data)
.catch(() => []);
viewer.dataSources.add(Cesium.CzmlDataSource.load(czml));
viewer.clock.shouldAnimate = false; // 暂停动画
}
}

View File

View File

@ -7,6 +7,7 @@ import Map2D from './M2D/Map2D';
import Map3D from './Map3D/Map3D';
import Markers from './Markers';
import { useLocation, useNavigate } from "react-router";
// const { Cesium } = window;
let id_factory_index = 1;
@ -18,6 +19,7 @@ export default function MapCtrl({mode}) {
const [_, forceRender] = useReducer(s => s + 1, 1);
const cameraTarget = useSelector(s => s.runtime.cameraTarget);
const layerVisible = useSelector(s => s.map.layerVisible);
// const map = useSelector(s => s.map.map);
const layerSetting = useSelector(s => s.map.layerSetting);
const clickLoopBtn = useSelector(s => s.map.clickLoopBtn);
const layerSetting1 = useSelector(s => s.runtime.layerSetting);
@ -93,12 +95,42 @@ export default function MapCtrl({mode}) {
}
}, [layerSettingLoop, clickLoopBtn]);
// const myTest = (flag)=>{
// const height = flag?1:-1
// if(map){
// const primitives = map.scene.primitives;
// let waterPrimitive = null
// // //判断是否存在Primitive
// for (let i = primitives.length - 1; i >= 0; i--) {
// if (primitives.get(i).id ===('Water1')) {
// waterPrimitive = primitives.get(i)
// }
// }
// var currentModelMatrix = Cesium.Matrix4.clone(waterPrimitive.modelMatrix);
// // 定义平移向量例如沿x轴平移100单位
// var translation = new Cesium.Cartesian3(-height*0.7, height, height*0.8);
// // 创建一个平移矩阵
// var translationMatrix = Cesium.Matrix4.fromTranslation(translation);
// // 计算新的modelMatrix将平移矩阵应用到当前模型矩阵上
// var newModelMatrix = Cesium.Matrix4.multiply(translationMatrix, currentModelMatrix, new Cesium.Matrix4());
// waterPrimitive.modelMatrix = newModelMatrix;
// }
// }
return (
<div key={mode} id={ctrlIdRef.current} className="map2d3d">
<FeaturePops mapobj={mapobjRef.current} />
<FeatureTip />
{/*<CoordsText />*/}
<Markers mapobj={mapobjRef.current} />
{/* <div style={{background:'#fff',position:'absolute',display:'inline-block',left:'300px',top:"100px",zIndex:99}}>
<button onClick={()=>myTest(true)}>+</button>
<button onClick={()=>myTest(false)}>-</button>
<Input defaultValue={'2000-01-01T04:00:13Z'} onPressEnter={(e)=>{
if(map){
map.clock.currentTime = Cesium.JulianDate.fromIso8601(e.target.value);
}
}}></Input>
</div> */}
</div>
);
}

View File

@ -10,11 +10,11 @@ const Page = ({ data, setClock }) => {
const marks = {
[0]: {
style: { color: '#333' },
label: <span style={{width: "130px", fontSize: "12px", display:'inline-block', marginTop:'3px'}}>{data?.[0]?.tm||''}</span>,
label: <span style={{width: "130px", fontSize: "12px", display:'inline-block', marginTop:'3px'}}>{data?.[0]?.tm2||''}</span>,
},
[data.length - 1]: {
style: { color: '#333' },
label: <div style={{width: "130px", fontSize: "12px", display:'inline-block', marginTop:'3px', marginLeft: "-32px"}}>{data?.[data?.length-1]?.tm||""}</div>,
label: <div style={{width: "130px", fontSize: "12px", display:'inline-block', marginTop:'3px', marginLeft: "-32px"}}>{data?.[data?.length-1]?.tm2||""}</div>,
}
};
@ -67,7 +67,7 @@ const Page = ({ data, setClock }) => {
marks={marks}
tooltip={{
open:true,
formatter:(value) => data[value].tm
formatter:(value) => data[value].tm2
}}
onChange={(val) => setIndex(val)}
/>

View File

@ -11,42 +11,54 @@ import moment from 'moment';
const { Cesium } = window;
const records = [
{ tm:'2000-01-01 04:00:00', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:01', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:02', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:03', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:04', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:05', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:06', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:07', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:08', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:09', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:10', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:11', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:12', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:13', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:14', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:15', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:16', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:17', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:18', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:19', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:20', data:[], text:'测试' },
{ tm:'2000-01-01 04:00:00', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:01', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:02', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:03', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:04', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:05', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:06', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:07', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:08', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:09', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:10', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:11', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:12', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:13', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:14', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:15', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:16', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:17', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:18', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:19', data:[], text:'测试', tm2:null, },
{ tm:'2000-01-01 04:00:20', data:[], text:'测试', tm2:null, },
]
const Page = ({ showPanels, mode }) => {
const dispatch = useDispatch();
let mapObj = useSelector(s => s.map.map)
const [ map, setMap ] = useState(null)
const [ ctx, setCtx ] = useState({mode:'预报方案',data:{}})
const [ clock, setClock ] = useState(null)
const [ testData, setTestData ] = useState([])
const [ playerData, setPlayerData ] = useState([])
//将预报方案的时间,按照records的长度平均分配tm是cesium时间tm2是展示时间
useEffect(()=>{
setTimeout(() => {
setTestData(records)
}, 2000);
},[])
const startTime = ctx?.data?.tms?.startTime
const endTime = ctx?.data?.tms?.endTime
if( startTime && endTime ){
const start = new Date(startTime.replace(' ', 'T'));
const end = new Date(endTime.replace(' ', 'T'));
const interval = (end - start) / (records.length - 1);
const list = records.map((item, index) => ({
...item,
tm2: moment(new Date(start.getTime() + interval * index)).format('YYYY-MM-DD HH:mm:ss')
}));
setPlayerData(list)
}else{
setPlayerData([])
}
},[ctx])
useEffect(() => {
dispatch.map.setLayerVisible({
@ -58,7 +70,7 @@ const Page = ({ showPanels, mode }) => {
QSYDWLayer: true,
YHJMHLayer: true
});
const { mode } = ctx
const { mode, data } = ctx
//当前map对象是cesium
if(!mapObj?._cesiumWidget){
return
@ -75,7 +87,7 @@ const Page = ({ showPanels, mode }) => {
});
const demo = new Demo3D()
demo.getCzml2(mapObj)
demo.getCzml3(mapObj,data.czmlPath)
}else{
mapObj.dataSources._dataSources.forEach(dataSource => {
if (dataSource.name === 'CZML1111') { // 确保你知道你想要移除的数据源名称
@ -105,18 +117,18 @@ const Page = ({ showPanels, mode }) => {
});
}
}, [mapObj,ctx])
useEffect(()=>{
if(clock!==null && mapObj?._cesiumWidget && testData?.length>0){
const tm = testData[clock].tm
if(clock!==null && mapObj?._cesiumWidget && playerData?.length>0){
const tm = playerData[clock].tm
if(tm){
const str = `${moment(tm).format('YYYY-MM-DD')}T${moment(tm).format('HH:mm:ss')}Z`
mapObj.clock.currentTime = Cesium.JulianDate.fromIso8601(str);
}
}
if(clock===null){return}
},[clock,mapObj,testData])
},[clock,mapObj,playerData])
@ -130,7 +142,7 @@ const Page = ({ showPanels, mode }) => {
{
ctx.mode==='淹没统计' && mode==='3d'?
<div className='homePage_playerBox' style={!showPanels?{left:'50%'}:{}}>
<Player data={testData} setClock={setClock}/>
{ playerData.length>0 && <Player data={playerData} ctx={ctx} setClock={setClock}/> }
</div>:null
}
</div>

View File

@ -10,29 +10,34 @@ import apiurl from '../../../../service/apiurl';
import Fack from './fack'
import Tjpz from './tjpz'
const Page = ({projectId,onCancel,setCtx}) => {
const Page = ({project,onCancel,setCtx}) => {
const [data,setData] = useState({data:[],tms:{}})
const [tabs, setTabsChange] = useState(0)
useEffect(()=>{
(async()=>{
const {code , data} = await httpget2(apiurl.fxdd_xyt.hsyb.ybfagl.getData+'?projectId='+projectId)
const {code , data} = await httpget2(apiurl.fxdd_xyt.hsyb.ybfagl.getData+'?projectId='+project.id)
if(code!==200){
return
}
setData({data:[...data.voList],tms:{
forecastTime: data.forecastTm,
projectTm: data.projectTm,
startTime: data.startTm,
endTime: data.endTm,
forecastPeriod: data.forecastPeriod,
forecastWarm: data.forecastWarm,
type:data.type,
ycMaxSwH:data.ycMaxSwH,
ycMaxRkQ:data.ycMaxRkQ,
ycMaxCkQ:data.ycMaxCkQ,
ycSumFlood:data.ycSumFlood,
}})
setData({
data:[...data.voList],
tms:{
forecastTime: data.forecastTm,
projectTm: data.projectTm,
startTime: data.startTm,
endTime: data.endTm,
forecastPeriod: data.forecastPeriod,
forecastWarm: data.forecastWarm,
type:data.type,
ycMaxSwH:data.ycMaxSwH,
ycMaxRkQ:data.ycMaxRkQ,
ycMaxCkQ:data.ycMaxCkQ,
ycSumFlood:data.ycSumFlood,
},
czmlPath : project.czmlPath,
ymtj: project.ymtj
})
})()
},[])
return (

View File

@ -17,7 +17,7 @@ const Page = ({ setCtx }) => {
let mapObj = useSelector(s => s.map.map)
const [index,setIndex] = useState(0)
const [data,setData] = useState([])
const [projectId, setProjectId] = useState('')
const [project, setProject] = useState(null)
const [open, setOpen] = useState(false)
const [name, setName] = useState('')
const [tms,setTms] = useState([])
@ -50,17 +50,96 @@ const Page = ({ setCtx }) => {
const getData = async()=>{
const data = await getTableData()
setData([data[0]])
const data1 = {
...data[0],
ymtj:{
count:{
xhl:2.98,//泄洪量
zgymss:0.8,//最高淹没水深
ymls:48,//淹没历时
szmj:1.18,//受灾面积
szcz:2,//受灾村庄
szrk:217,//受灾人口
},
czList:[
{
cznm:'檀树岗村',
rk:98,
sd:0.3,
tm:'2024-06-21 18:00:00',
},
{
cznm:'程维德村',
rk:99,
sd:0.5,
tm:'2024-06-21 18:20:00',
}
],
qsydwList:[
{
dw:'七里坪镇檀树中学',
rk:20,
sd:0.5,
tm:'2024-06-21 18:00:00'
}
]
}
}
const data2 = {
...data[1],
ymtj:{
count:{
xhl:4.56,//泄洪量
zgymss:0.8,//最高淹没水深
ymls:49,//淹没历时
szmj:2.88,//受灾面积
szcz:3,//受灾村庄
szrk:219,//受灾人口
},
czList:[
{
cznm:'檀树岗村',
rk:96,
sd:0.3,
tm:'2024-11-13 18:00:00',
},
{
cznm:'程维德村',
rk:99,
sd:0.5,
tm:'2024-11-13 18:20:00',
},
{
cznm:'戴世英村',
rk:12,
sd:0.8,
tm:'2024-11-13 18:50:00',
},
],
qsydwList:[
{
dw:'七里坪镇檀树中学',
rk:20,
sd:0.5,
tm:'2024-06-21 18:00:00'
}
]
}
}
setData([data1,data2])
}
const openModal = (item)=>{
if(index===0){ item.czmlPath = `${process.env.PUBLIC_URL}/data/json/czml1.json` }
if(index===1){ item.czmlPath = `${process.env.PUBLIC_URL}/data/json/czml2.json` }
setOpen(true)
setProjectId(item.id)
setProject(item)
}
const closeModal = ()=>{
setOpen(false)
setProjectId(null)
setProject(null)
}
return (
@ -115,7 +194,7 @@ const Page = ({ setCtx }) => {
</div>
<Modal width={1500} wrapClassName='home_modal' bodyStyle={{padding:0}} title={null} closable={false} footer={null} open={open} onCancel={closeModal} destroyOnClose={true}>
<ModalForm projectId={projectId} onCancel={closeModal} setCtx={setCtx}/>
<ModalForm project={project} index={index} onCancel={closeModal} setCtx={setCtx}/>
</Modal>
</>
)

View File

@ -12,49 +12,19 @@ const { RangePicker } = DatePicker
const Page = ({ ctx, setCtx }) => {
const dispatch = useDispatch();
let mapObj = useSelector(s => s.map.map)
const [data1,setData1] = useState([
{
cz:'檀树岗村',
rk:28,
sd:0.3,
sj:'2025-08-04 18:00:00',
},
{
cz:'程维德村',
rk:6,
sd:0.5,
sj:'2025-08-04 18:20:00',
},
{
cz:'戴世英村',
rk:6,
sd:0.8,
sj:'2025-08-04 18:50:00',
},
])
const [data2,setData2] = useState([
{
dwmc:'七里坪镇檀树中学',
rk:10,
sd:0.5,
sj:'2025-08-04 18:00:00',
}
])
const columns = [
{ title: '受灾村庄', key: 'cz', dataIndex: 'cz', align:"center"},
{ title: '受灾村庄', key: 'cznm', dataIndex: 'cznm', align:"center"},
{ title: '受灾人口(人)', key: 'rk', dataIndex: 'rk', width:'80px', align:"center"},
{ title: '最高淹没深度(m)', key: 'sd', dataIndex: 'sd', width:'100px', align:"center"},
{ title: '洪峰时间', key: 'sj', dataIndex: 'sj', align:"center"},
{ title: '洪峰时间', key: 'tm', dataIndex: 'tm', align:"center"},
];
const columns2 = [
{ title: '单位名称', key: 'dwmc', dataIndex: 'dwmc', align:"center"},
{ title: '单位名称', key: 'dw', dataIndex: 'dw', align:"center"},
{ title: '影响人口(人)', key: 'rk', dataIndex: 'rk', width:'80px', align:"center"},
{ title: '最高淹没深度(m)', key: 'sd', dataIndex: 'sd', width:'100px', align:"center"},
{ title: '洪峰时间', key: 'sj', dataIndex: 'sj', align:"center"},
{ title: '洪峰时间', key: 'tm', dataIndex: 'tm', align:"center"},
];
@ -79,32 +49,32 @@ const Page = ({ ctx, setCtx }) => {
<div className='ymtjBox'>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/xhl.png`} alt=""/>
<div className='text1' style={{color:'#3B81FA'}}>2.98<div className='dw'>万m³</div></div>
<div className='text1' style={{color:'#3B81FA'}}>{ctx?.data?.ymtj?.count?.xhl}<div className='dw'>万m³</div></div>
<div className='text2'>泄洪量</div>
</div>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/ymss.png`} alt=""/>
<div className='text1' style={{color:'#38B63E'}}>0.8<div className='dw'>m</div></div>
<div className='text1' style={{color:'#38B63E'}}>{ctx?.data?.ymtj?.count?.zgymss}<div className='dw'>m</div></div>
<div className='text2'>最高淹没水深</div>
</div>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/ymls.png`} alt=""/>
<div className='text1' style={{color:'#D0A807'}}>25<div className='dw'>h</div></div>
<div className='text1' style={{color:'#D0A807'}}>{ctx?.data?.ymtj?.count?.ymls}<div className='dw'>h</div></div>
<div className='text2'>淹没历时</div>
</div>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/szmj.png`} alt=""/>
<div className='text1' style={{color:'#2999D4'}}>1.18<div className='dw'>km²</div></div>
<div className='text1' style={{color:'#2999D4'}}>{ctx?.data?.ymtj?.count?.szmj}<div className='dw'>km²</div></div>
<div className='text2'>受灾面积</div>
</div>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/szcz.png`} alt=""/>
<div className='text1' style={{color:'#2999D4'}}>3<div className='dw'></div></div>
<div className='text1' style={{color:'#2999D4'}}>{ctx?.data?.ymtj?.count?.szcz}<div className='dw'></div></div>
<div className='text2'>受灾村庄</div>
</div>
<div className='ymtjBoxItem'>
<img width={40} src={`${process.env.PUBLIC_URL}/assets/hsyy/szrk.png`} alt=""/>
<div className='text1' style={{color:'#2999D4'}}>40<div className='dw'></div></div>
<div className='text1' style={{color:'#2999D4'}}>{ctx?.data?.ymtj?.count?.szrk}<div className='dw'></div></div>
<div className='text2'>受灾人口</div>
</div>
</div>
@ -117,7 +87,7 @@ const Page = ({ ctx, setCtx }) => {
sticky
columns={columns}
pagination={false}
dataSource={data1}
dataSource={ctx?.data?.ymtj?.czList}
scroll={{ y: "500px"}}
/>
<div className='homePage_head2'>
@ -129,7 +99,7 @@ const Page = ({ ctx, setCtx }) => {
sticky
columns={columns2}
pagination={false}
dataSource={data2}
dataSource={ctx?.data?.ymtj?.qsydwList}
scroll={{ y: "500px"}}
/>
</div>